diff --git a/public_html/libgit/base.php b/public_html/libgit/base.php index d2bc08b..0b1f4bd 100644 --- a/public_html/libgit/base.php +++ b/public_html/libgit/base.php @@ -29,6 +29,13 @@ function number_from_bin($bin) return $c[1]; } +define("OBJ_COMMIT", 1); +define("OBJ_TREE", 2); +define("OBJ_BLOB", 3); +define("OBJ_TAG", 4); +define("OBJ_OFS_DELTA", 6); +define("OBJ_REF_DELTA", 7); + class GitBranchNotFoundException extends Exception {} class GitTagNotFoundException extends Exception {} class GitInvalidOriginException extends Exception {} @@ -36,7 +43,9 @@ class GitInvalidElementException extends Exception {} class GitInvalidFormatException extends Exception {} class GitUnsupportedVersionException extends Exception {} class GitPathNotFoundException extends Exception {} +class GitObjectNotFoundException extends Exception {} class GitCorruptIndexException extends Exception {} +class GitUnknownTypeException extends Exception {} require(dirname(__FILE__) . "/class.repository.php"); require(dirname(__FILE__) . "/class.branch.php"); diff --git a/public_html/libgit/class.pack.php b/public_html/libgit/class.pack.php index f66ce52..890732b 100644 --- a/public_html/libgit/class.pack.php +++ b/public_html/libgit/class.pack.php @@ -2,15 +2,62 @@ class GitPack { public $repo = null; - public $index = array(); + public $index = null; + public $pack_filename = ""; function __construct($repo, $name) { $this->repo = $repo; $index_filename = "{$repo->path}/objects/pack/{$name}.idx"; - $pack_filename = "{$repo->path}/objects/pack/{$name}.pack"; + $this->pack_filename = "{$repo->path}/objects/pack/{$name}.pack"; $this->index = new GitPackIndex(file_get_contents($index_filename)); } + + function UnpackObject($sha) + { + if(isset($this->index->index[$sha])) + { + $start = $this->index->index[$sha]; + + $file = fopen($this->pack_filename, "rb"); + fseek($file, $start); + + $header = ord(fread($file, 1)); + $type = ($header >> 4) & 7; + $hasnext = ($header & 128) >> 7; + $size = $header & 0xf; + $offset = 4; + + while($hasnext) + { + $byte = ord(fread($file, 1)); + $size |= ($byte & 0x7f) << $offset; + $hasnext = ($byte & 128) >> 7; + $offset += 7; + } + + switch($type) + { + case OBJ_COMMIT: + case OBJ_TREE: + case OBJ_BLOB: + case OBJ_TAG: + // this is a compressed object + $data = fread($file, $size); + break; + case OBJ_OFS_DELTA: + case OBJ_REF_DELTA: + // this is a delta + break; + default: + throw new GitUnknownTypeException("The object type is not supported."); + } + } + else + { + throw new GitObjectNotFoundException("The specified object does not exist in this pack."); + } + } }