git.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: "Nguyễn Thái Ngọc Duy" <pclouds@gmail.com>
To: git@vger.kernel.org
Cc: "Nguyễn Thái Ngọc Duy" <pclouds@gmail.com>
Subject: [PATCH 1/5] tree-walk: support negative pathspec
Date: Thu, 10 Mar 2011 10:13:35 +0700	[thread overview]
Message-ID: <1299726819-5576-2-git-send-email-pclouds@gmail.com> (raw)
In-Reply-To: <1299726819-5576-1-git-send-email-pclouds@gmail.com>

While the UI will be simple, where negative pathspecs are always
appended in the end, this could should be able to handle a mixed set
of negative and positive pathspecs (ie. overlapping must be handled
correctly).

Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com>
---
 cache.h     |    1 +
 tree-walk.c |   37 ++++++++++++++++++++++++++++---------
 2 files changed, 29 insertions(+), 9 deletions(-)

diff --git a/cache.h b/cache.h
index 08a9022..2189366 100644
--- a/cache.h
+++ b/cache.h
@@ -510,6 +510,7 @@ struct pathspec {
 		const char *match;
 		int len;
 		int has_wildcard:1;
+		int to_exclude:1;
 	} *items;
 };
 
diff --git a/tree-walk.c b/tree-walk.c
index 322becc..acbee1b 100644
--- a/tree-walk.c
+++ b/tree-walk.c
@@ -560,6 +560,7 @@ int tree_entry_interesting(const struct name_entry *entry,
 	int i;
 	int pathlen, baselen = base->len - base_offset;
 	int never_interesting = ps->has_wildcard ? 0 : -1;
+	int all_interesting_ok = !ps->recursive || ps->max_depth == -1;
 
 	if (!ps->nr) {
 		if (!ps->recursive || ps->max_depth == -1)
@@ -569,6 +570,19 @@ int tree_entry_interesting(const struct name_entry *entry,
 				      ps->max_depth);
 	}
 
+	/*
+	 * TODO: add prepare_pathspec() to scan for pathspecs
+	 * overlapped with negative ones. The ones that do not overlap
+	 * can still return 2.
+	 */
+	for (i = 0; i < ps->nr; i++) {
+		const struct pathspec_item *item = ps->items+i;
+		if (item->to_exclude) {
+			all_interesting_ok = 0;
+			break;
+		}
+	}
+
 	pathlen = tree_entry_len(entry->path, entry->sha1);
 
 	for (i = ps->nr - 1; i >= 0; i--) {
@@ -578,17 +592,22 @@ int tree_entry_interesting(const struct name_entry *entry,
 		int matchlen = item->len;
 
 		if (baselen >= matchlen) {
+			int ret;
+
 			/* If it doesn't match, move along... */
 			if (!match_dir_prefix(base_str, baselen, match, matchlen))
 				goto match_wildcards;
 
-			if (!ps->recursive || ps->max_depth == -1)
+			if (all_interesting_ok)
 				return 2;
 
-			return !!within_depth(base_str + matchlen + 1,
-					      baselen - matchlen - 1,
-					      !!S_ISDIR(entry->mode),
-					      ps->max_depth);
+			ret = !!within_depth(base_str + matchlen + 1,
+					     baselen - matchlen - 1,
+					     !!S_ISDIR(entry->mode),
+					     ps->max_depth);
+			if (item->to_exclude)
+				ret = !ret;
+			return ret;
 		}
 
 		/* Does the base match? */
@@ -596,18 +615,18 @@ int tree_entry_interesting(const struct name_entry *entry,
 			if (match_entry(entry, pathlen,
 					match + baselen, matchlen - baselen,
 					&never_interesting))
-				return 1;
+				return item->to_exclude ? 0 : 1;
 
 			if (ps->items[i].has_wildcard) {
 				if (!fnmatch(match + baselen, entry->path, 0))
-					return 1;
+					return item->to_exclude ? 0 : 1;
 
 				/*
 				 * Match all directories. We'll try to
 				 * match files later on.
 				 */
 				if (ps->recursive && S_ISDIR(entry->mode))
-					return 1;
+					return item->to_exclude ? 0 : 1;
 			}
 
 			continue;
@@ -626,7 +645,7 @@ match_wildcards:
 
 		if (!fnmatch(match, base->buf + base_offset, 0)) {
 			strbuf_setlen(base, base_offset + baselen);
-			return 1;
+			return item->to_exclude ? 0 : 1;
 		}
 		strbuf_setlen(base, base_offset + baselen);
 
-- 
1.7.3.1.256.g2539c.dirty

  reply	other threads:[~2011-03-10  3:15 UTC|newest]

Thread overview: 20+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2011-03-10  3:13 [WIP PATCH 0/5] support --exclude for diff/log commands Nguyễn Thái Ngọc Duy
2011-03-10  3:13 ` Nguyễn Thái Ngọc Duy [this message]
2011-03-10  3:13 ` [PATCH 2/5] match_pathspec_depth: support negative pathspec Nguyễn Thái Ngọc Duy
2011-03-10  3:13 ` [PATCH 3/5] revision.c: get rid of struct rev_info.prune_data Nguyễn Thái Ngọc Duy
2011-03-10  6:20   ` Junio C Hamano
2011-03-10  6:52     ` Nguyen Thai Ngoc Duy
2011-03-10  3:13 ` [PATCH 4/5] diff: refactor init/release API Nguyễn Thái Ngọc Duy
2011-03-10  3:13 ` [PATCH 5/5] diff: support --exclude Nguyễn Thái Ngọc Duy
2011-03-10  6:11 ` [WIP PATCH 0/5] support --exclude for diff/log commands Junio C Hamano
2011-03-10  7:03   ` Nguyen Thai Ngoc Duy
2011-03-10  8:41   ` Junio C Hamano
2011-03-10 10:05     ` Nguyen Thai Ngoc Duy
2011-03-21  4:02       ` Nguyen Thai Ngoc Duy
2011-03-21  9:45         ` Michael J Gruber
2011-03-21 10:02           ` Nguyen Thai Ngoc Duy
2011-03-22 23:59           ` Junio C Hamano
2011-03-23 12:10             ` Nguyen Thai Ngoc Duy
2011-03-23 12:18               ` Nguyen Thai Ngoc Duy
2011-03-23 12:51               ` Michael J Gruber
2011-03-23 13:34                 ` Nguyen Thai Ngoc Duy

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=1299726819-5576-2-git-send-email-pclouds@gmail.com \
    --to=pclouds@gmail.com \
    --cc=git@vger.kernel.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).