Thread (43 messages) 43 messages, 4 authors, 2022-05-25
STALE1480d
Revisions (3)
  1. v1 [diff vs current]
  2. v2 [diff vs current]
  3. v3 current

[PATCH v3 05/10] cache-tree: implement cache_tree_find_path()

From: Derrick Stolee via GitGitGadget <hidden>
Date: 2022-05-23 13:49:14
Subsystem: the rest · Maintainer: Linus Torvalds

From: Derrick Stolee <redacted>

Given a 'struct cache_tree', it may be beneficial to navigate directly
to a node within that corresponds to a given path name. Create
cache_tree_find_path() for this function. It returns NULL when no such
path exists.

The implementation is adapted from do_invalidate_path() which does a
similar search but also modifies the nodes it finds along the way. The
method could be implemented simply using tail-recursion, but this while
loop does the same thing.

This new method is not currently used, but will be in an upcoming
change.

Helped-by: Junio C Hamano [off-list ref]
Signed-off-by: Derrick Stolee <redacted>
---
 cache-tree.c | 27 +++++++++++++++++++++++++++
 cache-tree.h |  2 ++
 2 files changed, 29 insertions(+)
diff --git a/cache-tree.c b/cache-tree.c
index 6752f69d515..f42db920d10 100644
--- a/cache-tree.c
+++ b/cache-tree.c
@@ -100,6 +100,33 @@ struct cache_tree_sub *cache_tree_sub(struct cache_tree *it, const char *path)
 	return find_subtree(it, path, pathlen, 1);
 }
 
+struct cache_tree *cache_tree_find_path(struct cache_tree *it, const char *path)
+{
+	const char *slash;
+	int namelen;
+	struct cache_tree_sub it_sub = {
+		.cache_tree = it,
+	};
+	struct cache_tree_sub *down = &it_sub;
+
+	while (down) {
+		slash = strchrnul(path, '/');
+		namelen = slash - path;
+		down->cache_tree->entry_count = -1;
+		if (!*slash) {
+			int pos;
+			pos = cache_tree_subtree_pos(down->cache_tree, path, namelen);
+			if (0 <= pos)
+				return down->cache_tree->down[pos]->cache_tree;
+			return NULL;
+		}
+		down = find_subtree(it, path, namelen, 0);
+		path = slash + 1;
+	}
+
+	return NULL;
+}
+
 static int do_invalidate_path(struct cache_tree *it, const char *path)
 {
 	/* a/b/c
diff --git a/cache-tree.h b/cache-tree.h
index 8efeccebfc9..f75f8e74dcd 100644
--- a/cache-tree.h
+++ b/cache-tree.h
@@ -29,6 +29,8 @@ struct cache_tree_sub *cache_tree_sub(struct cache_tree *, const char *);
 
 int cache_tree_subtree_pos(struct cache_tree *it, const char *path, int pathlen);
 
+struct cache_tree *cache_tree_find_path(struct cache_tree *it, const char *path);
+
 void cache_tree_write(struct strbuf *, struct cache_tree *root);
 struct cache_tree *cache_tree_read(const char *buffer, unsigned long size);
 
-- 
gitgitgadget
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help