diff options
| -rw-r--r-- | CMakeLists.txt | 15 | ||||
| -rw-r--r-- | CONTRIBUTING.md | 13 | ||||
| -rw-r--r-- | README.md | 19 | ||||
| -rw-r--r-- | include/git2/object.h | 2 | ||||
| -rw-r--r-- | include/git2/remote.h | 8 | ||||
| -rw-r--r-- | include/git2/tree.h | 2 | ||||
| -rw-r--r-- | src/diff_tform.c | 4 | ||||
| -rw-r--r-- | src/index.c | 12 | ||||
| -rw-r--r-- | src/indexer.c | 2 | ||||
| -rw-r--r-- | src/merge.c | 4 | ||||
| -rw-r--r-- | src/odb.c | 1 | ||||
| -rw-r--r-- | src/pack-objects.c | 4 | ||||
| -rw-r--r-- | src/pack.c | 4 | ||||
| -rw-r--r-- | src/remote.c | 6 | ||||
| -rw-r--r-- | src/repository.c | 6 | ||||
| -rw-r--r-- | src/revparse.c | 13 | ||||
| -rw-r--r-- | tests-clar/refs/revparse.c | 41 |
17 files changed, 124 insertions, 32 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt index 1086005c3..c937ba93c 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -30,16 +30,13 @@ OPTION( ENABLE_TRACE "Enables tracing support" OFF ) OPTION( LIBGIT2_FILENAME "Name of the produced binary" OFF ) IF(MSVC) - # This option is only availalbe when building with MSVC. By default, - # libgit2 is build using the stdcall calling convention, as that's what - # the CLR expects by default and how the Windows API is built. + # This option is only available when building with MSVC. By default, libgit2 + # is build using the cdecl calling convention, which is useful if you're + # writing C. However, the CLR and Win32 API both expect stdcall. # - # If you are writing a C or C++ program and want to link to libgit2, you - # have to either: - # - Add /Gz to the compiler options of _your_ program / library. - # - Turn this off by invoking CMake with the "-DSTDCALL=Off" argument. - # - OPTION( STDCALL "Build libgit2 with the __stdcall convention" ON ) + # If you are writing a CLR program and want to link to libgit2, you'll want + # to turn this on by invoking CMake with the "-DSTDCALL=ON" argument. + OPTION( STDCALL "Build libgit2 with the __stdcall convention" OFF ) # This option must match the settings used in your program, in particular if you # are linking statically diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 28ef27f42..5c2eaec5e 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -48,6 +48,12 @@ Please include a nice description of your changes with your PR; if we have to read the whole diff to figure out why you're contributing in the first place, you're less likely to get feedback and have your change merged in. +If you are working on a particular area then feel free to submit a PR that +highlights your work in progress (and flag in the PR title that it's not +ready to merge). This will help in getting visibility for your fix, allow +others to comment early on the changes and also let others know that you +are currently working on something. + ## Porting Code From Other Open-Source Projects `libgit2` is licensed under the terms of the GPL v2 with a linking @@ -57,14 +63,17 @@ The most common case is porting code from core Git. Git is a pure GPL project, which means that in order to port code to this project, we need the explicit permission of the author. Check the [`git.git-authors`](https://github.com/libgit2/libgit2/blob/development/git.git-authors) -file for authors who have already consented; feel free to add someone if -you've obtained their consent. +file for authors who have already consented. Other licenses have other requirements; check the license of the library you're porting code *from* to see what you need to do. As a general rule, MIT and BSD (3-clause) licenses are typically no problem. Apache 2.0 license typically doesn't work due to GPL incompatibility. +If you are pulling in code from core Git, another project or code you've pulled from +a forum / Stack Overflow then please flag this in your PR and also make sure you've +given proper credit to the original author in the code snippet. + ## Style Guide `libgit2` is written in [ANSI C](http://en.wikipedia.org/wiki/ANSI_C) @@ -11,20 +11,23 @@ libgit2 is licensed under a **very permissive license** (GPLv2 with a special Li This basically means that you can link it (unmodified) with any kind of software without having to release its source code. -* Mailing list: ~~<libgit2@librelist.org>~~ - The libgit2 mailing list has - traditionally been hosted in Librelist, but Librelist is and has always - been a shitshow. We encourage you to [open an issue](https://github.com/libgit2/libgit2/issues) - on GitHub instead for any questions regarding the library. - * Archives: <http://librelist.com/browser/libgit2/> * Website: <http://libgit2.github.com> +* StackOverflow Tag: [libgit2](http://stackoverflow.com/questions/tagged/libgit2) +* Issues: <https://github.com/libgit2/libgit2/issues> * API documentation: <http://libgit2.github.com/libgit2> * IRC: #libgit2 on irc.freenode.net. +* Mailing list: The libgit2 mailing list was + traditionally hosted in Librelist but has been deprecated. We encourage you to + [use StackOverflow](http://stackoverflow.com/questions/tagged/libgit2) or [open an issue](https://github.com/libgit2/libgit2/issues) + on GitHub instead for any questions regarding the library. The mailing list archives are still available at + <http://librelist.com/browser/libgit2/>. + What It Can Do ================================== -libgit2 is already very usable. +libgit2 is already very usable and is being used in production for many applications including the GitHub.com site, in Plastic SCM +and also powering Microsoft's Visual Studio tools for Git. The library provides: * SHA conversions, formatting and shortening * abstracted ODB backend system @@ -128,8 +131,8 @@ Here are the bindings to libgit2 that are currently available: * Lua * luagit2 <https://github.com/libgit2/luagit2> * .NET - * libgit2net, low level bindings <https://github.com/txdv/libgit2net> * libgit2sharp <https://github.com/libgit2/libgit2sharp> + * libgit2net, low level bindings superceeded by libgit2sharp <https://github.com/txdv/libgit2net> * Node.js * node-gitteh <https://github.com/libgit2/node-gitteh> * nodegit <https://github.com/tbranyen/nodegit> diff --git a/include/git2/object.h b/include/git2/object.h index b91b04dba..f74f3dfd1 100644 --- a/include/git2/object.h +++ b/include/git2/object.h @@ -36,7 +36,7 @@ GIT_BEGIN_DECL * @param repo the repository to look up the object * @param id the unique identifier for the object * @param type the type of the object - * @return a reference to the object + * @return 0 or an error code */ GIT_EXTERN(int) git_object_lookup( git_object **object, diff --git a/include/git2/remote.h b/include/git2/remote.h index 45d15d0a3..13b04367c 100644 --- a/include/git2/remote.h +++ b/include/git2/remote.h @@ -96,6 +96,14 @@ GIT_EXTERN(int) git_remote_load(git_remote **out, git_repository *repo, const ch GIT_EXTERN(int) git_remote_save(const git_remote *remote); /** + * Get the remote's repository + * + * @param remote the remote + * @return a pointer to the repository + */ +GIT_EXTERN(git_repository *) git_remote_owner(const git_remote *remote); + +/** * Get the remote's name * * @param remote the remote diff --git a/include/git2/tree.h b/include/git2/tree.h index 65d8cc16e..f1e7d0899 100644 --- a/include/git2/tree.h +++ b/include/git2/tree.h @@ -208,7 +208,7 @@ GIT_EXTERN(git_filemode_t) git_tree_entry_filemode(const git_tree_entry *entry); GIT_EXTERN(int) git_tree_entry_cmp(const git_tree_entry *e1, const git_tree_entry *e2); /** - * Convert a tree entry to the git_object it points too. + * Convert a tree entry to the git_object it points to. * * You must call `git_object_free()` on the object when you are done with it. * diff --git a/src/diff_tform.c b/src/diff_tform.c index b137bd319..ac5356a8c 100644 --- a/src/diff_tform.c +++ b/src/diff_tform.c @@ -590,11 +590,13 @@ static bool is_rename_target( return false; case GIT_DELTA_UNTRACKED: - case GIT_DELTA_IGNORED: if (!FLAG_SET(opts, GIT_DIFF_FIND_FOR_UNTRACKED)) return false; break; + case GIT_DELTA_IGNORED: + return false; + default: /* all other status values should be checked */ break; } diff --git a/src/index.c b/src/index.c index bd5e192f3..0610eb5b9 100644 --- a/src/index.c +++ b/src/index.c @@ -1409,14 +1409,18 @@ static int read_reuc(git_index *index, const char *buffer, size_t size) if (git__strtol32(&tmp, buffer, &endptr, 8) < 0 || !endptr || endptr == buffer || *endptr || - (unsigned)tmp > UINT_MAX) + (unsigned)tmp > UINT_MAX) { + index_entry_reuc_free(lost); return index_error_invalid("reading reuc entry stage"); + } lost->mode[i] = tmp; len = (endptr + 1) - buffer; - if (size <= len) + if (size <= len) { + index_entry_reuc_free(lost); return index_error_invalid("reading reuc entry stage"); + } size -= len; buffer += len; @@ -1426,8 +1430,10 @@ static int read_reuc(git_index *index, const char *buffer, size_t size) for (i = 0; i < 3; i++) { if (!lost->mode[i]) continue; - if (size < 20) + if (size < 20) { + index_entry_reuc_free(lost); return index_error_invalid("reading reuc entry oid"); + } git_oid_fromraw(&lost->oid[i], (const unsigned char *) buffer); size -= 20; diff --git a/src/indexer.c b/src/indexer.c index 1b638cd8a..09f962934 100644 --- a/src/indexer.c +++ b/src/indexer.c @@ -325,7 +325,7 @@ static int hash_and_save(git_indexer_stream *idx, git_rawobj *obj, git_off_t ent /* FIXME: Parse the object instead of hashing it */ if (git_odb__hashobj(&oid, obj) < 0) { giterr_set(GITERR_INDEXER, "Failed to hash object"); - return -1; + goto on_error; } pentry = git__calloc(1, sizeof(struct git_pack_entry)); diff --git a/src/merge.c b/src/merge.c index 82d2e6f37..2e94ce1cd 100644 --- a/src/merge.c +++ b/src/merge.c @@ -1902,8 +1902,10 @@ static int write_merge_msg( entries = git__calloc(heads_len, sizeof(struct merge_msg_entry)); GITERR_CHECK_ALLOC(entries); - if (git_vector_init(&matching, heads_len, NULL) < 0) + if (git_vector_init(&matching, heads_len, NULL) < 0) { + git__free(entries); return -1; + } for (i = 0; i < heads_len; i++) entries[i].merge_head = heads[i]; @@ -232,6 +232,7 @@ int git_odb__hashlink(git_oid *out, const char *path) link_data[size] = '\0'; if (read_len != (ssize_t)size) { giterr_set(GITERR_OS, "Failed to read symlink data for '%s'", path); + git__free(link_data); return -1; } diff --git a/src/pack-objects.c b/src/pack-objects.c index 500104c55..7f427e3bd 100644 --- a/src/pack-objects.c +++ b/src/pack-objects.c @@ -505,8 +505,10 @@ static git_pobject **compute_write_order(git_packbuilder *pb) /* * Mark objects that are at the tip of tags. */ - if (git_tag_foreach(pb->repo, &cb_tag_foreach, pb) < 0) + if (git_tag_foreach(pb->repo, &cb_tag_foreach, pb) < 0) { + git__free(wo); return NULL; + } /* * Give the objects in the original recency order until diff --git a/src/pack.c b/src/pack.c index 7ce7099e0..497db38e8 100644 --- a/src/pack.c +++ b/src/pack.c @@ -329,8 +329,10 @@ static int pack_index_open(struct git_pack_file *p) memcpy(idx_name, p->pack_name, base_len); memcpy(idx_name + base_len, ".idx", sizeof(".idx")); - if ((error = git_mutex_lock(&p->lock)) < 0) + if ((error = git_mutex_lock(&p->lock)) < 0) { + git__free(idx_name); return error; + } if (p->index_version == -1) error = pack_index_check(idx_name, p); diff --git a/src/remote.c b/src/remote.c index 0e8354a11..158f3e938 100644 --- a/src/remote.c +++ b/src/remote.c @@ -467,6 +467,12 @@ const char *git_remote_name(const git_remote *remote) return remote->name; } +git_repository *git_remote_owner(const git_remote *remote) +{ + assert(remote); + return remote->repo; +} + const char *git_remote_url(const git_remote *remote) { assert(remote); diff --git a/src/repository.c b/src/repository.c index bd7ef5476..99ac56ef9 100644 --- a/src/repository.c +++ b/src/repository.c @@ -1500,12 +1500,12 @@ int git_repository_is_empty(git_repository *repo) if (git_reference_lookup(&head, repo, GIT_HEAD_FILE) < 0) return -1; - if (!(error = git_reference_type(head) == GIT_REF_SYMBOLIC)) + if (!((error = git_reference_type(head)) == GIT_REF_SYMBOLIC)) goto cleanup; - if (!(error = strcmp( + if (!(error = (strcmp( git_reference_symbolic_target(head), - GIT_REFS_HEADS_DIR "master") == 0)) + GIT_REFS_HEADS_DIR "master") == 0))) goto cleanup; error = repo_contains_no_reference(repo); diff --git a/src/revparse.c b/src/revparse.c index bcfb0843f..d21f08b53 100644 --- a/src/revparse.c +++ b/src/revparse.c @@ -685,6 +685,8 @@ int revparse__ext( git_reference *reference = NULL; git_object *base_rev = NULL; + bool should_return_reference = true; + assert(object_out && reference_out && repo && spec); *object_out = NULL; @@ -693,6 +695,8 @@ int revparse__ext( while (spec[pos]) { switch (spec[pos]) { case '^': + should_return_reference = false; + if ((error = ensure_base_rev_loaded(&base_rev, &reference, spec, identifier_len, repo, false)) < 0) goto cleanup; @@ -725,6 +729,8 @@ int revparse__ext( { git_object *temp_object = NULL; + should_return_reference = false; + if ((error = extract_how_many(&n, spec, &pos)) < 0) goto cleanup; @@ -743,6 +749,8 @@ int revparse__ext( { git_object *temp_object = NULL; + should_return_reference = false; + if ((error = extract_path(&buf, spec, &pos)) < 0) goto cleanup; @@ -807,6 +815,11 @@ int revparse__ext( if ((error = ensure_base_rev_loaded(&base_rev, &reference, spec, identifier_len, repo, false)) < 0) goto cleanup; + if (!should_return_reference) { + git_reference_free(reference); + reference = NULL; + } + *object_out = base_rev; *reference_out = reference; *identifier_len_out = identifier_len; diff --git a/tests-clar/refs/revparse.c b/tests-clar/refs/revparse.c index 69d92745c..9657054de 100644 --- a/tests-clar/refs/revparse.c +++ b/tests-clar/refs/revparse.c @@ -738,4 +738,45 @@ void test_refs_revparse__ext_can_expand_short_reference_names(void) "master", "a65fedf39aefe402d3bb6e24df4d4f5fe4547750", "refs/heads/master"); + + test_object_and_ref( + "HEAD", + "a65fedf39aefe402d3bb6e24df4d4f5fe4547750", + "refs/heads/master"); + + test_object_and_ref( + "tags/test", + "b25fa35b38051e4ae45d4222e795f9df2e43f1d1", + "refs/tags/test"); +} + +void test_refs_revparse__ext_returns_NULL_reference_when_expression_points_at_a_revision(void) +{ + test_object_and_ref( + "HEAD~3", + "4a202b346bb0fb0db7eff3cffeb3c70babbd2045", + NULL); + + test_object_and_ref( + "HEAD~0", + "a65fedf39aefe402d3bb6e24df4d4f5fe4547750", + NULL); + + test_object_and_ref( + "HEAD^0", + "a65fedf39aefe402d3bb6e24df4d4f5fe4547750", + NULL); + + test_object_and_ref( + "@{-1}@{0}", + "a4a7dce85cf63874e984719f4fdd239f5145052f", + NULL); +} + +void test_refs_revparse__ext_returns_NULL_reference_when_expression_points_at_a_tree_content(void) +{ + test_object_and_ref( + "tags/test:readme.txt", + "0266163a49e280c4f5ed1e08facd36a2bd716bcf", + NULL); } |
