diff options
author | Vicent Martà <vicent@github.com> | 2012-10-09 11:45:50 -0700 |
---|---|---|
committer | Vicent Martà <vicent@github.com> | 2012-10-09 11:45:50 -0700 |
commit | 21e0d297af95e49b933c2a8d09994a32011354b1 (patch) | |
tree | 1e248d6899feac797f0c1307ad7cf52cead42389 /src/diff.c | |
parent | aa4437f637371c531355029686cb5780fd99c988 (diff) | |
parent | 5d1308f25ff36d03f0a22451642cc0f2a931daae (diff) | |
download | libgit2-21e0d297af95e49b933c2a8d09994a32011354b1.tar.gz |
Merge pull request #967 from arrbee/diff-submodule-tests-and-fixes
Diff submodule tests and fixes
Diffstat (limited to 'src/diff.c')
-rw-r--r-- | src/diff.c | 59 |
1 files changed, 48 insertions, 11 deletions
diff --git a/src/diff.c b/src/diff.c index 7a0051ae3..8ab8af3a1 100644 --- a/src/diff.c +++ b/src/diff.c @@ -224,7 +224,10 @@ static int diff_delta__from_one( } delta->old_file.flags |= GIT_DIFF_FILE_VALID_OID; - delta->new_file.flags |= GIT_DIFF_FILE_VALID_OID; + + if (delta->status == GIT_DELTA_DELETED || + !git_oid_iszero(&delta->new_file.oid)) + delta->new_file.flags |= GIT_DIFF_FILE_VALID_OID; if (git_vector_insert(&diff->deltas, delta) < 0) { git__free(delta); @@ -441,17 +444,28 @@ static int oid_for_workdir_item( const git_index_entry *item, git_oid *oid) { - int result; + int result = 0; git_buf full_path = GIT_BUF_INIT; - if (git_buf_joinpath(&full_path, git_repository_workdir(repo), item->path) < 0) + if (git_buf_joinpath( + &full_path, git_repository_workdir(repo), item->path) < 0) return -1; - /* calculate OID for file if possible*/ + /* calculate OID for file if possible */ if (S_ISGITLINK(item->mode)) { - /* Don't bother to figure out an oid for a submodule. We won't use it anyway. */ - memset(oid, 0, sizeof(*oid)); - result = 0; + git_submodule *sm; + const git_oid *sm_oid; + + if (!git_submodule_lookup(&sm, repo, item->path) && + (sm_oid = git_submodule_wd_oid(sm)) != NULL) + git_oid_cpy(oid, sm_oid); + else { + /* if submodule lookup failed probably just in an intermediate + * state where some init hasn't happened, so ignore the error + */ + giterr_clear(); + memset(oid, 0, sizeof(*oid)); + } } else if (S_ISLNK(item->mode)) result = git_odb__hashlink(oid, full_path.ptr); else if (!git__is_sizet(item->file_size)) { @@ -570,6 +584,15 @@ static int maybe_modified( return -1; status = GIT_SUBMODULE_STATUS_IS_UNMODIFIED(sm_status) ? GIT_DELTA_UNMODIFIED : GIT_DELTA_MODIFIED; + + /* grab OID while we are here */ + if (git_oid_iszero(&nitem->oid)) { + const git_oid *sm_oid = git_submodule_wd_oid(sub); + if (sub != NULL) { + git_oid_cpy(&noid, sm_oid); + use_noid = &noid; + } + } } } } @@ -669,7 +692,8 @@ static int diff_from_iterators( /* check if contained in ignored parent directory */ if (git_buf_len(&ignore_prefix) && - ITERATOR_PREFIXCMP(*old_iter, nitem->path, git_buf_cstr(&ignore_prefix)) == 0) + ITERATOR_PREFIXCMP(*old_iter, nitem->path, + git_buf_cstr(&ignore_prefix)) == 0) delta_type = GIT_DELTA_IGNORED; if (S_ISDIR(nitem->mode)) { @@ -677,10 +701,23 @@ static int diff_from_iterators( * it or if the user requested the contents of untracked * directories and it is not under an ignored directory. */ - if ((oitem && ITERATOR_PREFIXCMP(*old_iter, oitem->path, nitem->path) == 0) || + bool contains_tracked = + (oitem && + !ITERATOR_PREFIXCMP(*old_iter, oitem->path, nitem->path)); + bool recurse_untracked = (delta_type == GIT_DELTA_UNTRACKED && - (diff->opts.flags & GIT_DIFF_RECURSE_UNTRACKED_DIRS) != 0)) - { + (diff->opts.flags & GIT_DIFF_RECURSE_UNTRACKED_DIRS) != 0); + + /* do not advance into directories that contain a .git file */ + if (!contains_tracked && recurse_untracked) { + git_buf *full = NULL; + if (git_iterator_current_workdir_path(new_iter, &full) < 0) + goto fail; + if (git_path_contains_dir(full, DOT_GIT)) + recurse_untracked = false; + } + + if (contains_tracked || recurse_untracked) { /* if this directory is ignored, remember it as the * "ignore_prefix" for processing contained items */ |