[PATCH 15/22] replace cache_name_pos
- From
- Chuck Lever <cel@netapp.com>
- Date
- Sep 12, 2005, 14:56 UTC
- Message-ID
- <20050912145616.28120.30912.stgit@dexter.citi.umich.edu>
- In-Reply-To
- <20050912145543.28120.7086.stgit@dexter.citi.umich.edu>
Clean up: Introduce an interface to return a cache_cursor instead of an integer. Note we can also eliminate the need to overload the return value of cache_name_pos to return a negative "pos" value to signal an insertion point rather than a found entry.
Signed-off-by: Chuck Lever <cel@netapp.com> ---
cache.h | 13 +++++++++++++ read-cache.c | 44 ++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 57 insertions(+), 0 deletions(-)
diff --git a/cache.h b/cache.h --- a/cache.h +++ b/cache.h @@ -160,6 +160,8 @@ extern int read_cache(void); extern int read_cache_unmerged(void); extern int write_cache(int newfd); extern int cache_name_pos(const char *name, int namelen); +extern int cache_find_name(const char *name, int namelen, struct cache_cursor *cc); + #define ADD_CACHE_OK_TO_ADD 1 /* Ok to add */ #define ADD_CACHE_OK_TO_REPLACE 2 /* Ok to replace file/directory */ #define ADD_CACHE_SKIP_DFCHECK 4 /* Ok to skip DF conflict checks */ @@ -350,6 +352,17 @@ static inline int walk_cache(cache_itera return 0; } +static inline int cache_find_entry(const char *name, int namelen, struct cache_entry **ce) +{ + struct cache_cursor cc; + int result; + + result = cache_find_name(name, namelen, &cc); + if (ce) + *ce = active_cache[cc.pos]; + return result; +} + struct checkout { const char *base_dir; int base_dir_len; diff --git a/read-cache.c b/read-cache.c --- a/read-cache.c +++ b/read-cache.c @@ -144,6 +144,50 @@ int cache_name_pos(const char *name, int return -first-1; } +/* + * Given a name, find the first cache entry that matches. Returning 1 + * means the cursor points to the cache entry with a matching name. + * Returning 0 means the name wasn't found, but the cursor points to an + * appropriate insertion point. + */ +int cache_find_name(const char *name, int namelen, struct cache_cursor *cc) +{ + int first, last; + + /* + * Look for the right name + */ + cc->pos = first = 0; + last = active_nr; + while (last > first) { + struct cache_entry *ce; + int cmp; + cc->pos = (last + first) >> 1; + ce = active_cache[cc->pos]; + cmp = cache_name_compare(name, namelen, ce->name, ntohs(ce->ce_flags)); + if (!cmp) { + /* found it */ + return 1; + } + if (cmp < 0) { + /* next: search [first, cc->pos] */ + last = cc->pos; + continue; + } + /* next: search [cc->pos + 1, last] */ + first = cc->pos + 1; + } + + /* + * Name not found, so return an insertion point. + * + * On return, callers insert *before* the insertion point, + * not after it, to maintain proper list order. + */ + cc->pos = first; + return 0; +} + /* Remove entry, return true if there are more entries to go.. */ int remove_cache_entry_at(int pos) {