diff: wrap the iterator functions Wrap the iterator current / advance functions so that we can extend them, but also handle GIT_ITEROVER cases in the iterator funcs instead of the callers.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188
diff --git a/src/diff.c b/src/diff.c
index f7e1c8e..f829fb0 100644
--- a/src/diff.c
+++ b/src/diff.c
@@ -857,6 +857,64 @@ static bool entry_is_prefixed(
item->path[pathlen] == '/');
}
+static int iterator_current(
+ const git_index_entry **entry,
+ git_iterator *iterator)
+{
+ int error;
+
+ if ((error = git_iterator_current(entry, iterator)) == GIT_ITEROVER) {
+ *entry = NULL;
+ error = 0;
+ }
+
+ return error;
+}
+
+static int iterator_advance(
+ const git_index_entry **entry,
+ git_iterator *iterator)
+{
+ int error;
+
+ if ((error = git_iterator_advance(entry, iterator)) == GIT_ITEROVER) {
+ *entry = NULL;
+ error = 0;
+ }
+
+ return error;
+}
+
+static int iterator_advance_into(
+ const git_index_entry **entry,
+ git_iterator *iterator)
+{
+ int error;
+
+ if ((error = git_iterator_advance_into(entry, iterator)) == GIT_ITEROVER) {
+ *entry = NULL;
+ error = 0;
+ }
+
+ return error;
+}
+
+static int iterator_advance_over_with_status(
+ const git_index_entry **entry,
+ git_iterator_status_t *status,
+ git_iterator *iterator)
+{
+ int error;
+
+ if ((error = git_iterator_advance_over_with_status(
+ entry, status, iterator)) == GIT_ITEROVER) {
+ *entry = NULL;
+ error = 0;
+ }
+
+ return error;
+}
+
static int handle_unmatched_new_item(
git_diff *diff, diff_in_progress *info)
{
@@ -910,12 +968,11 @@ static int handle_unmatched_new_item(
/* if delta wasn't created (because of rules), just skip ahead */
last = diff_delta__last_for_item(diff, nitem);
if (!last)
- return git_iterator_advance(&info->nitem, info->new_iter);
+ return iterator_advance(&info->nitem, info->new_iter);
/* iterate into dir looking for an actual untracked file */
- if ((error = git_iterator_advance_over_with_status(
- &info->nitem, &untracked_state, info->new_iter)) < 0 &&
- error != GIT_ITEROVER)
+ if ((error = iterator_advance_over_with_status(
+ &info->nitem, &untracked_state, info->new_iter)) < 0)
return error;
/* if we found nothing or just ignored items, update the record */
@@ -935,7 +992,7 @@ static int handle_unmatched_new_item(
/* try to advance into directory if necessary */
if (recurse_into_dir) {
- error = git_iterator_advance_into(&info->nitem, info->new_iter);
+ error = iterator_advance_into(&info->nitem, info->new_iter);
/* if real error or no error, proceed with iteration */
if (error != GIT_ENOTFOUND)
@@ -946,7 +1003,7 @@ static int handle_unmatched_new_item(
* it or ignore it
*/
if (contains_oitem)
- return git_iterator_advance(&info->nitem, info->new_iter);
+ return iterator_advance(&info->nitem, info->new_iter);
delta_type = GIT_DELTA_IGNORED;
}
}
@@ -955,7 +1012,7 @@ static int handle_unmatched_new_item(
DIFF_FLAG_ISNT_SET(diff, GIT_DIFF_RECURSE_IGNORED_DIRS) &&
git_iterator_current_tree_is_ignored(info->new_iter))
/* item contained in ignored directory, so skip over it */
- return git_iterator_advance(&info->nitem, info->new_iter);
+ return iterator_advance(&info->nitem, info->new_iter);
else if (info->new_iter->type != GIT_ITERATOR_TYPE_WORKDIR)
delta_type = GIT_DELTA_ADDED;
@@ -968,12 +1025,12 @@ static int handle_unmatched_new_item(
/* if this contains a tracked item, treat as normal TREE */
if (contains_oitem) {
- error = git_iterator_advance_into(&info->nitem, info->new_iter);
+ error = iterator_advance_into(&info->nitem, info->new_iter);
if (error != GIT_ENOTFOUND)
return error;
giterr_clear();
- return git_iterator_advance(&info->nitem, info->new_iter);
+ return iterator_advance(&info->nitem, info->new_iter);
}
}
}
@@ -1004,7 +1061,7 @@ static int handle_unmatched_new_item(
}
}
- return git_iterator_advance(&info->nitem, info->new_iter);
+ return iterator_advance(&info->nitem, info->new_iter);
}
static int handle_unmatched_old_item(
@@ -1033,10 +1090,10 @@ static int handle_unmatched_old_item(
*/
if (S_ISDIR(info->nitem->mode) &&
DIFF_FLAG_ISNT_SET(diff, GIT_DIFF_RECURSE_UNTRACKED_DIRS))
- return git_iterator_advance(&info->nitem, info->new_iter);
+ return iterator_advance(&info->nitem, info->new_iter);
}
- return git_iterator_advance(&info->oitem, info->old_iter);
+ return iterator_advance(&info->oitem, info->old_iter);
}
static int handle_matched_item(
@@ -1047,9 +1104,8 @@ static int handle_matched_item(
if ((error = maybe_modified(diff, info)) < 0)
return error;
- if (!(error = git_iterator_advance(&info->oitem, info->old_iter)) ||
- error == GIT_ITEROVER)
- error = git_iterator_advance(&info->nitem, info->new_iter);
+ if (!(error = iterator_advance(&info->oitem, info->old_iter)))
+ error = iterator_advance(&info->nitem, info->new_iter);
return error;
}
@@ -1085,13 +1141,9 @@ int git_diff__from_iterators(
if ((error = diff_list_apply_options(diff, opts)) < 0)
goto cleanup;
- if ((error = git_iterator_current(&info.oitem, old_iter)) < 0 &&
- error != GIT_ITEROVER)
- goto cleanup;
- if ((error = git_iterator_current(&info.nitem, new_iter)) < 0 &&
- error != GIT_ITEROVER)
+ if ((error = iterator_current(&info.oitem, old_iter)) < 0 ||
+ (error = iterator_current(&info.nitem, new_iter)) < 0)
goto cleanup;
- error = 0;
/* run iterators building diffs */
while (!error && (info.oitem || info.nitem)) {
@@ -1113,10 +1165,6 @@ int git_diff__from_iterators(
*/
else
error = handle_matched_item(diff, &info);
-
- /* because we are iterating over two lists, ignore ITEROVER */
- if (error == GIT_ITEROVER)
- error = 0;
}
diff->perf.stat_calls += old_iter->stat_calls + new_iter->stat_calls;