Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@xxxxxxxxx> --- builtin/add.c | 46 ++++++++++++--------------- dir.c | 100 ---------------------------------------------------------- dir.h | 1 - 3 files changed, 20 insertions(+), 127 deletions(-) diff --git a/builtin/add.c b/builtin/add.c index 89ae67d..9edab95 100644 --- a/builtin/add.c +++ b/builtin/add.c @@ -99,7 +99,7 @@ int add_files_to_cache(const char *prefix, return !!data.add_errors; } -static void fill_pathspec_matches(const char **pathspec, char *seen, int specs) +static void fill_pathspec_matches(struct pathspec *pathspec, char *seen) { int num_unmatched = 0, i; @@ -109,49 +109,43 @@ static void fill_pathspec_matches(const char **pathspec, char *seen, int specs) * mistakenly think that the user gave a pathspec that did not match * anything. */ - for (i = 0; i < specs; i++) + for (i = 0; i < pathspec->nr; i++) if (!seen[i]) num_unmatched++; if (!num_unmatched) return; for (i = 0; i < active_nr; i++) { struct cache_entry *ce = active_cache[i]; - match_pathspec(pathspec, ce->name, ce_namelen(ce), 0, seen); + match_pathspec_depth(pathspec, ce->name, ce_namelen(ce), 0, seen); } } -static char *find_used_pathspec(const char **pathspec) +static char *find_used_pathspec(struct pathspec *pathspec) { char *seen; - int i; - - for (i = 0; pathspec[i]; i++) - ; /* just counting */ - seen = xcalloc(i, 1); - fill_pathspec_matches(pathspec, seen, i); + seen = xcalloc(pathspec->nr, 1); + fill_pathspec_matches(pathspec, seen); return seen; } -static char *prune_directory(struct dir_struct *dir, const char **pathspec, int prefix) +static char *prune_directory(struct dir_struct *dir, struct pathspec *pathspec, int prefix) { char *seen; - int i, specs; + int i; struct dir_entry **src, **dst; - for (specs = 0; pathspec[specs]; specs++) - /* nothing */; - seen = xcalloc(specs, 1); + seen = xcalloc(pathspec->nr, 1); src = dst = dir->entries; i = dir->nr; while (--i >= 0) { struct dir_entry *entry = *src++; - if (match_pathspec(pathspec, entry->name, entry->len, - prefix, seen)) + if (match_pathspec_depth(pathspec, entry->name, entry->len, + prefix, seen)) *dst++ = entry; } dir->nr = dst - dir->entries; - fill_pathspec_matches(pathspec, seen, specs); + fill_pathspec_matches(pathspec, seen); return seen; } @@ -401,7 +395,7 @@ int cmd_add(int argc, const char **argv, const char *prefix) /* This picks up the paths that are not tracked */ baselen = fill_directory(&dir, &pathspec); if (pathspec.nr) - seen = prune_directory(&dir, pathspec.raw, baselen); + seen = prune_directory(&dir, &pathspec, baselen); } if (refresh_only) { @@ -415,23 +409,23 @@ int cmd_add(int argc, const char **argv, const char *prefix) path_exclude_check_init(&check, &dir); if (!seen) - seen = find_used_pathspec(pathspec.raw); + seen = find_used_pathspec(&pathspec); /* * file_exists() assumes exact match */ GUARD_PATHSPEC(&pathspec, PATHSPEC_FROMTOP); - for (i = 0; pathspec.raw[i]; i++) { - if (!seen[i] && pathspec.raw[i][0] - && !file_exists(pathspec.raw[i])) { + for (i = 0; i < pathspec.nr; i++) { + const char *path = pathspec.items[i].match; + if (!seen[i] && !file_exists(path)) { if (ignore_missing) { int dtype = DT_UNKNOWN; - if (is_path_excluded(&check, pathspec.raw[i], -1, &dtype)) - dir_add_ignored(&dir, pathspec.raw[i], strlen(pathspec.raw[i])); + if (is_path_excluded(&check, path, -1, &dtype)) + dir_add_ignored(&dir, path, pathspec.items[i].len); } else die(_("pathspec '%s' did not match any files"), - pathspec.raw[i]); + pathspec.items[i].original); } } free(seen); diff --git a/dir.c b/dir.c index 76b267e..2a1bcb8 100644 --- a/dir.c +++ b/dir.c @@ -139,106 +139,6 @@ int within_depth(const char *name, int namelen, * * It returns 0 when there is no match. */ -static int match_one(const char *match, const char *name, int namelen) -{ - int matchlen; - int literal = limit_pathspec_to_literal(); - - /* If the match was just the prefix, we matched */ - if (!*match) - return MATCHED_RECURSIVELY; - - if (ignore_case) { - for (;;) { - unsigned char c1 = tolower(*match); - unsigned char c2 = tolower(*name); - if (c1 == '\0' || (!literal && is_glob_special(c1))) - break; - if (c1 != c2) - return 0; - match++; - name++; - namelen--; - } - } else { - for (;;) { - unsigned char c1 = *match; - unsigned char c2 = *name; - if (c1 == '\0' || (!literal && is_glob_special(c1))) - break; - if (c1 != c2) - return 0; - match++; - name++; - namelen--; - } - } - - /* - * If we don't match the matchstring exactly, - * we need to match by fnmatch - */ - matchlen = strlen(match); - if (strncmp_icase(match, name, matchlen)) { - if (literal) - return 0; - return !fnmatch_icase(match, name, 0) ? MATCHED_FNMATCH : 0; - } - - if (namelen == matchlen) - return MATCHED_EXACTLY; - if (match[matchlen-1] == '/' || name[matchlen] == '/') - return MATCHED_RECURSIVELY; - return 0; -} - -/* - * Given a name and a list of pathspecs, see if the name matches - * any of the pathspecs. The caller is also interested in seeing - * all pathspec matches some names it calls this function with - * (otherwise the user could have mistyped the unmatched pathspec), - * and a mark is left in seen[] array for pathspec element that - * actually matched anything. - */ -int match_pathspec(const char **pathspec, const char *name, int namelen, - int prefix, char *seen) -{ - int i, retval = 0; - - if (!pathspec) - return 1; - - name += prefix; - namelen -= prefix; - - for (i = 0; pathspec[i] != NULL; i++) { - int how; - const char *match = pathspec[i] + prefix; - if (seen && seen[i] == MATCHED_EXACTLY) - continue; - how = match_one(match, name, namelen); - if (how) { - if (retval < how) - retval = how; - if (seen && seen[i] < how) - seen[i] = how; - } - } - return retval; -} - -/* - * Does 'match' match the given name? - * A match is found if - * - * (1) the 'match' string is leading directory of 'name', or - * (2) the 'match' string is a wildcard and matches 'name', or - * (3) the 'match' string is exactly the same as 'name'. - * - * and the return value tells which case it was. - * - * It returns 0 when there is no match. - */ static int match_pathspec_item(const struct pathspec_item *item, int prefix, const char *name, int namelen) { diff --git a/dir.h b/dir.h index ff5ada5..a03af80 100644 --- a/dir.h +++ b/dir.h @@ -91,7 +91,6 @@ struct dir_struct { extern int simple_length(const char *match); extern int no_wildcard(const char *string); extern char *common_prefix(const struct pathspec *pathspec); -extern int match_pathspec(const char **pathspec, const char *name, int namelen, int prefix, char *seen); extern int match_pathspec_depth(const struct pathspec *pathspec, const char *name, int namelen, int prefix, char *seen); -- 1.8.0.rc2.23.g1fb49df -- To unsubscribe from this list: send the line "unsubscribe git" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html