rugged 0.17.0.b6 → 0.17.0.b7
Sign up to get free protection for your applications and to get access to all the features.
- data/README.md +3 -3
- data/Rakefile +3 -1
- data/ext/rugged/rugged.c +30 -0
- data/ext/rugged/rugged.h +9 -0
- data/ext/rugged/rugged_branch.c +306 -0
- data/ext/rugged/rugged_config.c +16 -13
- data/ext/rugged/rugged_index.c +25 -0
- data/ext/rugged/rugged_object.c +6 -2
- data/ext/rugged/rugged_reference.c +11 -18
- data/ext/rugged/rugged_revwalk.c +1 -1
- data/lib/rugged.rb +1 -0
- data/lib/rugged/branch.rb +28 -0
- data/lib/rugged/commit.rb +5 -5
- data/lib/rugged/repository.rb +32 -7
- data/lib/rugged/tag.rb +5 -1
- data/lib/rugged/version.rb +1 -1
- data/test/branch_test.rb +227 -0
- data/test/config_test.rb +1 -1
- data/test/fixtures/testrepo.git/objects/4b/825dc642cb6eb9a060e54bf8d69288fbee4904 +0 -0
- data/test/fixtures/testrepo.git/objects/a3/e05719b428a2d0ed7a55c4ce53dcc5768c6d5e +0 -0
- data/test/index_test.rb +31 -0
- data/test/index_test.rb~ +218 -0
- data/test/lib_test.rb +22 -0
- data/test/reference_test.rb +5 -3
- data/vendor/libgit2/Makefile.embed +1 -1
- data/vendor/libgit2/include/git2.h +1 -0
- data/vendor/libgit2/include/git2/branch.h +17 -13
- data/vendor/libgit2/include/git2/checkout.h +83 -22
- data/vendor/libgit2/include/git2/clone.h +6 -3
- data/vendor/libgit2/include/git2/common.h +1 -8
- data/vendor/libgit2/include/git2/config.h +185 -26
- data/vendor/libgit2/include/git2/diff.h +229 -17
- data/vendor/libgit2/include/git2/errors.h +39 -1
- data/vendor/libgit2/include/git2/ignore.h +6 -3
- data/vendor/libgit2/include/git2/indexer.h +1 -0
- data/vendor/libgit2/include/git2/merge.h +1 -1
- data/vendor/libgit2/include/git2/object.h +7 -4
- data/vendor/libgit2/include/git2/odb.h +4 -2
- data/vendor/libgit2/include/git2/odb_backend.h +6 -0
- data/vendor/libgit2/include/git2/oid.h +2 -0
- data/vendor/libgit2/include/git2/pack.h +89 -0
- data/vendor/libgit2/include/git2/refs.h +88 -0
- data/vendor/libgit2/include/git2/refspec.h +0 -8
- data/vendor/libgit2/include/git2/remote.h +34 -1
- data/vendor/libgit2/include/git2/repository.h +238 -6
- data/vendor/libgit2/include/git2/reset.h +4 -1
- data/vendor/libgit2/include/git2/revwalk.h +1 -1
- data/vendor/libgit2/include/git2/status.h +19 -14
- data/vendor/libgit2/include/git2/strarray.h +54 -0
- data/vendor/libgit2/include/git2/submodule.h +451 -45
- data/vendor/libgit2/include/git2/tag.h +16 -0
- data/vendor/libgit2/include/git2/tree.h +2 -2
- data/vendor/libgit2/include/git2/types.h +4 -0
- data/vendor/libgit2/src/amiga/map.c +4 -7
- data/vendor/libgit2/src/attr.c +21 -13
- data/vendor/libgit2/src/attr.h +3 -1
- data/vendor/libgit2/src/attr_file.c +14 -14
- data/vendor/libgit2/src/attr_file.h +6 -5
- data/vendor/libgit2/src/blob.c +22 -12
- data/vendor/libgit2/src/branch.c +62 -66
- data/vendor/libgit2/src/buffer.c +63 -14
- data/vendor/libgit2/src/buffer.h +4 -0
- data/vendor/libgit2/src/cache.c +5 -4
- data/vendor/libgit2/src/checkout.c +381 -159
- data/vendor/libgit2/src/clone.c +221 -94
- data/vendor/libgit2/src/common.h +13 -3
- data/vendor/libgit2/src/compress.c +53 -0
- data/vendor/libgit2/src/compress.h +16 -0
- data/vendor/libgit2/src/config.c +380 -175
- data/vendor/libgit2/src/config.h +2 -5
- data/vendor/libgit2/src/config_file.c +63 -46
- data/vendor/libgit2/src/config_file.h +16 -4
- data/vendor/libgit2/src/crlf.c +4 -3
- data/vendor/libgit2/src/delta.c +491 -0
- data/vendor/libgit2/src/delta.h +112 -0
- data/vendor/libgit2/src/diff.c +310 -67
- data/vendor/libgit2/src/diff.h +10 -1
- data/vendor/libgit2/src/diff_output.c +1030 -337
- data/vendor/libgit2/src/diff_output.h +86 -0
- data/vendor/libgit2/src/errors.c +10 -1
- data/vendor/libgit2/src/fetch.c +108 -24
- data/vendor/libgit2/src/filebuf.c +8 -2
- data/vendor/libgit2/src/fileops.c +342 -177
- data/vendor/libgit2/src/fileops.h +84 -7
- data/vendor/libgit2/src/filter.c +0 -35
- data/vendor/libgit2/src/filter.h +0 -12
- data/vendor/libgit2/src/{compat/fnmatch.c → fnmatch.c} +16 -4
- data/vendor/libgit2/src/{compat/fnmatch.h → fnmatch.h} +4 -3
- data/vendor/libgit2/src/global.c +4 -0
- data/vendor/libgit2/src/ignore.c +122 -23
- data/vendor/libgit2/src/ignore.h +1 -0
- data/vendor/libgit2/src/index.c +56 -10
- data/vendor/libgit2/src/index.h +2 -0
- data/vendor/libgit2/src/indexer.c +8 -9
- data/vendor/libgit2/src/iterator.c +244 -31
- data/vendor/libgit2/src/iterator.h +30 -1
- data/vendor/libgit2/src/message.c +1 -1
- data/vendor/libgit2/src/netops.c +44 -4
- data/vendor/libgit2/src/object.c +80 -69
- data/vendor/libgit2/src/object.h +39 -0
- data/vendor/libgit2/src/odb.c +79 -15
- data/vendor/libgit2/src/odb.h +20 -5
- data/vendor/libgit2/src/odb_pack.c +65 -33
- data/vendor/libgit2/src/oid.c +0 -3
- data/vendor/libgit2/src/pack-objects.c +1315 -0
- data/vendor/libgit2/src/pack-objects.h +87 -0
- data/vendor/libgit2/src/pack.c +36 -12
- data/vendor/libgit2/src/pack.h +1 -0
- data/vendor/libgit2/src/path.c +42 -9
- data/vendor/libgit2/src/path.h +14 -0
- data/vendor/libgit2/src/pkt.c +52 -2
- data/vendor/libgit2/src/pkt.h +10 -0
- data/vendor/libgit2/src/pool.h +11 -0
- data/vendor/libgit2/src/posix.h +8 -0
- data/vendor/libgit2/src/protocol.c +24 -2
- data/vendor/libgit2/src/protocol.h +4 -0
- data/vendor/libgit2/src/reflog.c +1 -1
- data/vendor/libgit2/src/refs.c +292 -124
- data/vendor/libgit2/src/refs.h +4 -2
- data/vendor/libgit2/src/refspec.c +117 -19
- data/vendor/libgit2/src/refspec.h +19 -0
- data/vendor/libgit2/src/remote.c +152 -48
- data/vendor/libgit2/src/remote.h +4 -1
- data/vendor/libgit2/src/repo_template.h +58 -0
- data/vendor/libgit2/src/repository.c +594 -179
- data/vendor/libgit2/src/repository.h +23 -22
- data/vendor/libgit2/src/reset.c +71 -29
- data/vendor/libgit2/src/revparse.c +26 -17
- data/vendor/libgit2/src/revwalk.c +36 -19
- data/vendor/libgit2/src/sha1.h +7 -0
- data/vendor/libgit2/src/{sha1.c → sha1/sha1.c} +0 -0
- data/vendor/libgit2/src/signature.c +12 -10
- data/vendor/libgit2/src/status.c +52 -6
- data/vendor/libgit2/src/submodule.c +1363 -255
- data/vendor/libgit2/src/submodule.h +102 -0
- data/vendor/libgit2/src/tag.c +42 -26
- data/vendor/libgit2/src/thread-utils.h +7 -7
- data/vendor/libgit2/src/transport.h +15 -1
- data/vendor/libgit2/src/transports/git.c +1 -1
- data/vendor/libgit2/src/transports/http.c +197 -36
- data/vendor/libgit2/src/tree.c +3 -3
- data/vendor/libgit2/src/unix/map.c +2 -0
- data/vendor/libgit2/src/unix/posix.h +1 -8
- data/vendor/libgit2/src/util.c +6 -1
- data/vendor/libgit2/src/util.h +7 -0
- data/vendor/libgit2/src/vector.c +16 -0
- data/vendor/libgit2/src/vector.h +1 -0
- data/vendor/libgit2/src/win32/dir.c +8 -21
- data/vendor/libgit2/src/win32/findfile.c +149 -0
- data/vendor/libgit2/src/win32/findfile.h +23 -0
- data/vendor/libgit2/src/win32/posix.h +3 -7
- data/vendor/libgit2/src/win32/posix_w32.c +44 -102
- data/vendor/libgit2/src/win32/pthread.c +68 -0
- data/vendor/libgit2/src/win32/pthread.h +7 -0
- data/vendor/libgit2/src/win32/utf-conv.c +60 -71
- data/vendor/libgit2/src/win32/utf-conv.h +4 -3
- metadata +70 -71
- data/vendor/libgit2/include/git2/windows.h +0 -59
@@ -9,6 +9,12 @@
|
|
9
9
|
|
10
10
|
#include "common.h"
|
11
11
|
#include "git2/index.h"
|
12
|
+
#include "vector.h"
|
13
|
+
#include "buffer.h"
|
14
|
+
|
15
|
+
#define ITERATOR_PREFIXCMP(ITER, STR, PREFIX) (((ITER).ignore_case) ? \
|
16
|
+
git__prefixcmp_icase((STR), (PREFIX)) : \
|
17
|
+
git__prefixcmp((STR), (PREFIX)))
|
12
18
|
|
13
19
|
typedef struct git_iterator git_iterator;
|
14
20
|
|
@@ -16,7 +22,8 @@ typedef enum {
|
|
16
22
|
GIT_ITERATOR_EMPTY = 0,
|
17
23
|
GIT_ITERATOR_TREE = 1,
|
18
24
|
GIT_ITERATOR_INDEX = 2,
|
19
|
-
GIT_ITERATOR_WORKDIR = 3
|
25
|
+
GIT_ITERATOR_WORKDIR = 3,
|
26
|
+
GIT_ITERATOR_SPOOLANDSORT = 4
|
20
27
|
} git_iterator_type_t;
|
21
28
|
|
22
29
|
struct git_iterator {
|
@@ -29,6 +36,7 @@ struct git_iterator {
|
|
29
36
|
int (*seek)(git_iterator *, const char *prefix);
|
30
37
|
int (*reset)(git_iterator *);
|
31
38
|
void (*free)(git_iterator *);
|
39
|
+
unsigned int ignore_case:1;
|
32
40
|
};
|
33
41
|
|
34
42
|
extern int git_iterator_for_nothing(git_iterator **iter);
|
@@ -63,6 +71,17 @@ GIT_INLINE(int) git_iterator_for_workdir(
|
|
63
71
|
return git_iterator_for_workdir_range(iter, repo, NULL, NULL);
|
64
72
|
}
|
65
73
|
|
74
|
+
extern int git_iterator_spoolandsort_range(
|
75
|
+
git_iterator **iter, git_iterator *towrap,
|
76
|
+
git_vector_cmp comparer, bool ignore_case,
|
77
|
+
const char *start, const char *end);
|
78
|
+
|
79
|
+
GIT_INLINE(int) git_iterator_spoolandsort(
|
80
|
+
git_iterator **iter, git_iterator *towrap,
|
81
|
+
git_vector_cmp comparer, bool ignore_case)
|
82
|
+
{
|
83
|
+
return git_iterator_spoolandsort_range(iter, towrap, comparer, ignore_case, NULL, NULL);
|
84
|
+
}
|
66
85
|
|
67
86
|
/* Entry is not guaranteed to be fully populated. For a tree iterator,
|
68
87
|
* we will only populate the mode, oid and path, for example. For a workdir
|
@@ -123,6 +142,9 @@ GIT_INLINE(git_iterator_type_t) git_iterator_type(git_iterator *iter)
|
|
123
142
|
extern int git_iterator_current_tree_entry(
|
124
143
|
git_iterator *iter, const git_tree_entry **tree_entry);
|
125
144
|
|
145
|
+
extern int git_iterator_current_parent_tree(
|
146
|
+
git_iterator *iter, const char *parent_path, const git_tree **tree_ptr);
|
147
|
+
|
126
148
|
extern int git_iterator_current_is_ignored(git_iterator *iter);
|
127
149
|
|
128
150
|
/**
|
@@ -148,4 +170,11 @@ extern int git_iterator_advance_into_directory(
|
|
148
170
|
extern int git_iterator_cmp(
|
149
171
|
git_iterator *iter, const char *path_prefix);
|
150
172
|
|
173
|
+
/**
|
174
|
+
* Get the full path of the current item from a workdir iterator.
|
175
|
+
* This will return NULL for a non-workdir iterator.
|
176
|
+
*/
|
177
|
+
extern int git_iterator_current_workdir_path(
|
178
|
+
git_iterator *iter, git_buf **path);
|
179
|
+
|
151
180
|
#endif
|
data/vendor/libgit2/src/netops.c
CHANGED
@@ -55,8 +55,44 @@ static void net_set_error(const char *str)
|
|
55
55
|
static int ssl_set_error(gitno_ssl *ssl, int error)
|
56
56
|
{
|
57
57
|
int err;
|
58
|
+
unsigned long e;
|
59
|
+
|
58
60
|
err = SSL_get_error(ssl->ssl, error);
|
59
|
-
|
61
|
+
|
62
|
+
assert(err != SSL_ERROR_WANT_READ);
|
63
|
+
assert(err != SSL_ERROR_WANT_WRITE);
|
64
|
+
|
65
|
+
switch (err) {
|
66
|
+
case SSL_ERROR_WANT_CONNECT:
|
67
|
+
case SSL_ERROR_WANT_ACCEPT:
|
68
|
+
giterr_set(GITERR_NET, "SSL error: connection failure\n");
|
69
|
+
break;
|
70
|
+
case SSL_ERROR_WANT_X509_LOOKUP:
|
71
|
+
giterr_set(GITERR_NET, "SSL error: x509 error\n");
|
72
|
+
break;
|
73
|
+
case SSL_ERROR_SYSCALL:
|
74
|
+
e = ERR_get_error();
|
75
|
+
if (e > 0) {
|
76
|
+
giterr_set(GITERR_NET, "SSL error: %s",
|
77
|
+
ERR_error_string(e, NULL));
|
78
|
+
break;
|
79
|
+
} else if (error < 0) {
|
80
|
+
giterr_set(GITERR_OS, "SSL error: syscall failure");
|
81
|
+
break;
|
82
|
+
}
|
83
|
+
giterr_set(GITERR_NET, "SSL error: received early EOF");
|
84
|
+
break;
|
85
|
+
case SSL_ERROR_SSL:
|
86
|
+
e = ERR_get_error();
|
87
|
+
giterr_set(GITERR_NET, "SSL error: %s",
|
88
|
+
ERR_error_string(e, NULL));
|
89
|
+
break;
|
90
|
+
case SSL_ERROR_NONE:
|
91
|
+
case SSL_ERROR_ZERO_RETURN:
|
92
|
+
default:
|
93
|
+
giterr_set(GITERR_NET, "SSL error: unknown error");
|
94
|
+
break;
|
95
|
+
}
|
60
96
|
return -1;
|
61
97
|
}
|
62
98
|
#endif
|
@@ -238,6 +274,10 @@ static int verify_server_cert(git_transport *t, const char *host)
|
|
238
274
|
void *addr;
|
239
275
|
int i = -1,j;
|
240
276
|
|
277
|
+
if (SSL_get_verify_result(t->ssl.ssl) != X509_V_OK) {
|
278
|
+
giterr_set(GITERR_SSL, "The SSL certificate is invalid");
|
279
|
+
return -1;
|
280
|
+
}
|
241
281
|
|
242
282
|
/* Try to parse the host as an IP address to see if it is */
|
243
283
|
if (inet_pton(AF_INET, host, &addr4)) {
|
@@ -286,7 +326,7 @@ static int verify_server_cert(git_transport *t, const char *host)
|
|
286
326
|
GENERAL_NAMES_free(alts);
|
287
327
|
|
288
328
|
if (matched == 0)
|
289
|
-
goto
|
329
|
+
goto cert_fail;
|
290
330
|
|
291
331
|
if (matched == 1)
|
292
332
|
return 0;
|
@@ -354,7 +394,7 @@ static int ssl_setup(git_transport *t, const char *host)
|
|
354
394
|
return ssl_set_error(&t->ssl, 0);
|
355
395
|
|
356
396
|
SSL_CTX_set_mode(t->ssl.ctx, SSL_MODE_AUTO_RETRY);
|
357
|
-
SSL_CTX_set_verify(t->ssl.ctx,
|
397
|
+
SSL_CTX_set_verify(t->ssl.ctx, SSL_VERIFY_NONE, NULL);
|
358
398
|
if (!SSL_CTX_set_default_verify_paths(t->ssl.ctx))
|
359
399
|
return ssl_set_error(&t->ssl, 0);
|
360
400
|
|
@@ -438,7 +478,7 @@ static int send_ssl(gitno_ssl *ssl, const char *msg, size_t len)
|
|
438
478
|
|
439
479
|
while (off < len) {
|
440
480
|
ret = SSL_write(ssl->ssl, msg + off, len - off);
|
441
|
-
if (ret <= 0)
|
481
|
+
if (ret <= 0 && ret != SSL_ERROR_WANT_WRITE)
|
442
482
|
return ssl_set_error(ssl, ret);
|
443
483
|
|
444
484
|
off += ret;
|
data/vendor/libgit2/src/object.c
CHANGED
@@ -77,6 +77,58 @@ static int create_object(git_object **object_out, git_otype type)
|
|
77
77
|
return 0;
|
78
78
|
}
|
79
79
|
|
80
|
+
int git_object__from_odb_object(
|
81
|
+
git_object **object_out,
|
82
|
+
git_repository *repo,
|
83
|
+
git_odb_object *odb_obj,
|
84
|
+
git_otype type)
|
85
|
+
{
|
86
|
+
int error;
|
87
|
+
git_object *object = NULL;
|
88
|
+
|
89
|
+
if (type != GIT_OBJ_ANY && type != odb_obj->raw.type) {
|
90
|
+
giterr_set(GITERR_ODB, "The requested type does not match the type in the ODB");
|
91
|
+
return GIT_ENOTFOUND;
|
92
|
+
}
|
93
|
+
|
94
|
+
type = odb_obj->raw.type;
|
95
|
+
|
96
|
+
if ((error = create_object(&object, type)) < 0)
|
97
|
+
return error;
|
98
|
+
|
99
|
+
/* Initialize parent object */
|
100
|
+
git_oid_cpy(&object->cached.oid, &odb_obj->cached.oid);
|
101
|
+
object->repo = repo;
|
102
|
+
|
103
|
+
switch (type) {
|
104
|
+
case GIT_OBJ_COMMIT:
|
105
|
+
error = git_commit__parse((git_commit *)object, odb_obj);
|
106
|
+
break;
|
107
|
+
|
108
|
+
case GIT_OBJ_TREE:
|
109
|
+
error = git_tree__parse((git_tree *)object, odb_obj);
|
110
|
+
break;
|
111
|
+
|
112
|
+
case GIT_OBJ_TAG:
|
113
|
+
error = git_tag__parse((git_tag *)object, odb_obj);
|
114
|
+
break;
|
115
|
+
|
116
|
+
case GIT_OBJ_BLOB:
|
117
|
+
error = git_blob__parse((git_blob *)object, odb_obj);
|
118
|
+
break;
|
119
|
+
|
120
|
+
default:
|
121
|
+
break;
|
122
|
+
}
|
123
|
+
|
124
|
+
if (error < 0)
|
125
|
+
git_object__free(object);
|
126
|
+
else
|
127
|
+
*object_out = git_cache_try_store(&repo->objects, object);
|
128
|
+
|
129
|
+
return error;
|
130
|
+
}
|
131
|
+
|
80
132
|
int git_object_lookup_prefix(
|
81
133
|
git_object **object_out,
|
82
134
|
git_repository *repo,
|
@@ -148,53 +200,11 @@ int git_object_lookup_prefix(
|
|
148
200
|
if (error < 0)
|
149
201
|
return error;
|
150
202
|
|
151
|
-
|
152
|
-
git_odb_object_free(odb_obj);
|
153
|
-
giterr_set(GITERR_ODB, "The given type does not match the type on the ODB");
|
154
|
-
return GIT_ENOTFOUND;
|
155
|
-
}
|
156
|
-
|
157
|
-
type = odb_obj->raw.type;
|
158
|
-
|
159
|
-
if (create_object(&object, type) < 0) {
|
160
|
-
git_odb_object_free(odb_obj);
|
161
|
-
return -1;
|
162
|
-
}
|
163
|
-
|
164
|
-
/* Initialize parent object */
|
165
|
-
git_oid_cpy(&object->cached.oid, &odb_obj->cached.oid);
|
166
|
-
object->repo = repo;
|
167
|
-
|
168
|
-
switch (type) {
|
169
|
-
case GIT_OBJ_COMMIT:
|
170
|
-
error = git_commit__parse((git_commit *)object, odb_obj);
|
171
|
-
break;
|
172
|
-
|
173
|
-
case GIT_OBJ_TREE:
|
174
|
-
error = git_tree__parse((git_tree *)object, odb_obj);
|
175
|
-
break;
|
176
|
-
|
177
|
-
case GIT_OBJ_TAG:
|
178
|
-
error = git_tag__parse((git_tag *)object, odb_obj);
|
179
|
-
break;
|
180
|
-
|
181
|
-
case GIT_OBJ_BLOB:
|
182
|
-
error = git_blob__parse((git_blob *)object, odb_obj);
|
183
|
-
break;
|
184
|
-
|
185
|
-
default:
|
186
|
-
break;
|
187
|
-
}
|
203
|
+
error = git_object__from_odb_object(object_out, repo, odb_obj, type);
|
188
204
|
|
189
205
|
git_odb_object_free(odb_obj);
|
190
206
|
|
191
|
-
|
192
|
-
git_object__free(object);
|
193
|
-
return -1;
|
194
|
-
}
|
195
|
-
|
196
|
-
*object_out = git_cache_try_store(&repo->objects, object);
|
197
|
-
return 0;
|
207
|
+
return error;
|
198
208
|
}
|
199
209
|
|
200
210
|
int git_object_lookup(git_object **object_out, git_repository *repo, const git_oid *id, git_otype type) {
|
@@ -334,6 +344,12 @@ int git_object__resolve_to_type(git_object **obj, git_otype type)
|
|
334
344
|
return error;
|
335
345
|
}
|
336
346
|
|
347
|
+
static int peel_error(int error, const char* msg)
|
348
|
+
{
|
349
|
+
giterr_set(GITERR_INVALID, "The given object cannot be peeled - %s", msg);
|
350
|
+
return error;
|
351
|
+
}
|
352
|
+
|
337
353
|
static int dereference_object(git_object **dereferenced, git_object *obj)
|
338
354
|
{
|
339
355
|
git_otype type = git_object_type(obj);
|
@@ -341,48 +357,36 @@ static int dereference_object(git_object **dereferenced, git_object *obj)
|
|
341
357
|
switch (type) {
|
342
358
|
case GIT_OBJ_COMMIT:
|
343
359
|
return git_commit_tree((git_tree **)dereferenced, (git_commit*)obj);
|
344
|
-
break;
|
345
360
|
|
346
361
|
case GIT_OBJ_TAG:
|
347
362
|
return git_tag_target(dereferenced, (git_tag*)obj);
|
348
|
-
|
363
|
+
|
364
|
+
case GIT_OBJ_BLOB:
|
365
|
+
return peel_error(GIT_ERROR, "cannot dereference blob");
|
366
|
+
|
367
|
+
case GIT_OBJ_TREE:
|
368
|
+
return peel_error(GIT_ERROR, "cannot dereference tree");
|
349
369
|
|
350
370
|
default:
|
351
|
-
return GIT_ENOTFOUND;
|
352
|
-
break;
|
371
|
+
return peel_error(GIT_ENOTFOUND, "unexpected object type encountered");
|
353
372
|
}
|
354
373
|
}
|
355
374
|
|
356
|
-
static int peel_error(int error, const char* msg)
|
357
|
-
{
|
358
|
-
giterr_set(GITERR_INVALID, "The given object cannot be peeled - %s", msg);
|
359
|
-
return error;
|
360
|
-
}
|
361
|
-
|
362
375
|
int git_object_peel(
|
363
|
-
|
364
|
-
|
365
|
-
|
376
|
+
git_object **peeled,
|
377
|
+
git_object *object,
|
378
|
+
git_otype target_type)
|
366
379
|
{
|
367
380
|
git_object *source, *deref = NULL;
|
368
381
|
|
369
|
-
assert(object);
|
382
|
+
assert(object && peeled);
|
370
383
|
|
371
384
|
if (git_object_type(object) == target_type)
|
372
385
|
return git_object__dup(peeled, object);
|
373
386
|
|
374
|
-
if (target_type == GIT_OBJ_BLOB
|
375
|
-
|| target_type == GIT_OBJ_ANY)
|
376
|
-
return peel_error(GIT_EAMBIGUOUS, "Ambiguous target type");
|
377
|
-
|
378
|
-
if (git_object_type(object) == GIT_OBJ_BLOB)
|
379
|
-
return peel_error(GIT_ERROR, "A blob cannot be dereferenced");
|
380
|
-
|
381
387
|
source = object;
|
382
388
|
|
383
|
-
while (
|
384
|
-
if (dereference_object(&deref, source) < 0)
|
385
|
-
goto cleanup;
|
389
|
+
while (!dereference_object(&deref, source)) {
|
386
390
|
|
387
391
|
if (source != object)
|
388
392
|
git_object_free(source);
|
@@ -392,13 +396,20 @@ int git_object_peel(
|
|
392
396
|
return 0;
|
393
397
|
}
|
394
398
|
|
399
|
+
if (target_type == GIT_OBJ_ANY &&
|
400
|
+
git_object_type(deref) != git_object_type(object))
|
401
|
+
{
|
402
|
+
*peeled = deref;
|
403
|
+
return 0;
|
404
|
+
}
|
405
|
+
|
395
406
|
source = deref;
|
396
407
|
deref = NULL;
|
397
408
|
}
|
398
409
|
|
399
|
-
cleanup:
|
400
410
|
if (source != object)
|
401
411
|
git_object_free(source);
|
412
|
+
|
402
413
|
git_object_free(deref);
|
403
414
|
return -1;
|
404
415
|
}
|
@@ -0,0 +1,39 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright (C) 2009-2012 the libgit2 contributors
|
3
|
+
*
|
4
|
+
* This file is part of libgit2, distributed under the GNU GPL v2 with
|
5
|
+
* a Linking Exception. For full terms see the included COPYING file.
|
6
|
+
*/
|
7
|
+
#ifndef INCLUDE_object_h__
|
8
|
+
#define INCLUDE_object_h__
|
9
|
+
|
10
|
+
/** Base git object for inheritance */
|
11
|
+
struct git_object {
|
12
|
+
git_cached_obj cached;
|
13
|
+
git_repository *repo;
|
14
|
+
git_otype type;
|
15
|
+
};
|
16
|
+
|
17
|
+
/* fully free the object; internal method, DO NOT EXPORT */
|
18
|
+
void git_object__free(void *object);
|
19
|
+
|
20
|
+
GIT_INLINE(int) git_object__dup(git_object **dest, git_object *source)
|
21
|
+
{
|
22
|
+
git_cached_obj_incref(source);
|
23
|
+
*dest = source;
|
24
|
+
return 0;
|
25
|
+
}
|
26
|
+
|
27
|
+
int git_object__from_odb_object(
|
28
|
+
git_object **object_out,
|
29
|
+
git_repository *repo,
|
30
|
+
git_odb_object *odb_obj,
|
31
|
+
git_otype type);
|
32
|
+
|
33
|
+
int git_object__resolve_to_type(git_object **obj, git_otype type);
|
34
|
+
|
35
|
+
int git_oid__parse(git_oid *oid, const char **buffer_out, const char *buffer_end, const char *header);
|
36
|
+
|
37
|
+
void git_oid__writebuf(git_buf *buf, const char *header, const git_oid *oid);
|
38
|
+
|
39
|
+
#endif
|
data/vendor/libgit2/src/odb.c
CHANGED
@@ -12,6 +12,7 @@
|
|
12
12
|
#include "hash.h"
|
13
13
|
#include "odb.h"
|
14
14
|
#include "delta-apply.h"
|
15
|
+
#include "filter.h"
|
15
16
|
|
16
17
|
#include "git2/odb_backend.h"
|
17
18
|
#include "git2/oid.h"
|
@@ -106,6 +107,9 @@ git_otype git_odb_object_type(git_odb_object *object)
|
|
106
107
|
|
107
108
|
void git_odb_object_free(git_odb_object *object)
|
108
109
|
{
|
110
|
+
if (object == NULL)
|
111
|
+
return;
|
112
|
+
|
109
113
|
git_cached_obj_decref((git_cached_obj *)object, &free_odb_object);
|
110
114
|
}
|
111
115
|
|
@@ -114,32 +118,67 @@ int git_odb__hashfd(git_oid *out, git_file fd, size_t size, git_otype type)
|
|
114
118
|
int hdr_len;
|
115
119
|
char hdr[64], buffer[2048];
|
116
120
|
git_hash_ctx *ctx;
|
121
|
+
ssize_t read_len = 0;
|
122
|
+
|
123
|
+
if (!git_object_typeisloose(type)) {
|
124
|
+
giterr_set(GITERR_INVALID, "Invalid object type for hash");
|
125
|
+
return -1;
|
126
|
+
}
|
117
127
|
|
118
128
|
hdr_len = format_object_header(hdr, sizeof(hdr), size, type);
|
119
129
|
|
120
130
|
ctx = git_hash_new_ctx();
|
131
|
+
GITERR_CHECK_ALLOC(ctx);
|
121
132
|
|
122
133
|
git_hash_update(ctx, hdr, hdr_len);
|
123
134
|
|
124
|
-
while (size > 0) {
|
125
|
-
ssize_t read_len = read(fd, buffer, sizeof(buffer));
|
126
|
-
|
127
|
-
if (read_len < 0) {
|
128
|
-
git_hash_free_ctx(ctx);
|
129
|
-
giterr_set(GITERR_OS, "Error reading file");
|
130
|
-
return -1;
|
131
|
-
}
|
132
|
-
|
135
|
+
while (size > 0 && (read_len = p_read(fd, buffer, sizeof(buffer))) > 0) {
|
133
136
|
git_hash_update(ctx, buffer, read_len);
|
134
137
|
size -= read_len;
|
135
138
|
}
|
136
139
|
|
140
|
+
/* If p_read returned an error code, the read obviously failed.
|
141
|
+
* If size is not zero, the file was truncated after we originally
|
142
|
+
* stat'd it, so we consider this a read failure too */
|
143
|
+
if (read_len < 0 || size > 0) {
|
144
|
+
git_hash_free_ctx(ctx);
|
145
|
+
giterr_set(GITERR_OS, "Error reading file for hashing");
|
146
|
+
return -1;
|
147
|
+
}
|
148
|
+
|
137
149
|
git_hash_final(out, ctx);
|
138
150
|
git_hash_free_ctx(ctx);
|
139
151
|
|
140
152
|
return 0;
|
141
153
|
}
|
142
154
|
|
155
|
+
int git_odb__hashfd_filtered(
|
156
|
+
git_oid *out, git_file fd, size_t size, git_otype type, git_vector *filters)
|
157
|
+
{
|
158
|
+
int error;
|
159
|
+
git_buf raw = GIT_BUF_INIT;
|
160
|
+
git_buf filtered = GIT_BUF_INIT;
|
161
|
+
|
162
|
+
if (!filters || !filters->length)
|
163
|
+
return git_odb__hashfd(out, fd, size, type);
|
164
|
+
|
165
|
+
/* size of data is used in header, so we have to read the whole file
|
166
|
+
* into memory to apply filters before beginning to calculate the hash
|
167
|
+
*/
|
168
|
+
|
169
|
+
if (!(error = git_futils_readbuffer_fd(&raw, fd, size)))
|
170
|
+
error = git_filters_apply(&filtered, &raw, filters);
|
171
|
+
|
172
|
+
git_buf_free(&raw);
|
173
|
+
|
174
|
+
if (!error)
|
175
|
+
error = git_odb_hash(out, filtered.ptr, filtered.size, type);
|
176
|
+
|
177
|
+
git_buf_free(&filtered);
|
178
|
+
|
179
|
+
return error;
|
180
|
+
}
|
181
|
+
|
143
182
|
int git_odb__hashlink(git_oid *out, const char *path)
|
144
183
|
{
|
145
184
|
struct stat st;
|
@@ -160,10 +199,11 @@ int git_odb__hashlink(git_oid *out, const char *path)
|
|
160
199
|
char *link_data;
|
161
200
|
ssize_t read_len;
|
162
201
|
|
163
|
-
link_data = git__malloc((size_t)size);
|
202
|
+
link_data = git__malloc((size_t)(size + 1));
|
164
203
|
GITERR_CHECK_ALLOC(link_data);
|
165
204
|
|
166
|
-
read_len = p_readlink(path, link_data, (size_t)
|
205
|
+
read_len = p_readlink(path, link_data, (size_t)size);
|
206
|
+
link_data[size] = '\0';
|
167
207
|
if (read_len != (ssize_t)size) {
|
168
208
|
giterr_set(GITERR_OS, "Failed to read symlink data for '%s'", path);
|
169
209
|
return -1;
|
@@ -171,7 +211,7 @@ int git_odb__hashlink(git_oid *out, const char *path)
|
|
171
211
|
|
172
212
|
result = git_odb_hash(out, link_data, (size_t)size, GIT_OBJ_BLOB);
|
173
213
|
git__free(link_data);
|
174
|
-
} else {
|
214
|
+
} else {
|
175
215
|
int fd = git_futils_open_ro(path);
|
176
216
|
if (fd < 0)
|
177
217
|
return -1;
|
@@ -484,20 +524,37 @@ int git_odb_exists(git_odb *db, const git_oid *id)
|
|
484
524
|
}
|
485
525
|
|
486
526
|
int git_odb_read_header(size_t *len_p, git_otype *type_p, git_odb *db, const git_oid *id)
|
527
|
+
{
|
528
|
+
int error;
|
529
|
+
git_odb_object *object;
|
530
|
+
|
531
|
+
error = git_odb__read_header_or_object(&object, len_p, type_p, db, id);
|
532
|
+
|
533
|
+
if (object)
|
534
|
+
git_odb_object_free(object);
|
535
|
+
|
536
|
+
return error;
|
537
|
+
}
|
538
|
+
|
539
|
+
int git_odb__read_header_or_object(
|
540
|
+
git_odb_object **out, size_t *len_p, git_otype *type_p,
|
541
|
+
git_odb *db, const git_oid *id)
|
487
542
|
{
|
488
543
|
unsigned int i;
|
489
544
|
int error = GIT_ENOTFOUND;
|
490
545
|
git_odb_object *object;
|
491
546
|
|
492
|
-
assert(db && id);
|
547
|
+
assert(db && id && out && len_p && type_p);
|
493
548
|
|
494
549
|
if ((object = git_cache_get(&db->cache, id)) != NULL) {
|
495
550
|
*len_p = object->raw.len;
|
496
551
|
*type_p = object->raw.type;
|
497
|
-
|
552
|
+
*out = object;
|
498
553
|
return 0;
|
499
554
|
}
|
500
555
|
|
556
|
+
*out = NULL;
|
557
|
+
|
501
558
|
for (i = 0; i < db->backends.length && error < 0; ++i) {
|
502
559
|
backend_internal *internal = git_vector_get(&db->backends, i);
|
503
560
|
git_odb_backend *b = internal->backend;
|
@@ -518,7 +575,8 @@ int git_odb_read_header(size_t *len_p, git_otype *type_p, git_odb *db, const git
|
|
518
575
|
|
519
576
|
*len_p = object->raw.len;
|
520
577
|
*type_p = object->raw.type;
|
521
|
-
|
578
|
+
*out = object;
|
579
|
+
|
522
580
|
return 0;
|
523
581
|
}
|
524
582
|
|
@@ -708,6 +766,12 @@ int git_odb_open_rstream(git_odb_stream **stream, git_odb *db, const git_oid *oi
|
|
708
766
|
return error;
|
709
767
|
}
|
710
768
|
|
769
|
+
void * git_odb_backend_malloc(git_odb_backend *backend, size_t len)
|
770
|
+
{
|
771
|
+
GIT_UNUSED(backend);
|
772
|
+
return git__malloc(len);
|
773
|
+
}
|
774
|
+
|
711
775
|
int git_odb__error_notfound(const char *message, const git_oid *oid)
|
712
776
|
{
|
713
777
|
if (oid != NULL) {
|