rugged 0.17.0.b7 → 0.18.0.b1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/LICENSE +1 -1
- data/README.md +88 -32
- data/ext/rugged/extconf.rb +4 -2
- data/ext/rugged/rugged.c +72 -10
- data/ext/rugged/rugged.h +14 -10
- data/ext/rugged/rugged_blob.c +8 -10
- data/ext/rugged/rugged_branch.c +11 -14
- data/ext/rugged/rugged_commit.c +31 -24
- data/ext/rugged/rugged_config.c +2 -2
- data/ext/rugged/rugged_index.c +133 -198
- data/ext/rugged/rugged_note.c +372 -0
- data/ext/rugged/rugged_object.c +50 -22
- data/ext/rugged/rugged_reference.c +122 -130
- data/ext/rugged/rugged_remote.c +72 -29
- data/ext/rugged/rugged_repo.c +402 -20
- data/ext/rugged/rugged_revwalk.c +7 -3
- data/ext/rugged/rugged_settings.c +110 -0
- data/ext/rugged/rugged_signature.c +23 -7
- data/ext/rugged/rugged_tag.c +32 -16
- data/ext/rugged/rugged_tree.c +44 -15
- data/lib/rugged.rb +1 -0
- data/lib/rugged/index.rb +8 -0
- data/lib/rugged/remote.rb +13 -0
- data/lib/rugged/repository.rb +3 -3
- data/lib/rugged/version.rb +1 -1
- data/test/blob_test.rb +13 -15
- data/test/branch_test.rb +32 -67
- data/test/commit_test.rb +50 -12
- data/test/config_test.rb +12 -11
- data/test/coverage/HEAD.json +1 -1
- data/test/coverage/cover.rb +40 -21
- data/test/errors_test.rb +34 -0
- data/test/fixtures/alternate/objects/14/6ae76773c91e3b1d00cf7a338ec55ae58297e2 +0 -0
- data/test/fixtures/alternate/objects/14/9c32d47e99d0a3572ff1e70a2e0051bbf347a9 +0 -0
- data/test/fixtures/alternate/objects/14/fb3108588f9421bf764041e5e3ac305eb6277f +0 -0
- data/test/fixtures/testrepo.git/logs/refs/notes/commits +1 -0
- data/test/fixtures/testrepo.git/objects/44/1034f860c1d5d90e4188d11ae0d325176869a8 +1 -0
- data/test/fixtures/testrepo.git/objects/60/d415052a33de2150bf68757f6461df4f563ae4 +0 -0
- data/test/fixtures/testrepo.git/objects/68/8a8f4ef7496901d15322972f96e212a9e466cc +1 -0
- data/test/fixtures/testrepo.git/objects/94/eca2de348d5f672faf56b0decafa5937e3235e +0 -0
- data/test/fixtures/testrepo.git/objects/9b/7384fe1676186192842f5d3e129457b62db9e3 +0 -0
- data/test/fixtures/testrepo.git/objects/b7/4713326bc972cc15751ed504dca6f6f3b91f7a +3 -0
- data/test/fixtures/testrepo.git/refs/notes/commits +1 -0
- data/test/index_test.rb +65 -69
- data/test/lib_test.rb +76 -11
- data/test/note_test.rb +158 -0
- data/test/object_test.rb +8 -11
- data/test/reference_test.rb +77 -85
- data/test/remote_test.rb +86 -8
- data/test/repo_pack_test.rb +9 -7
- data/test/repo_reset_test.rb +80 -0
- data/test/repo_test.rb +176 -53
- data/test/tag_test.rb +44 -7
- data/test/test_helper.rb +63 -35
- data/test/tree_test.rb +34 -13
- data/test/walker_test.rb +14 -14
- data/vendor/libgit2/Makefile.embed +1 -1
- data/vendor/libgit2/deps/http-parser/http_parser.c +974 -578
- data/vendor/libgit2/deps/http-parser/http_parser.h +106 -70
- data/vendor/libgit2/deps/regex/regcomp.c +7 -6
- data/vendor/libgit2/deps/regex/regex_internal.c +1 -1
- data/vendor/libgit2/deps/regex/regex_internal.h +12 -3
- data/vendor/libgit2/deps/regex/regexec.c +5 -5
- data/vendor/libgit2/include/git2.h +5 -1
- data/vendor/libgit2/include/git2/attr.h +4 -2
- data/vendor/libgit2/include/git2/blob.h +39 -12
- data/vendor/libgit2/include/git2/branch.h +123 -35
- data/vendor/libgit2/include/git2/checkout.h +206 -48
- data/vendor/libgit2/include/git2/clone.h +72 -27
- data/vendor/libgit2/include/git2/commit.h +20 -17
- data/vendor/libgit2/include/git2/common.h +67 -1
- data/vendor/libgit2/include/git2/config.h +81 -60
- data/vendor/libgit2/include/git2/cred_helpers.h +53 -0
- data/vendor/libgit2/include/git2/diff.h +459 -150
- data/vendor/libgit2/include/git2/errors.h +9 -1
- data/vendor/libgit2/include/git2/graph.h +41 -0
- data/vendor/libgit2/include/git2/ignore.h +7 -6
- data/vendor/libgit2/include/git2/index.h +323 -97
- data/vendor/libgit2/include/git2/indexer.h +27 -59
- data/vendor/libgit2/include/git2/inttypes.h +4 -0
- data/vendor/libgit2/include/git2/merge.h +13 -3
- data/vendor/libgit2/include/git2/message.h +14 -8
- data/vendor/libgit2/include/git2/net.h +9 -7
- data/vendor/libgit2/include/git2/notes.h +88 -29
- data/vendor/libgit2/include/git2/object.h +16 -6
- data/vendor/libgit2/include/git2/odb.h +80 -17
- data/vendor/libgit2/include/git2/odb_backend.h +47 -11
- data/vendor/libgit2/include/git2/oid.h +26 -17
- data/vendor/libgit2/include/git2/pack.h +62 -8
- data/vendor/libgit2/include/git2/push.h +131 -0
- data/vendor/libgit2/include/git2/refdb.h +103 -0
- data/vendor/libgit2/include/git2/refdb_backend.h +109 -0
- data/vendor/libgit2/include/git2/reflog.h +30 -21
- data/vendor/libgit2/include/git2/refs.h +215 -193
- data/vendor/libgit2/include/git2/refspec.h +22 -2
- data/vendor/libgit2/include/git2/remote.h +158 -37
- data/vendor/libgit2/include/git2/repository.h +150 -31
- data/vendor/libgit2/include/git2/reset.h +43 -9
- data/vendor/libgit2/include/git2/revparse.h +48 -4
- data/vendor/libgit2/include/git2/revwalk.h +25 -10
- data/vendor/libgit2/include/git2/signature.h +20 -12
- data/vendor/libgit2/include/git2/stash.h +121 -0
- data/vendor/libgit2/include/git2/status.h +122 -53
- data/vendor/libgit2/include/git2/strarray.h +17 -11
- data/vendor/libgit2/include/git2/submodule.h +42 -7
- data/vendor/libgit2/include/git2/tag.h +72 -59
- data/vendor/libgit2/include/git2/threads.h +4 -2
- data/vendor/libgit2/include/git2/trace.h +68 -0
- data/vendor/libgit2/include/git2/transport.h +328 -0
- data/vendor/libgit2/include/git2/tree.h +149 -120
- data/vendor/libgit2/include/git2/types.h +13 -12
- data/vendor/libgit2/include/git2/version.h +3 -3
- data/vendor/libgit2/src/amiga/map.c +2 -2
- data/vendor/libgit2/src/attr.c +58 -48
- data/vendor/libgit2/src/attr.h +4 -18
- data/vendor/libgit2/src/attr_file.c +30 -6
- data/vendor/libgit2/src/attr_file.h +6 -8
- data/vendor/libgit2/src/attrcache.h +24 -0
- data/vendor/libgit2/src/blob.c +30 -7
- data/vendor/libgit2/src/blob.h +1 -1
- data/vendor/libgit2/src/branch.c +361 -68
- data/vendor/libgit2/src/branch.h +17 -0
- data/vendor/libgit2/src/bswap.h +1 -1
- data/vendor/libgit2/src/buf_text.c +291 -0
- data/vendor/libgit2/src/buf_text.h +122 -0
- data/vendor/libgit2/src/buffer.c +27 -101
- data/vendor/libgit2/src/buffer.h +54 -39
- data/vendor/libgit2/src/cache.c +15 -6
- data/vendor/libgit2/src/cache.h +1 -1
- data/vendor/libgit2/src/cc-compat.h +3 -1
- data/vendor/libgit2/src/checkout.c +1165 -222
- data/vendor/libgit2/src/checkout.h +24 -0
- data/vendor/libgit2/src/clone.c +171 -86
- data/vendor/libgit2/src/commit.c +44 -45
- data/vendor/libgit2/src/commit.h +3 -3
- data/vendor/libgit2/src/commit_list.c +194 -0
- data/vendor/libgit2/src/commit_list.h +49 -0
- data/vendor/libgit2/src/common.h +44 -10
- data/vendor/libgit2/src/compress.c +1 -1
- data/vendor/libgit2/src/compress.h +1 -1
- data/vendor/libgit2/src/config.c +211 -124
- data/vendor/libgit2/src/config.h +23 -4
- data/vendor/libgit2/src/config_cache.c +2 -2
- data/vendor/libgit2/src/config_file.c +129 -53
- data/vendor/libgit2/src/config_file.h +10 -8
- data/vendor/libgit2/src/crlf.c +66 -67
- data/vendor/libgit2/src/date.c +12 -12
- data/vendor/libgit2/src/delta-apply.c +14 -1
- data/vendor/libgit2/src/delta-apply.h +18 -1
- data/vendor/libgit2/src/delta.c +40 -107
- data/vendor/libgit2/src/delta.h +19 -17
- data/vendor/libgit2/src/diff.c +347 -496
- data/vendor/libgit2/src/diff.h +27 -1
- data/vendor/libgit2/src/diff_output.c +564 -249
- data/vendor/libgit2/src/diff_output.h +15 -8
- data/vendor/libgit2/src/diff_tform.c +687 -0
- data/vendor/libgit2/src/errors.c +27 -36
- data/vendor/libgit2/src/fetch.c +13 -351
- data/vendor/libgit2/src/fetch.h +13 -3
- data/vendor/libgit2/src/fetchhead.c +295 -0
- data/vendor/libgit2/src/fetchhead.h +34 -0
- data/vendor/libgit2/src/filebuf.c +42 -15
- data/vendor/libgit2/src/filebuf.h +4 -2
- data/vendor/libgit2/src/fileops.c +466 -113
- data/vendor/libgit2/src/fileops.h +154 -28
- data/vendor/libgit2/src/filter.c +3 -75
- data/vendor/libgit2/src/filter.h +1 -29
- data/vendor/libgit2/src/fnmatch.c +1 -1
- data/vendor/libgit2/src/fnmatch.h +1 -1
- data/vendor/libgit2/src/global.c +54 -10
- data/vendor/libgit2/src/global.h +10 -1
- data/vendor/libgit2/src/graph.c +178 -0
- data/vendor/libgit2/src/hash.c +25 -52
- data/vendor/libgit2/src/hash.h +21 -9
- data/vendor/libgit2/src/{sha1/sha1.c → hash/hash_generic.c} +20 -12
- data/vendor/libgit2/src/hash/hash_generic.h +24 -0
- data/vendor/libgit2/src/hash/hash_openssl.h +45 -0
- data/vendor/libgit2/src/hash/hash_win32.c +291 -0
- data/vendor/libgit2/src/hash/hash_win32.h +140 -0
- data/vendor/libgit2/src/hashsig.c +368 -0
- data/vendor/libgit2/src/hashsig.h +72 -0
- data/vendor/libgit2/src/ignore.c +22 -15
- data/vendor/libgit2/src/ignore.h +6 -1
- data/vendor/libgit2/src/index.c +770 -171
- data/vendor/libgit2/src/index.h +13 -5
- data/vendor/libgit2/src/indexer.c +286 -431
- data/vendor/libgit2/src/iterator.c +854 -466
- data/vendor/libgit2/src/iterator.h +134 -109
- data/vendor/libgit2/src/map.h +1 -1
- data/vendor/libgit2/src/merge.c +296 -0
- data/vendor/libgit2/src/merge.h +22 -0
- data/vendor/libgit2/src/message.c +1 -1
- data/vendor/libgit2/src/message.h +1 -1
- data/vendor/libgit2/src/mwindow.c +35 -30
- data/vendor/libgit2/src/mwindow.h +2 -2
- data/vendor/libgit2/src/netops.c +162 -98
- data/vendor/libgit2/src/netops.h +50 -15
- data/vendor/libgit2/src/notes.c +109 -58
- data/vendor/libgit2/src/notes.h +2 -1
- data/vendor/libgit2/src/object.c +46 -57
- data/vendor/libgit2/src/object.h +1 -8
- data/vendor/libgit2/src/odb.c +151 -40
- data/vendor/libgit2/src/odb.h +5 -1
- data/vendor/libgit2/src/odb_loose.c +4 -5
- data/vendor/libgit2/src/odb_pack.c +122 -80
- data/vendor/libgit2/src/offmap.h +65 -0
- data/vendor/libgit2/src/oid.c +12 -4
- data/vendor/libgit2/src/oidmap.h +1 -1
- data/vendor/libgit2/src/pack-objects.c +88 -61
- data/vendor/libgit2/src/pack-objects.h +8 -8
- data/vendor/libgit2/src/pack.c +293 -28
- data/vendor/libgit2/src/pack.h +49 -4
- data/vendor/libgit2/src/path.c +103 -14
- data/vendor/libgit2/src/path.h +23 -7
- data/vendor/libgit2/src/pathspec.c +168 -0
- data/vendor/libgit2/src/pathspec.h +40 -0
- data/vendor/libgit2/src/pool.c +29 -4
- data/vendor/libgit2/src/pool.h +8 -1
- data/vendor/libgit2/src/posix.c +26 -27
- data/vendor/libgit2/src/posix.h +2 -3
- data/vendor/libgit2/src/pqueue.c +23 -1
- data/vendor/libgit2/src/pqueue.h +23 -1
- data/vendor/libgit2/src/push.c +653 -0
- data/vendor/libgit2/src/push.h +51 -0
- data/vendor/libgit2/src/refdb.c +185 -0
- data/vendor/libgit2/src/refdb.h +46 -0
- data/vendor/libgit2/src/refdb_fs.c +1024 -0
- data/vendor/libgit2/src/refdb_fs.h +15 -0
- data/vendor/libgit2/src/reflog.c +77 -45
- data/vendor/libgit2/src/reflog.h +1 -3
- data/vendor/libgit2/src/refs.c +366 -1326
- data/vendor/libgit2/src/refs.h +22 -13
- data/vendor/libgit2/src/refspec.c +46 -7
- data/vendor/libgit2/src/refspec.h +11 -1
- data/vendor/libgit2/src/remote.c +758 -120
- data/vendor/libgit2/src/remote.h +10 -5
- data/vendor/libgit2/src/repo_template.h +6 -6
- data/vendor/libgit2/src/repository.c +315 -96
- data/vendor/libgit2/src/repository.h +5 -3
- data/vendor/libgit2/src/reset.c +99 -81
- data/vendor/libgit2/src/revparse.c +157 -84
- data/vendor/libgit2/src/revwalk.c +68 -470
- data/vendor/libgit2/src/revwalk.h +44 -0
- data/vendor/libgit2/src/sha1_lookup.c +1 -1
- data/vendor/libgit2/src/sha1_lookup.h +1 -1
- data/vendor/libgit2/src/signature.c +68 -200
- data/vendor/libgit2/src/signature.h +1 -1
- data/vendor/libgit2/src/stash.c +663 -0
- data/vendor/libgit2/src/status.c +101 -79
- data/vendor/libgit2/src/strmap.h +1 -1
- data/vendor/libgit2/src/submodule.c +67 -51
- data/vendor/libgit2/src/submodule.h +1 -1
- data/vendor/libgit2/src/tag.c +35 -29
- data/vendor/libgit2/src/tag.h +1 -1
- data/vendor/libgit2/src/thread-utils.c +1 -1
- data/vendor/libgit2/src/thread-utils.h +2 -2
- data/vendor/libgit2/src/trace.c +39 -0
- data/vendor/libgit2/src/trace.h +56 -0
- data/vendor/libgit2/src/transport.c +81 -34
- data/vendor/libgit2/src/transports/cred.c +60 -0
- data/vendor/libgit2/src/transports/cred_helpers.c +49 -0
- data/vendor/libgit2/src/transports/git.c +234 -127
- data/vendor/libgit2/src/transports/http.c +761 -433
- data/vendor/libgit2/src/transports/local.c +460 -64
- data/vendor/libgit2/src/transports/smart.c +345 -0
- data/vendor/libgit2/src/transports/smart.h +179 -0
- data/vendor/libgit2/src/{pkt.c → transports/smart_pkt.c} +131 -12
- data/vendor/libgit2/src/transports/smart_protocol.c +856 -0
- data/vendor/libgit2/src/transports/winhttp.c +1136 -0
- data/vendor/libgit2/src/tree-cache.c +2 -2
- data/vendor/libgit2/src/tree-cache.h +1 -1
- data/vendor/libgit2/src/tree.c +239 -166
- data/vendor/libgit2/src/tree.h +11 -2
- data/vendor/libgit2/src/tsort.c +39 -23
- data/vendor/libgit2/src/unix/map.c +1 -1
- data/vendor/libgit2/src/unix/posix.h +12 -2
- data/vendor/libgit2/src/unix/realpath.c +30 -0
- data/vendor/libgit2/src/util.c +250 -13
- data/vendor/libgit2/src/util.h +71 -14
- data/vendor/libgit2/src/vector.c +123 -60
- data/vendor/libgit2/src/vector.h +24 -22
- data/vendor/libgit2/src/win32/dir.c +1 -1
- data/vendor/libgit2/src/win32/dir.h +1 -1
- data/vendor/libgit2/src/win32/error.c +77 -0
- data/vendor/libgit2/src/win32/error.h +13 -0
- data/vendor/libgit2/src/win32/findfile.c +143 -54
- data/vendor/libgit2/src/win32/findfile.h +10 -6
- data/vendor/libgit2/src/win32/map.c +1 -1
- data/vendor/libgit2/src/win32/mingw-compat.h +1 -1
- data/vendor/libgit2/src/win32/msvc-compat.h +10 -1
- data/vendor/libgit2/src/win32/posix.h +10 -1
- data/vendor/libgit2/src/win32/posix_w32.c +132 -63
- data/vendor/libgit2/src/win32/precompiled.c +1 -1
- data/vendor/libgit2/src/win32/pthread.c +1 -1
- data/vendor/libgit2/src/win32/pthread.h +1 -1
- data/vendor/libgit2/src/win32/utf-conv.c +5 -5
- data/vendor/libgit2/src/win32/utf-conv.h +3 -3
- data/vendor/libgit2/src/win32/version.h +20 -0
- metadata +308 -252
- data/test/fixtures/testrepo.git/objects/4b/825dc642cb6eb9a060e54bf8d69288fbee4904 +0 -0
- data/test/fixtures/testrepo.git/objects/7f/043268ea43ce18e3540acaabf9e090c91965b0 +0 -0
- data/test/fixtures/testrepo.git/objects/a3/e05719b428a2d0ed7a55c4ce53dcc5768c6d5e +0 -0
- data/test/index_test.rb~ +0 -218
- data/vendor/libgit2/src/pkt.h +0 -91
- data/vendor/libgit2/src/ppc/sha1.c +0 -70
- data/vendor/libgit2/src/ppc/sha1.h +0 -26
- data/vendor/libgit2/src/protocol.c +0 -110
- data/vendor/libgit2/src/protocol.h +0 -21
- data/vendor/libgit2/src/sha1.h +0 -33
- data/vendor/libgit2/src/transport.h +0 -148
data/vendor/libgit2/src/index.h
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/*
|
|
2
|
-
* Copyright (C)
|
|
2
|
+
* Copyright (C) the libgit2 contributors. All rights reserved.
|
|
3
3
|
*
|
|
4
4
|
* This file is part of libgit2, distributed under the GNU GPL v2 with
|
|
5
5
|
* a Linking Exception. For full terms see the included COPYING file.
|
|
@@ -22,7 +22,7 @@ struct git_index {
|
|
|
22
22
|
|
|
23
23
|
char *index_file_path;
|
|
24
24
|
|
|
25
|
-
|
|
25
|
+
git_futils_filestamp stamp;
|
|
26
26
|
git_vector entries;
|
|
27
27
|
|
|
28
28
|
unsigned int on_disk:1;
|
|
@@ -33,13 +33,21 @@ struct git_index {
|
|
|
33
33
|
|
|
34
34
|
git_tree_cache *tree;
|
|
35
35
|
|
|
36
|
-
git_vector
|
|
36
|
+
git_vector reuc;
|
|
37
37
|
|
|
38
|
+
git_vector_cmp entries_cmp_path;
|
|
38
39
|
git_vector_cmp entries_search;
|
|
40
|
+
git_vector_cmp entries_search_path;
|
|
41
|
+
git_vector_cmp reuc_search;
|
|
39
42
|
};
|
|
40
43
|
|
|
41
|
-
extern void
|
|
44
|
+
extern void git_index_entry__init_from_stat(git_index_entry *entry, struct stat *st);
|
|
42
45
|
|
|
43
|
-
extern
|
|
46
|
+
extern size_t git_index__prefix_position(git_index *index, const char *path);
|
|
47
|
+
|
|
48
|
+
extern int git_index_entry__cmp(const void *a, const void *b);
|
|
49
|
+
extern int git_index_entry__cmp_icase(const void *a, const void *b);
|
|
50
|
+
|
|
51
|
+
extern void git_index__set_ignore_case(git_index *index, bool ignore_case);
|
|
44
52
|
|
|
45
53
|
#endif
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/*
|
|
2
|
-
* Copyright (C)
|
|
2
|
+
* Copyright (C) the libgit2 contributors. All rights reserved.
|
|
3
3
|
*
|
|
4
4
|
* This file is part of libgit2, distributed under the GNU GPL v2 with
|
|
5
5
|
* a Linking Exception. For full terms see the included COPYING file.
|
|
@@ -17,7 +17,7 @@
|
|
|
17
17
|
#include "posix.h"
|
|
18
18
|
#include "pack.h"
|
|
19
19
|
#include "filebuf.h"
|
|
20
|
-
#include "
|
|
20
|
+
#include "oidmap.h"
|
|
21
21
|
|
|
22
22
|
#define UINT31_MAX (0x7FFFFFFF)
|
|
23
23
|
|
|
@@ -28,39 +28,32 @@ struct entry {
|
|
|
28
28
|
uint64_t offset_long;
|
|
29
29
|
};
|
|
30
30
|
|
|
31
|
-
struct git_indexer {
|
|
32
|
-
struct git_pack_file *pack;
|
|
33
|
-
size_t nr_objects;
|
|
34
|
-
git_vector objects;
|
|
35
|
-
git_filebuf file;
|
|
36
|
-
unsigned int fanout[256];
|
|
37
|
-
git_oid hash;
|
|
38
|
-
};
|
|
39
|
-
|
|
40
31
|
struct git_indexer_stream {
|
|
41
32
|
unsigned int parsed_header :1,
|
|
42
|
-
opened_pack
|
|
33
|
+
opened_pack :1,
|
|
34
|
+
have_stream :1,
|
|
35
|
+
have_delta :1;
|
|
43
36
|
struct git_pack_file *pack;
|
|
44
37
|
git_filebuf pack_file;
|
|
45
|
-
git_filebuf index_file;
|
|
46
38
|
git_off_t off;
|
|
39
|
+
git_off_t entry_start;
|
|
40
|
+
git_packfile_stream stream;
|
|
47
41
|
size_t nr_objects;
|
|
48
42
|
git_vector objects;
|
|
49
43
|
git_vector deltas;
|
|
50
44
|
unsigned int fanout[256];
|
|
45
|
+
git_hash_ctx hash_ctx;
|
|
51
46
|
git_oid hash;
|
|
47
|
+
git_transfer_progress_callback progress_cb;
|
|
48
|
+
void *progress_payload;
|
|
49
|
+
char objbuf[8*1024];
|
|
52
50
|
};
|
|
53
51
|
|
|
54
52
|
struct delta_info {
|
|
55
53
|
git_off_t delta_off;
|
|
56
54
|
};
|
|
57
55
|
|
|
58
|
-
const git_oid *
|
|
59
|
-
{
|
|
60
|
-
return &idx->hash;
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
const git_oid *git_indexer_stream_hash(git_indexer_stream *idx)
|
|
56
|
+
const git_oid *git_indexer_stream_hash(const git_indexer_stream *idx)
|
|
64
57
|
{
|
|
65
58
|
return &idx->hash;
|
|
66
59
|
}
|
|
@@ -130,15 +123,11 @@ static int objects_cmp(const void *a, const void *b)
|
|
|
130
123
|
return git_oid_cmp(&entrya->oid, &entryb->oid);
|
|
131
124
|
}
|
|
132
125
|
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
return git_oid_cmp(&ea->sha1, &eb->sha1);
|
|
139
|
-
}
|
|
140
|
-
|
|
141
|
-
int git_indexer_stream_new(git_indexer_stream **out, const char *prefix)
|
|
126
|
+
int git_indexer_stream_new(
|
|
127
|
+
git_indexer_stream **out,
|
|
128
|
+
const char *prefix,
|
|
129
|
+
git_transfer_progress_callback progress_cb,
|
|
130
|
+
void *progress_payload)
|
|
142
131
|
{
|
|
143
132
|
git_indexer_stream *idx;
|
|
144
133
|
git_buf path = GIT_BUF_INIT;
|
|
@@ -147,6 +136,8 @@ int git_indexer_stream_new(git_indexer_stream **out, const char *prefix)
|
|
|
147
136
|
|
|
148
137
|
idx = git__calloc(1, sizeof(git_indexer_stream));
|
|
149
138
|
GITERR_CHECK_ALLOC(idx);
|
|
139
|
+
idx->progress_cb = progress_cb;
|
|
140
|
+
idx->progress_payload = progress_payload;
|
|
150
141
|
|
|
151
142
|
error = git_buf_joinpath(&path, prefix, suff);
|
|
152
143
|
if (error < 0)
|
|
@@ -169,56 +160,173 @@ cleanup:
|
|
|
169
160
|
}
|
|
170
161
|
|
|
171
162
|
/* Try to store the delta so we can try to resolve it later */
|
|
172
|
-
static int store_delta(git_indexer_stream *idx
|
|
163
|
+
static int store_delta(git_indexer_stream *idx)
|
|
173
164
|
{
|
|
174
|
-
git_mwindow *w = NULL;
|
|
175
165
|
struct delta_info *delta;
|
|
176
|
-
|
|
177
|
-
|
|
166
|
+
|
|
167
|
+
delta = git__calloc(1, sizeof(struct delta_info));
|
|
168
|
+
GITERR_CHECK_ALLOC(delta);
|
|
169
|
+
delta->delta_off = idx->entry_start;
|
|
170
|
+
|
|
171
|
+
if (git_vector_insert(&idx->deltas, delta) < 0)
|
|
172
|
+
return -1;
|
|
173
|
+
|
|
174
|
+
return 0;
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
static void hash_header(git_hash_ctx *ctx, git_off_t len, git_otype type)
|
|
178
|
+
{
|
|
179
|
+
char buffer[64];
|
|
180
|
+
size_t hdrlen;
|
|
181
|
+
|
|
182
|
+
hdrlen = git_odb__format_object_header(buffer, sizeof(buffer), (size_t)len, type);
|
|
183
|
+
git_hash_update(ctx, buffer, hdrlen);
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
static int hash_object_stream(git_indexer_stream *idx, git_packfile_stream *stream)
|
|
187
|
+
{
|
|
188
|
+
ssize_t read;
|
|
189
|
+
|
|
190
|
+
assert(idx && stream);
|
|
191
|
+
|
|
192
|
+
do {
|
|
193
|
+
if ((read = git_packfile_stream_read(stream, idx->objbuf, sizeof(idx->objbuf))) < 0)
|
|
194
|
+
break;
|
|
195
|
+
|
|
196
|
+
git_hash_update(&idx->hash_ctx, idx->objbuf, read);
|
|
197
|
+
} while (read > 0);
|
|
198
|
+
|
|
199
|
+
if (read < 0)
|
|
200
|
+
return (int)read;
|
|
201
|
+
|
|
202
|
+
return 0;
|
|
203
|
+
}
|
|
204
|
+
|
|
205
|
+
/* In order to create the packfile stream, we need to skip over the delta base description */
|
|
206
|
+
static int advance_delta_offset(git_indexer_stream *idx, git_otype type)
|
|
207
|
+
{
|
|
208
|
+
git_mwindow *w = NULL;
|
|
178
209
|
|
|
179
210
|
assert(type == GIT_OBJ_REF_DELTA || type == GIT_OBJ_OFS_DELTA);
|
|
180
211
|
|
|
181
212
|
if (type == GIT_OBJ_REF_DELTA) {
|
|
182
213
|
idx->off += GIT_OID_RAWSZ;
|
|
183
214
|
} else {
|
|
184
|
-
git_off_t base_off;
|
|
185
|
-
|
|
186
|
-
base_off = get_delta_base(idx->pack, &w, &idx->off, type, entry_start);
|
|
215
|
+
git_off_t base_off = get_delta_base(idx->pack, &w, &idx->off, type, idx->entry_start);
|
|
187
216
|
git_mwindow_close(&w);
|
|
188
217
|
if (base_off < 0)
|
|
189
218
|
return (int)base_off;
|
|
190
219
|
}
|
|
191
220
|
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
221
|
+
return 0;
|
|
222
|
+
}
|
|
223
|
+
|
|
224
|
+
/* Read from the stream and discard any output */
|
|
225
|
+
static int read_object_stream(git_indexer_stream *idx, git_packfile_stream *stream)
|
|
226
|
+
{
|
|
227
|
+
ssize_t read;
|
|
228
|
+
|
|
229
|
+
assert(stream);
|
|
230
|
+
|
|
231
|
+
do {
|
|
232
|
+
read = git_packfile_stream_read(stream, idx->objbuf, sizeof(idx->objbuf));
|
|
233
|
+
} while (read > 0);
|
|
234
|
+
|
|
235
|
+
if (read < 0)
|
|
236
|
+
return (int)read;
|
|
237
|
+
|
|
238
|
+
return 0;
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
static int crc_object(uint32_t *crc_out, git_mwindow_file *mwf, git_off_t start, git_off_t size)
|
|
242
|
+
{
|
|
243
|
+
void *ptr;
|
|
244
|
+
uint32_t crc;
|
|
245
|
+
unsigned int left, len;
|
|
246
|
+
git_mwindow *w = NULL;
|
|
247
|
+
|
|
248
|
+
crc = crc32(0L, Z_NULL, 0);
|
|
249
|
+
while (size) {
|
|
250
|
+
ptr = git_mwindow_open(mwf, &w, start, (size_t)size, &left);
|
|
251
|
+
if (ptr == NULL)
|
|
252
|
+
return -1;
|
|
253
|
+
|
|
254
|
+
len = min(left, (unsigned int)size);
|
|
255
|
+
crc = crc32(crc, ptr, len);
|
|
256
|
+
size -= len;
|
|
257
|
+
start += len;
|
|
258
|
+
git_mwindow_close(&w);
|
|
198
259
|
}
|
|
199
260
|
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
261
|
+
*crc_out = htonl(crc);
|
|
262
|
+
return 0;
|
|
263
|
+
}
|
|
264
|
+
|
|
265
|
+
static int store_object(git_indexer_stream *idx)
|
|
266
|
+
{
|
|
267
|
+
int i, error;
|
|
268
|
+
khiter_t k;
|
|
269
|
+
git_oid oid;
|
|
270
|
+
struct entry *entry;
|
|
271
|
+
git_off_t entry_size;
|
|
272
|
+
struct git_pack_entry *pentry;
|
|
273
|
+
git_hash_ctx *ctx = &idx->hash_ctx;
|
|
274
|
+
git_off_t entry_start = idx->entry_start;
|
|
203
275
|
|
|
204
|
-
|
|
276
|
+
entry = git__calloc(1, sizeof(*entry));
|
|
277
|
+
GITERR_CHECK_ALLOC(entry);
|
|
205
278
|
|
|
206
|
-
|
|
207
|
-
|
|
279
|
+
pentry = git__malloc(sizeof(struct git_pack_entry));
|
|
280
|
+
GITERR_CHECK_ALLOC(pentry);
|
|
281
|
+
|
|
282
|
+
git_hash_final(&oid, ctx);
|
|
283
|
+
entry_size = idx->off - entry_start;
|
|
284
|
+
if (entry_start > UINT31_MAX) {
|
|
285
|
+
entry->offset = UINT32_MAX;
|
|
286
|
+
entry->offset_long = entry_start;
|
|
287
|
+
} else {
|
|
288
|
+
entry->offset = (uint32_t)entry_start;
|
|
289
|
+
}
|
|
290
|
+
|
|
291
|
+
git_oid_cpy(&pentry->sha1, &oid);
|
|
292
|
+
pentry->offset = entry_start;
|
|
293
|
+
|
|
294
|
+
k = kh_put(oid, idx->pack->idx_cache, &pentry->sha1, &error);
|
|
295
|
+
if (!error) {
|
|
296
|
+
git__free(pentry);
|
|
297
|
+
goto on_error;
|
|
298
|
+
}
|
|
299
|
+
|
|
300
|
+
kh_value(idx->pack->idx_cache, k) = pentry;
|
|
301
|
+
|
|
302
|
+
git_oid_cpy(&entry->oid, &oid);
|
|
303
|
+
|
|
304
|
+
if (crc_object(&entry->crc, &idx->pack->mwf, entry_start, entry_size) < 0)
|
|
305
|
+
goto on_error;
|
|
306
|
+
|
|
307
|
+
/* Add the object to the list */
|
|
308
|
+
if (git_vector_insert(&idx->objects, entry) < 0)
|
|
309
|
+
goto on_error;
|
|
310
|
+
|
|
311
|
+
for (i = oid.id[0]; i < 256; ++i) {
|
|
312
|
+
idx->fanout[i]++;
|
|
313
|
+
}
|
|
208
314
|
|
|
209
315
|
return 0;
|
|
316
|
+
|
|
317
|
+
on_error:
|
|
318
|
+
git__free(entry);
|
|
319
|
+
|
|
320
|
+
return -1;
|
|
210
321
|
}
|
|
211
322
|
|
|
212
323
|
static int hash_and_save(git_indexer_stream *idx, git_rawobj *obj, git_off_t entry_start)
|
|
213
324
|
{
|
|
214
|
-
int i;
|
|
325
|
+
int i, error;
|
|
326
|
+
khiter_t k;
|
|
215
327
|
git_oid oid;
|
|
216
|
-
void *packed;
|
|
217
328
|
size_t entry_size;
|
|
218
|
-
unsigned int left;
|
|
219
329
|
struct entry *entry;
|
|
220
|
-
git_mwindow *w = NULL;
|
|
221
|
-
git_mwindow_file *mwf = &idx->pack->mwf;
|
|
222
330
|
struct git_pack_entry *pentry;
|
|
223
331
|
|
|
224
332
|
entry = git__calloc(1, sizeof(*entry));
|
|
@@ -242,20 +350,21 @@ static int hash_and_save(git_indexer_stream *idx, git_rawobj *obj, git_off_t ent
|
|
|
242
350
|
|
|
243
351
|
git_oid_cpy(&pentry->sha1, &oid);
|
|
244
352
|
pentry->offset = entry_start;
|
|
245
|
-
|
|
353
|
+
k = kh_put(oid, idx->pack->idx_cache, &pentry->sha1, &error);
|
|
354
|
+
if (!error) {
|
|
355
|
+
git__free(pentry);
|
|
246
356
|
goto on_error;
|
|
357
|
+
}
|
|
358
|
+
|
|
359
|
+
kh_value(idx->pack->idx_cache, k) = pentry;
|
|
247
360
|
|
|
248
361
|
git_oid_cpy(&entry->oid, &oid);
|
|
249
362
|
entry->crc = crc32(0L, Z_NULL, 0);
|
|
250
363
|
|
|
251
364
|
entry_size = (size_t)(idx->off - entry_start);
|
|
252
|
-
|
|
253
|
-
if (packed == NULL)
|
|
365
|
+
if (crc_object(&entry->crc, &idx->pack->mwf, entry_start, entry_size) < 0)
|
|
254
366
|
goto on_error;
|
|
255
367
|
|
|
256
|
-
entry->crc = htonl(crc32(entry->crc, packed, (uInt)entry_size));
|
|
257
|
-
git_mwindow_close(&w);
|
|
258
|
-
|
|
259
368
|
/* Add the object to the list */
|
|
260
369
|
if (git_vector_insert(&idx->objects, entry) < 0)
|
|
261
370
|
goto on_error;
|
|
@@ -268,21 +377,26 @@ static int hash_and_save(git_indexer_stream *idx, git_rawobj *obj, git_off_t ent
|
|
|
268
377
|
|
|
269
378
|
on_error:
|
|
270
379
|
git__free(entry);
|
|
271
|
-
git__free(pentry);
|
|
272
380
|
git__free(obj->data);
|
|
273
381
|
return -1;
|
|
274
382
|
}
|
|
275
383
|
|
|
276
|
-
int
|
|
384
|
+
static int do_progress_callback(git_indexer_stream *idx, git_transfer_progress *stats)
|
|
277
385
|
{
|
|
278
|
-
|
|
386
|
+
if (!idx->progress_cb) return 0;
|
|
387
|
+
return idx->progress_cb(stats, idx->progress_payload);
|
|
388
|
+
}
|
|
389
|
+
|
|
390
|
+
int git_indexer_stream_add(git_indexer_stream *idx, const void *data, size_t size, git_transfer_progress *stats)
|
|
391
|
+
{
|
|
392
|
+
int error = -1;
|
|
279
393
|
struct git_pack_header hdr;
|
|
280
394
|
size_t processed;
|
|
281
395
|
git_mwindow_file *mwf = &idx->pack->mwf;
|
|
282
396
|
|
|
283
397
|
assert(idx && data && stats);
|
|
284
398
|
|
|
285
|
-
processed = stats->
|
|
399
|
+
processed = stats->indexed_objects;
|
|
286
400
|
|
|
287
401
|
if (git_filebuf_write(&idx->pack_file, data, size) < 0)
|
|
288
402
|
return -1;
|
|
@@ -301,6 +415,8 @@ int git_indexer_stream_add(git_indexer_stream *idx, const void *data, size_t siz
|
|
|
301
415
|
}
|
|
302
416
|
|
|
303
417
|
if (!idx->parsed_header) {
|
|
418
|
+
unsigned int total_objects;
|
|
419
|
+
|
|
304
420
|
if ((unsigned)idx->pack->mwf.size < sizeof(hdr))
|
|
305
421
|
return 0;
|
|
306
422
|
|
|
@@ -313,19 +429,25 @@ int git_indexer_stream_add(git_indexer_stream *idx, const void *data, size_t siz
|
|
|
313
429
|
|
|
314
430
|
/* for now, limit to 2^32 objects */
|
|
315
431
|
assert(idx->nr_objects == (size_t)((unsigned int)idx->nr_objects));
|
|
432
|
+
if (idx->nr_objects == (size_t)((unsigned int)idx->nr_objects))
|
|
433
|
+
total_objects = (unsigned int)idx->nr_objects;
|
|
434
|
+
else
|
|
435
|
+
total_objects = UINT_MAX;
|
|
316
436
|
|
|
317
|
-
|
|
318
|
-
|
|
437
|
+
idx->pack->idx_cache = git_oidmap_alloc();
|
|
438
|
+
GITERR_CHECK_ALLOC(idx->pack->idx_cache);
|
|
319
439
|
|
|
320
440
|
idx->pack->has_cache = 1;
|
|
321
|
-
if (git_vector_init(&idx->objects,
|
|
441
|
+
if (git_vector_init(&idx->objects, total_objects, objects_cmp) < 0)
|
|
322
442
|
return -1;
|
|
323
443
|
|
|
324
|
-
if (git_vector_init(&idx->deltas,
|
|
444
|
+
if (git_vector_init(&idx->deltas, total_objects / 2, NULL) < 0)
|
|
325
445
|
return -1;
|
|
326
446
|
|
|
327
|
-
|
|
328
|
-
stats->
|
|
447
|
+
stats->received_objects = 0;
|
|
448
|
+
processed = stats->indexed_objects = 0;
|
|
449
|
+
stats->total_objects = total_objects;
|
|
450
|
+
do_progress_callback(idx, stats);
|
|
329
451
|
}
|
|
330
452
|
|
|
331
453
|
/* Now that we have data in the pack, let's try to parse it */
|
|
@@ -333,7 +455,7 @@ int git_indexer_stream_add(git_indexer_stream *idx, const void *data, size_t siz
|
|
|
333
455
|
/* As the file grows any windows we try to use will be out of date */
|
|
334
456
|
git_mwindow_free_all(mwf);
|
|
335
457
|
while (processed < idx->nr_objects) {
|
|
336
|
-
|
|
458
|
+
git_packfile_stream *stream = &idx->stream;
|
|
337
459
|
git_off_t entry_start = idx->off;
|
|
338
460
|
size_t entry_size;
|
|
339
461
|
git_otype type;
|
|
@@ -342,52 +464,82 @@ int git_indexer_stream_add(git_indexer_stream *idx, const void *data, size_t siz
|
|
|
342
464
|
if (idx->pack->mwf.size <= idx->off + 20)
|
|
343
465
|
return 0;
|
|
344
466
|
|
|
345
|
-
|
|
346
|
-
|
|
347
|
-
idx->off = entry_start;
|
|
348
|
-
return 0;
|
|
349
|
-
}
|
|
350
|
-
if (error < 0)
|
|
351
|
-
return -1;
|
|
352
|
-
|
|
353
|
-
git_mwindow_close(&w);
|
|
354
|
-
|
|
355
|
-
if (type == GIT_OBJ_REF_DELTA || type == GIT_OBJ_OFS_DELTA) {
|
|
356
|
-
error = store_delta(idx, entry_start, entry_size, type);
|
|
467
|
+
if (!idx->have_stream) {
|
|
468
|
+
error = git_packfile_unpack_header(&entry_size, &type, mwf, &w, &idx->off);
|
|
357
469
|
if (error == GIT_EBUFS) {
|
|
358
470
|
idx->off = entry_start;
|
|
359
471
|
return 0;
|
|
360
472
|
}
|
|
361
473
|
if (error < 0)
|
|
362
|
-
return
|
|
474
|
+
return -1;
|
|
475
|
+
|
|
476
|
+
git_mwindow_close(&w);
|
|
477
|
+
idx->entry_start = entry_start;
|
|
478
|
+
git_hash_ctx_init(&idx->hash_ctx);
|
|
479
|
+
|
|
480
|
+
if (type == GIT_OBJ_REF_DELTA || type == GIT_OBJ_OFS_DELTA) {
|
|
481
|
+
error = advance_delta_offset(idx, type);
|
|
482
|
+
if (error == GIT_EBUFS) {
|
|
483
|
+
idx->off = entry_start;
|
|
484
|
+
return 0;
|
|
485
|
+
}
|
|
486
|
+
if (error < 0)
|
|
487
|
+
return -1;
|
|
488
|
+
|
|
489
|
+
idx->have_delta = 1;
|
|
490
|
+
} else {
|
|
491
|
+
idx->have_delta = 0;
|
|
492
|
+
hash_header(&idx->hash_ctx, entry_size, type);
|
|
493
|
+
}
|
|
494
|
+
|
|
495
|
+
idx->have_stream = 1;
|
|
496
|
+
if (git_packfile_stream_open(stream, idx->pack, idx->off) < 0)
|
|
497
|
+
goto on_error;
|
|
363
498
|
|
|
364
|
-
stats->received++;
|
|
365
|
-
continue;
|
|
366
499
|
}
|
|
367
500
|
|
|
368
|
-
idx->
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
372
|
-
return 0;
|
|
501
|
+
if (idx->have_delta) {
|
|
502
|
+
error = read_object_stream(idx, stream);
|
|
503
|
+
} else {
|
|
504
|
+
error = hash_object_stream(idx, stream);
|
|
373
505
|
}
|
|
506
|
+
|
|
507
|
+
idx->off = stream->curpos;
|
|
508
|
+
if (error == GIT_EBUFS)
|
|
509
|
+
return 0;
|
|
510
|
+
|
|
511
|
+
/* We want to free the stream reasorces no matter what here */
|
|
512
|
+
idx->have_stream = 0;
|
|
513
|
+
git_packfile_stream_free(stream);
|
|
514
|
+
|
|
374
515
|
if (error < 0)
|
|
375
|
-
|
|
516
|
+
goto on_error;
|
|
517
|
+
|
|
518
|
+
if (idx->have_delta) {
|
|
519
|
+
error = store_delta(idx);
|
|
520
|
+
} else {
|
|
521
|
+
error = store_object(idx);
|
|
522
|
+
}
|
|
376
523
|
|
|
377
|
-
if (
|
|
524
|
+
if (error < 0)
|
|
378
525
|
goto on_error;
|
|
379
526
|
|
|
380
|
-
|
|
527
|
+
if (!idx->have_delta) {
|
|
528
|
+
stats->indexed_objects = (unsigned int)++processed;
|
|
529
|
+
}
|
|
530
|
+
stats->received_objects++;
|
|
381
531
|
|
|
382
|
-
stats
|
|
383
|
-
|
|
532
|
+
if (do_progress_callback(idx, stats) != 0) {
|
|
533
|
+
error = GIT_EUSER;
|
|
534
|
+
goto on_error;
|
|
535
|
+
}
|
|
384
536
|
}
|
|
385
537
|
|
|
386
538
|
return 0;
|
|
387
539
|
|
|
388
540
|
on_error:
|
|
389
541
|
git_mwindow_free_all(mwf);
|
|
390
|
-
return
|
|
542
|
+
return error;
|
|
391
543
|
}
|
|
392
544
|
|
|
393
545
|
static int index_path_stream(git_buf *path, git_indexer_stream *idx, const char *suffix)
|
|
@@ -412,7 +564,7 @@ static int index_path_stream(git_buf *path, git_indexer_stream *idx, const char
|
|
|
412
564
|
return git_buf_oom(path) ? -1 : 0;
|
|
413
565
|
}
|
|
414
566
|
|
|
415
|
-
static int resolve_deltas(git_indexer_stream *idx,
|
|
567
|
+
static int resolve_deltas(git_indexer_stream *idx, git_transfer_progress *stats)
|
|
416
568
|
{
|
|
417
569
|
unsigned int i;
|
|
418
570
|
struct delta_info *delta;
|
|
@@ -428,13 +580,14 @@ static int resolve_deltas(git_indexer_stream *idx, git_indexer_stats *stats)
|
|
|
428
580
|
return -1;
|
|
429
581
|
|
|
430
582
|
git__free(obj.data);
|
|
431
|
-
stats->
|
|
583
|
+
stats->indexed_objects++;
|
|
584
|
+
do_progress_callback(idx, stats);
|
|
432
585
|
}
|
|
433
586
|
|
|
434
587
|
return 0;
|
|
435
588
|
}
|
|
436
589
|
|
|
437
|
-
int git_indexer_stream_finalize(git_indexer_stream *idx,
|
|
590
|
+
int git_indexer_stream_finalize(git_indexer_stream *idx, git_transfer_progress *stats)
|
|
438
591
|
{
|
|
439
592
|
git_mwindow *w = NULL;
|
|
440
593
|
unsigned int i, long_offsets = 0, left;
|
|
@@ -443,11 +596,15 @@ int git_indexer_stream_finalize(git_indexer_stream *idx, git_indexer_stats *stat
|
|
|
443
596
|
struct entry *entry;
|
|
444
597
|
void *packfile_hash;
|
|
445
598
|
git_oid file_hash;
|
|
446
|
-
|
|
599
|
+
git_hash_ctx ctx;
|
|
600
|
+
git_filebuf index_file = {0};
|
|
601
|
+
|
|
602
|
+
if (git_hash_ctx_init(&ctx) < 0)
|
|
603
|
+
return -1;
|
|
447
604
|
|
|
448
605
|
/* Test for this before resolve_deltas(), as it plays with idx->off */
|
|
449
606
|
if (idx->off < idx->pack->mwf.size - GIT_OID_RAWSZ) {
|
|
450
|
-
giterr_set(GITERR_INDEXER, "Indexing error:
|
|
607
|
+
giterr_set(GITERR_INDEXER, "Indexing error: unexpected data at the end of the pack");
|
|
451
608
|
return -1;
|
|
452
609
|
}
|
|
453
610
|
|
|
@@ -455,7 +612,7 @@ int git_indexer_stream_finalize(git_indexer_stream *idx, git_indexer_stats *stat
|
|
|
455
612
|
if (resolve_deltas(idx, stats) < 0)
|
|
456
613
|
return -1;
|
|
457
614
|
|
|
458
|
-
if (stats->
|
|
615
|
+
if (stats->indexed_objects != stats->total_objects) {
|
|
459
616
|
giterr_set(GITERR_INDEXER, "Indexing error: early EOF");
|
|
460
617
|
return -1;
|
|
461
618
|
}
|
|
@@ -468,31 +625,30 @@ int git_indexer_stream_finalize(git_indexer_stream *idx, git_indexer_stats *stat
|
|
|
468
625
|
if (git_buf_oom(&filename))
|
|
469
626
|
return -1;
|
|
470
627
|
|
|
471
|
-
if (git_filebuf_open(&
|
|
628
|
+
if (git_filebuf_open(&index_file, filename.ptr, GIT_FILEBUF_HASH_CONTENTS) < 0)
|
|
472
629
|
goto on_error;
|
|
473
630
|
|
|
474
631
|
/* Write out the header */
|
|
475
632
|
hdr.idx_signature = htonl(PACK_IDX_SIGNATURE);
|
|
476
633
|
hdr.idx_version = htonl(2);
|
|
477
|
-
git_filebuf_write(&
|
|
634
|
+
git_filebuf_write(&index_file, &hdr, sizeof(hdr));
|
|
478
635
|
|
|
479
636
|
/* Write out the fanout table */
|
|
480
637
|
for (i = 0; i < 256; ++i) {
|
|
481
638
|
uint32_t n = htonl(idx->fanout[i]);
|
|
482
|
-
git_filebuf_write(&
|
|
639
|
+
git_filebuf_write(&index_file, &n, sizeof(n));
|
|
483
640
|
}
|
|
484
641
|
|
|
485
642
|
/* Write out the object names (SHA-1 hashes) */
|
|
486
|
-
SHA1_Init(&ctx);
|
|
487
643
|
git_vector_foreach(&idx->objects, i, entry) {
|
|
488
|
-
git_filebuf_write(&
|
|
489
|
-
|
|
644
|
+
git_filebuf_write(&index_file, &entry->oid, sizeof(git_oid));
|
|
645
|
+
git_hash_update(&ctx, &entry->oid, GIT_OID_RAWSZ);
|
|
490
646
|
}
|
|
491
|
-
|
|
647
|
+
git_hash_final(&idx->hash, &ctx);
|
|
492
648
|
|
|
493
649
|
/* Write out the CRC32 values */
|
|
494
650
|
git_vector_foreach(&idx->objects, i, entry) {
|
|
495
|
-
git_filebuf_write(&
|
|
651
|
+
git_filebuf_write(&index_file, &entry->crc, sizeof(uint32_t));
|
|
496
652
|
}
|
|
497
653
|
|
|
498
654
|
/* Write out the offsets */
|
|
@@ -504,7 +660,7 @@ int git_indexer_stream_finalize(git_indexer_stream *idx, git_indexer_stats *stat
|
|
|
504
660
|
else
|
|
505
661
|
n = htonl(entry->offset);
|
|
506
662
|
|
|
507
|
-
git_filebuf_write(&
|
|
663
|
+
git_filebuf_write(&index_file, &n, sizeof(uint32_t));
|
|
508
664
|
}
|
|
509
665
|
|
|
510
666
|
/* Write out the long offsets */
|
|
@@ -517,7 +673,7 @@ int git_indexer_stream_finalize(git_indexer_stream *idx, git_indexer_stats *stat
|
|
|
517
673
|
split[0] = htonl(entry->offset_long >> 32);
|
|
518
674
|
split[1] = htonl(entry->offset_long & 0xffffffff);
|
|
519
675
|
|
|
520
|
-
git_filebuf_write(&
|
|
676
|
+
git_filebuf_write(&index_file, &split, sizeof(uint32_t) * 2);
|
|
521
677
|
}
|
|
522
678
|
|
|
523
679
|
/* Write out the packfile trailer */
|
|
@@ -530,24 +686,26 @@ int git_indexer_stream_finalize(git_indexer_stream *idx, git_indexer_stats *stat
|
|
|
530
686
|
memcpy(&file_hash, packfile_hash, GIT_OID_RAWSZ);
|
|
531
687
|
git_mwindow_close(&w);
|
|
532
688
|
|
|
533
|
-
git_filebuf_write(&
|
|
689
|
+
git_filebuf_write(&index_file, &file_hash, sizeof(git_oid));
|
|
534
690
|
|
|
535
691
|
/* Write out the packfile trailer to the idx file as well */
|
|
536
|
-
if (git_filebuf_hash(&file_hash, &
|
|
692
|
+
if (git_filebuf_hash(&file_hash, &index_file) < 0)
|
|
537
693
|
goto on_error;
|
|
538
694
|
|
|
539
|
-
git_filebuf_write(&
|
|
695
|
+
git_filebuf_write(&index_file, &file_hash, sizeof(git_oid));
|
|
540
696
|
|
|
541
697
|
/* Figure out what the final name should be */
|
|
542
698
|
if (index_path_stream(&filename, idx, ".idx") < 0)
|
|
543
699
|
goto on_error;
|
|
544
700
|
|
|
545
701
|
/* Commit file */
|
|
546
|
-
if (git_filebuf_commit_at(&
|
|
702
|
+
if (git_filebuf_commit_at(&index_file, filename.ptr, GIT_PACK_FILE_MODE) < 0)
|
|
547
703
|
goto on_error;
|
|
548
704
|
|
|
549
705
|
git_mwindow_free_all(&idx->pack->mwf);
|
|
706
|
+
/* We need to close the descriptor here so Windows doesn't choke on commit_at */
|
|
550
707
|
p_close(idx->pack->mwf.fd);
|
|
708
|
+
idx->pack->mwf.fd = -1;
|
|
551
709
|
|
|
552
710
|
if (index_path_stream(&filename, idx, ".pack") < 0)
|
|
553
711
|
goto on_error;
|
|
@@ -560,17 +718,17 @@ int git_indexer_stream_finalize(git_indexer_stream *idx, git_indexer_stats *stat
|
|
|
560
718
|
|
|
561
719
|
on_error:
|
|
562
720
|
git_mwindow_free_all(&idx->pack->mwf);
|
|
563
|
-
|
|
564
|
-
git_filebuf_cleanup(&idx->index_file);
|
|
721
|
+
git_filebuf_cleanup(&index_file);
|
|
565
722
|
git_buf_free(&filename);
|
|
723
|
+
git_hash_ctx_cleanup(&ctx);
|
|
566
724
|
return -1;
|
|
567
725
|
}
|
|
568
726
|
|
|
569
727
|
void git_indexer_stream_free(git_indexer_stream *idx)
|
|
570
728
|
{
|
|
729
|
+
khiter_t k;
|
|
571
730
|
unsigned int i;
|
|
572
731
|
struct entry *e;
|
|
573
|
-
struct git_pack_entry *pe;
|
|
574
732
|
struct delta_info *delta;
|
|
575
733
|
|
|
576
734
|
if (idx == NULL)
|
|
@@ -579,323 +737,20 @@ void git_indexer_stream_free(git_indexer_stream *idx)
|
|
|
579
737
|
git_vector_foreach(&idx->objects, i, e)
|
|
580
738
|
git__free(e);
|
|
581
739
|
git_vector_free(&idx->objects);
|
|
582
|
-
if (idx->pack) {
|
|
583
|
-
git_vector_foreach(&idx->pack->cache, i, pe)
|
|
584
|
-
git__free(pe);
|
|
585
|
-
git_vector_free(&idx->pack->cache);
|
|
586
|
-
}
|
|
587
|
-
git_vector_foreach(&idx->deltas, i, delta)
|
|
588
|
-
git__free(delta);
|
|
589
|
-
git_vector_free(&idx->deltas);
|
|
590
|
-
git__free(idx->pack);
|
|
591
|
-
git__free(idx);
|
|
592
|
-
}
|
|
593
|
-
|
|
594
|
-
int git_indexer_new(git_indexer **out, const char *packname)
|
|
595
|
-
{
|
|
596
|
-
git_indexer *idx;
|
|
597
|
-
struct git_pack_header hdr;
|
|
598
|
-
int error;
|
|
599
|
-
|
|
600
|
-
assert(out && packname);
|
|
601
|
-
|
|
602
|
-
idx = git__calloc(1, sizeof(git_indexer));
|
|
603
|
-
GITERR_CHECK_ALLOC(idx);
|
|
604
|
-
|
|
605
|
-
open_pack(&idx->pack, packname);
|
|
606
|
-
|
|
607
|
-
if ((error = parse_header(&hdr, idx->pack)) < 0)
|
|
608
|
-
goto cleanup;
|
|
609
|
-
|
|
610
|
-
idx->nr_objects = ntohl(hdr.hdr_entries);
|
|
611
|
-
|
|
612
|
-
/* for now, limit to 2^32 objects */
|
|
613
|
-
assert(idx->nr_objects == (size_t)((unsigned int)idx->nr_objects));
|
|
614
|
-
|
|
615
|
-
error = git_vector_init(&idx->pack->cache, (unsigned int)idx->nr_objects, cache_cmp);
|
|
616
|
-
if (error < 0)
|
|
617
|
-
goto cleanup;
|
|
618
|
-
|
|
619
|
-
idx->pack->has_cache = 1;
|
|
620
|
-
error = git_vector_init(&idx->objects, (unsigned int)idx->nr_objects, objects_cmp);
|
|
621
|
-
if (error < 0)
|
|
622
|
-
goto cleanup;
|
|
623
|
-
|
|
624
|
-
*out = idx;
|
|
625
|
-
|
|
626
|
-
return 0;
|
|
627
|
-
|
|
628
|
-
cleanup:
|
|
629
|
-
git_indexer_free(idx);
|
|
630
740
|
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
{
|
|
636
|
-
const char prefix[] = "pack-", suffix[] = ".idx";
|
|
637
|
-
size_t slash = (size_t)path->size;
|
|
638
|
-
|
|
639
|
-
/* search backwards for '/' */
|
|
640
|
-
while (slash > 0 && path->ptr[slash - 1] != '/')
|
|
641
|
-
slash--;
|
|
642
|
-
|
|
643
|
-
if (git_buf_grow(path, slash + 1 + strlen(prefix) +
|
|
644
|
-
GIT_OID_HEXSZ + strlen(suffix) + 1) < 0)
|
|
645
|
-
return -1;
|
|
646
|
-
|
|
647
|
-
git_buf_truncate(path, slash);
|
|
648
|
-
git_buf_puts(path, prefix);
|
|
649
|
-
git_oid_fmt(path->ptr + git_buf_len(path), &idx->hash);
|
|
650
|
-
path->size += GIT_OID_HEXSZ;
|
|
651
|
-
git_buf_puts(path, suffix);
|
|
652
|
-
|
|
653
|
-
return git_buf_oom(path) ? -1 : 0;
|
|
654
|
-
}
|
|
655
|
-
|
|
656
|
-
int git_indexer_write(git_indexer *idx)
|
|
657
|
-
{
|
|
658
|
-
git_mwindow *w = NULL;
|
|
659
|
-
int error;
|
|
660
|
-
unsigned int i, long_offsets = 0, left;
|
|
661
|
-
struct git_pack_idx_header hdr;
|
|
662
|
-
git_buf filename = GIT_BUF_INIT;
|
|
663
|
-
struct entry *entry;
|
|
664
|
-
void *packfile_hash;
|
|
665
|
-
git_oid file_hash;
|
|
666
|
-
SHA_CTX ctx;
|
|
667
|
-
|
|
668
|
-
git_vector_sort(&idx->objects);
|
|
669
|
-
|
|
670
|
-
git_buf_sets(&filename, idx->pack->pack_name);
|
|
671
|
-
git_buf_truncate(&filename, filename.size - strlen("pack"));
|
|
672
|
-
git_buf_puts(&filename, "idx");
|
|
673
|
-
if (git_buf_oom(&filename))
|
|
674
|
-
return -1;
|
|
675
|
-
|
|
676
|
-
error = git_filebuf_open(&idx->file, filename.ptr, GIT_FILEBUF_HASH_CONTENTS);
|
|
677
|
-
if (error < 0)
|
|
678
|
-
goto cleanup;
|
|
679
|
-
|
|
680
|
-
/* Write out the header */
|
|
681
|
-
hdr.idx_signature = htonl(PACK_IDX_SIGNATURE);
|
|
682
|
-
hdr.idx_version = htonl(2);
|
|
683
|
-
error = git_filebuf_write(&idx->file, &hdr, sizeof(hdr));
|
|
684
|
-
if (error < 0)
|
|
685
|
-
goto cleanup;
|
|
686
|
-
|
|
687
|
-
/* Write out the fanout table */
|
|
688
|
-
for (i = 0; i < 256; ++i) {
|
|
689
|
-
uint32_t n = htonl(idx->fanout[i]);
|
|
690
|
-
error = git_filebuf_write(&idx->file, &n, sizeof(n));
|
|
691
|
-
if (error < 0)
|
|
692
|
-
goto cleanup;
|
|
693
|
-
}
|
|
694
|
-
|
|
695
|
-
/* Write out the object names (SHA-1 hashes) */
|
|
696
|
-
SHA1_Init(&ctx);
|
|
697
|
-
git_vector_foreach(&idx->objects, i, entry) {
|
|
698
|
-
error = git_filebuf_write(&idx->file, &entry->oid, sizeof(git_oid));
|
|
699
|
-
SHA1_Update(&ctx, &entry->oid, GIT_OID_RAWSZ);
|
|
700
|
-
if (error < 0)
|
|
701
|
-
goto cleanup;
|
|
702
|
-
}
|
|
703
|
-
SHA1_Final(idx->hash.id, &ctx);
|
|
704
|
-
|
|
705
|
-
/* Write out the CRC32 values */
|
|
706
|
-
git_vector_foreach(&idx->objects, i, entry) {
|
|
707
|
-
error = git_filebuf_write(&idx->file, &entry->crc, sizeof(uint32_t));
|
|
708
|
-
if (error < 0)
|
|
709
|
-
goto cleanup;
|
|
710
|
-
}
|
|
711
|
-
|
|
712
|
-
/* Write out the offsets */
|
|
713
|
-
git_vector_foreach(&idx->objects, i, entry) {
|
|
714
|
-
uint32_t n;
|
|
715
|
-
|
|
716
|
-
if (entry->offset == UINT32_MAX)
|
|
717
|
-
n = htonl(0x80000000 | long_offsets++);
|
|
718
|
-
else
|
|
719
|
-
n = htonl(entry->offset);
|
|
720
|
-
|
|
721
|
-
error = git_filebuf_write(&idx->file, &n, sizeof(uint32_t));
|
|
722
|
-
if (error < 0)
|
|
723
|
-
goto cleanup;
|
|
724
|
-
}
|
|
725
|
-
|
|
726
|
-
/* Write out the long offsets */
|
|
727
|
-
git_vector_foreach(&idx->objects, i, entry) {
|
|
728
|
-
uint32_t split[2];
|
|
729
|
-
|
|
730
|
-
if (entry->offset != UINT32_MAX)
|
|
731
|
-
continue;
|
|
732
|
-
|
|
733
|
-
split[0] = htonl(entry->offset_long >> 32);
|
|
734
|
-
split[1] = htonl(entry->offset_long & 0xffffffff);
|
|
735
|
-
|
|
736
|
-
error = git_filebuf_write(&idx->file, &split, sizeof(uint32_t) * 2);
|
|
737
|
-
if (error < 0)
|
|
738
|
-
goto cleanup;
|
|
739
|
-
}
|
|
740
|
-
|
|
741
|
-
/* Write out the packfile trailer */
|
|
742
|
-
|
|
743
|
-
packfile_hash = git_mwindow_open(&idx->pack->mwf, &w, idx->pack->mwf.size - GIT_OID_RAWSZ, GIT_OID_RAWSZ, &left);
|
|
744
|
-
git_mwindow_close(&w);
|
|
745
|
-
if (packfile_hash == NULL) {
|
|
746
|
-
error = -1;
|
|
747
|
-
goto cleanup;
|
|
748
|
-
}
|
|
749
|
-
|
|
750
|
-
memcpy(&file_hash, packfile_hash, GIT_OID_RAWSZ);
|
|
751
|
-
|
|
752
|
-
git_mwindow_close(&w);
|
|
753
|
-
|
|
754
|
-
error = git_filebuf_write(&idx->file, &file_hash, sizeof(git_oid));
|
|
755
|
-
if (error < 0)
|
|
756
|
-
goto cleanup;
|
|
757
|
-
|
|
758
|
-
/* Write out the index sha */
|
|
759
|
-
error = git_filebuf_hash(&file_hash, &idx->file);
|
|
760
|
-
if (error < 0)
|
|
761
|
-
goto cleanup;
|
|
762
|
-
|
|
763
|
-
error = git_filebuf_write(&idx->file, &file_hash, sizeof(git_oid));
|
|
764
|
-
if (error < 0)
|
|
765
|
-
goto cleanup;
|
|
766
|
-
|
|
767
|
-
/* Figure out what the final name should be */
|
|
768
|
-
error = index_path(&filename, idx);
|
|
769
|
-
if (error < 0)
|
|
770
|
-
goto cleanup;
|
|
771
|
-
|
|
772
|
-
/* Commit file */
|
|
773
|
-
error = git_filebuf_commit_at(&idx->file, filename.ptr, GIT_PACK_FILE_MODE);
|
|
774
|
-
|
|
775
|
-
cleanup:
|
|
776
|
-
git_mwindow_free_all(&idx->pack->mwf);
|
|
777
|
-
git_mwindow_file_deregister(&idx->pack->mwf);
|
|
778
|
-
if (error < 0)
|
|
779
|
-
git_filebuf_cleanup(&idx->file);
|
|
780
|
-
git_buf_free(&filename);
|
|
781
|
-
|
|
782
|
-
return error;
|
|
783
|
-
}
|
|
784
|
-
|
|
785
|
-
int git_indexer_run(git_indexer *idx, git_indexer_stats *stats)
|
|
786
|
-
{
|
|
787
|
-
git_mwindow_file *mwf;
|
|
788
|
-
git_off_t off = sizeof(struct git_pack_header);
|
|
789
|
-
int error;
|
|
790
|
-
struct entry *entry;
|
|
791
|
-
unsigned int left, processed;
|
|
792
|
-
|
|
793
|
-
assert(idx && stats);
|
|
794
|
-
|
|
795
|
-
mwf = &idx->pack->mwf;
|
|
796
|
-
error = git_mwindow_file_register(mwf);
|
|
797
|
-
if (error < 0)
|
|
798
|
-
return error;
|
|
799
|
-
|
|
800
|
-
stats->total = (unsigned int)idx->nr_objects;
|
|
801
|
-
stats->processed = processed = 0;
|
|
802
|
-
|
|
803
|
-
while (processed < idx->nr_objects) {
|
|
804
|
-
git_rawobj obj;
|
|
805
|
-
git_oid oid;
|
|
806
|
-
struct git_pack_entry *pentry;
|
|
807
|
-
git_mwindow *w = NULL;
|
|
808
|
-
int i;
|
|
809
|
-
git_off_t entry_start = off;
|
|
810
|
-
void *packed;
|
|
811
|
-
size_t entry_size;
|
|
812
|
-
char fmt[GIT_OID_HEXSZ] = {0};
|
|
813
|
-
|
|
814
|
-
entry = git__calloc(1, sizeof(*entry));
|
|
815
|
-
GITERR_CHECK_ALLOC(entry);
|
|
816
|
-
|
|
817
|
-
if (off > UINT31_MAX) {
|
|
818
|
-
entry->offset = UINT32_MAX;
|
|
819
|
-
entry->offset_long = off;
|
|
820
|
-
} else {
|
|
821
|
-
entry->offset = (uint32_t)off;
|
|
822
|
-
}
|
|
823
|
-
|
|
824
|
-
error = git_packfile_unpack(&obj, idx->pack, &off);
|
|
825
|
-
if (error < 0)
|
|
826
|
-
goto cleanup;
|
|
827
|
-
|
|
828
|
-
/* FIXME: Parse the object instead of hashing it */
|
|
829
|
-
error = git_odb__hashobj(&oid, &obj);
|
|
830
|
-
if (error < 0) {
|
|
831
|
-
giterr_set(GITERR_INDEXER, "Failed to hash object");
|
|
832
|
-
goto cleanup;
|
|
833
|
-
}
|
|
834
|
-
|
|
835
|
-
pentry = git__malloc(sizeof(struct git_pack_entry));
|
|
836
|
-
if (pentry == NULL) {
|
|
837
|
-
error = -1;
|
|
838
|
-
goto cleanup;
|
|
839
|
-
}
|
|
840
|
-
|
|
841
|
-
git_oid_cpy(&pentry->sha1, &oid);
|
|
842
|
-
pentry->offset = entry_start;
|
|
843
|
-
git_oid_fmt(fmt, &oid);
|
|
844
|
-
error = git_vector_insert(&idx->pack->cache, pentry);
|
|
845
|
-
if (error < 0)
|
|
846
|
-
goto cleanup;
|
|
847
|
-
|
|
848
|
-
git_oid_cpy(&entry->oid, &oid);
|
|
849
|
-
entry->crc = crc32(0L, Z_NULL, 0);
|
|
850
|
-
|
|
851
|
-
entry_size = (size_t)(off - entry_start);
|
|
852
|
-
packed = git_mwindow_open(mwf, &w, entry_start, entry_size, &left);
|
|
853
|
-
if (packed == NULL) {
|
|
854
|
-
error = -1;
|
|
855
|
-
goto cleanup;
|
|
856
|
-
}
|
|
857
|
-
entry->crc = htonl(crc32(entry->crc, packed, (uInt)entry_size));
|
|
858
|
-
git_mwindow_close(&w);
|
|
859
|
-
|
|
860
|
-
/* Add the object to the list */
|
|
861
|
-
error = git_vector_insert(&idx->objects, entry);
|
|
862
|
-
if (error < 0)
|
|
863
|
-
goto cleanup;
|
|
864
|
-
|
|
865
|
-
for (i = oid.id[0]; i < 256; ++i) {
|
|
866
|
-
idx->fanout[i]++;
|
|
741
|
+
if (idx->pack) {
|
|
742
|
+
for (k = kh_begin(idx->pack->idx_cache); k != kh_end(idx->pack->idx_cache); k++) {
|
|
743
|
+
if (kh_exist(idx->pack->idx_cache, k))
|
|
744
|
+
git__free(kh_value(idx->pack->idx_cache, k));
|
|
867
745
|
}
|
|
868
746
|
|
|
869
|
-
|
|
870
|
-
|
|
871
|
-
stats->processed = ++processed;
|
|
747
|
+
git_oidmap_free(idx->pack->idx_cache);
|
|
872
748
|
}
|
|
873
749
|
|
|
874
|
-
|
|
875
|
-
|
|
876
|
-
|
|
877
|
-
|
|
878
|
-
|
|
879
|
-
}
|
|
880
|
-
|
|
881
|
-
void git_indexer_free(git_indexer *idx)
|
|
882
|
-
{
|
|
883
|
-
unsigned int i;
|
|
884
|
-
struct entry *e;
|
|
885
|
-
struct git_pack_entry *pe;
|
|
886
|
-
|
|
887
|
-
if (idx == NULL)
|
|
888
|
-
return;
|
|
889
|
-
|
|
890
|
-
p_close(idx->pack->mwf.fd);
|
|
891
|
-
git_mwindow_file_deregister(&idx->pack->mwf);
|
|
892
|
-
git_vector_foreach(&idx->objects, i, e)
|
|
893
|
-
git__free(e);
|
|
894
|
-
git_vector_free(&idx->objects);
|
|
895
|
-
git_vector_foreach(&idx->pack->cache, i, pe)
|
|
896
|
-
git__free(pe);
|
|
897
|
-
git_vector_free(&idx->pack->cache);
|
|
898
|
-
git__free(idx->pack);
|
|
750
|
+
git_vector_foreach(&idx->deltas, i, delta)
|
|
751
|
+
git__free(delta);
|
|
752
|
+
git_vector_free(&idx->deltas);
|
|
753
|
+
git_packfile_free(idx->pack);
|
|
754
|
+
git_filebuf_cleanup(&idx->pack_file);
|
|
899
755
|
git__free(idx);
|
|
900
756
|
}
|
|
901
|
-
|