git.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: Elijah Newren <newren@gmail.com>
To: git@vger.kernel.org
Cc: Elijah Newren <newren@gmail.com>
Subject: [RFC PATCH] tree.c: Nuke match_tree_entry(), it just duplicates tree_entry_interesting()
Date: Mon,  6 Sep 2010 19:53:39 -0600	[thread overview]
Message-ID: <1283824419-21730-1-git-send-email-newren@gmail.com> (raw)

WARNING: RFC because: This has a minor conflict with my sparse-clone
series, and a less minor conflict with Nguyễn Thái Ngọc Duy's updates to
the en/object-list-with-pathspec series.  Duy's changes to
en/object-list-with-pathspec, at least with my additional suggestions,
should probably also be applied to en/tree-walk-optim for
skip_uninteresting.  If all that other stuff is done, this particular patch
could be made smaller and we could nuke the FIXME.  That'd make it into a
simple code cleanup.  I'm sending right now for comments, before I forget
about this simple cleanup.

I'll clean up and resend once Duy is done with his changes.

---
 tree-diff.c |    2 +-
 tree-walk.h |    3 ++
 tree.c      |   77 ++++++++++++++++++----------------------------------------
 3 files changed, 28 insertions(+), 54 deletions(-)

diff --git a/tree-diff.c b/tree-diff.c
index cd659c6..2fb670b 100644
--- a/tree-diff.c
+++ b/tree-diff.c
@@ -91,7 +91,7 @@ static int compare_tree_entry(struct tree_desc *t1, struct tree_desc *t2, const
  *  - zero for no
  *  - negative for "no, and no subsequent entries will be either"
  */
-static int tree_entry_interesting(struct tree_desc *desc, const char *base, int baselen, struct diff_options *opt)
+int tree_entry_interesting(struct tree_desc *desc, const char *base, int baselen, struct diff_options *opt)
 {
 	const char *path;
 	const unsigned char *sha1;
diff --git a/tree-walk.h b/tree-walk.h
index 7e3e0b5..e3e0137 100644
--- a/tree-walk.h
+++ b/tree-walk.h
@@ -60,4 +60,7 @@ static inline int traverse_path_len(const struct traverse_info *info, const stru
 	return info->pathlen + tree_entry_len(n->path, n->sha1);
 }
 
+struct diff_options;
+extern int tree_entry_interesting(struct tree_desc *desc, const char *base, int baselen, struct diff_options *opt);
+
 #endif
diff --git a/tree.c b/tree.c
index 5ab90af..405f56b 100644
--- a/tree.c
+++ b/tree.c
@@ -5,6 +5,13 @@
 #include "commit.h"
 #include "tag.h"
 #include "tree-walk.h"
+/*
+ * FIXME: Shouldn't need diff.h, but need it now for skip_uninteresting and
+ * diff_options; Nguyen's pending update to en/object-list-with-pathspec may
+ * fix this need, if coupled with my suggestion and a similar fix for
+ * skip_uninteresting...
+ */
+#include "diff.h"
 
 const char *tree_type = "tree";
 
@@ -45,71 +52,35 @@ static int read_one_entry_quick(const unsigned char *sha1, const char *base, int
 				  ADD_CACHE_JUST_APPEND);
 }
 
-static int match_tree_entry(const char *base, int baselen, const char *path, unsigned int mode, const char **paths)
-{
-	const char *match;
-	int pathlen;
-
-	if (!paths)
-		return 1;
-	pathlen = strlen(path);
-	while ((match = *paths++) != NULL) {
-		int matchlen = strlen(match);
-
-		if (baselen >= matchlen) {
-			/* If it doesn't match, move along... */
-			if (strncmp(base, match, matchlen))
-				continue;
-			/* pathspecs match only at the directory boundaries */
-			if (!matchlen ||
-			    baselen == matchlen ||
-			    base[matchlen] == '/' ||
-			    match[matchlen - 1] == '/')
-				return 1;
-			continue;
-		}
-
-		/* Does the base match? */
-		if (strncmp(base, match, baselen))
-			continue;
-
-		match += baselen;
-		matchlen -= baselen;
-
-		if (pathlen > matchlen)
-			continue;
-
-		if (matchlen > pathlen) {
-			if (match[pathlen] != '/')
-				continue;
-			if (!S_ISDIR(mode))
-				continue;
-		}
-
-		if (strncmp(path, match, pathlen))
-			continue;
-
-		return 1;
-	}
-	return 0;
-}
-
 int read_tree_recursive(struct tree *tree,
 			const char *base, int baselen,
 			int stage, const char **match,
 			read_tree_fn_t fn, void *context)
 {
 	struct tree_desc desc;
-	struct name_entry entry;
+	struct diff_options diff_opts;
+	int all_interesting;
 
 	if (parse_tree(tree))
 		return -1;
 
+	diff_tree_setup_paths(match, &diff_opts);
+	all_interesting = diff_opts.nr_paths == 0;
+
 	init_tree_desc(&desc, tree->buffer, tree->size);
 
-	while (tree_entry(&desc, &entry)) {
-		if (!match_tree_entry(base, baselen, entry.path, entry.mode, match))
-			continue;
+	for (; desc.size; update_tree_entry(&desc)) {
+		struct name_entry entry;
+		if (!all_interesting) {
+			int show = tree_entry_interesting(&desc, base, baselen, &diff_opts);
+			if (show < 0)
+				return 0;
+			else if (!show)
+				continue;
+			else if (show == 2)
+				all_interesting = 1;
+		}
+		entry = desc.entry;
 
 		switch (fn(entry.sha1, base, baselen, entry.path, entry.mode, stage, context)) {
 		case 0:
-- 
1.7.3.rc0.1.g43ab

                 reply	other threads:[~2010-09-07  1:52 UTC|newest]

Thread overview: [no followups] expand[flat|nested]  mbox.gz  Atom feed

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=1283824419-21730-1-git-send-email-newren@gmail.com \
    --to=newren@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).