Skip to content

Commit d265ddc

Browse files
committed
Merge branch 'jc/maint-read-tree-multi' into maint
* jc/maint-read-tree-multi: checkout branch: prime cache-tree fully read-tree -m A B: prime cache-tree from the switched-to tree Move prime_cache_tree() to cache-tree.c read-tree A B: do not corrupt cache-tree
2 parents c2eae0a + 83ae209 commit d265ddc

File tree

4 files changed

+55
-41
lines changed

4 files changed

+55
-41
lines changed

builtin-checkout.c

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
#include "commit.h"
66
#include "tree.h"
77
#include "tree-walk.h"
8+
#include "cache-tree.h"
89
#include "unpack-trees.h"
910
#include "dir.h"
1011
#include "run-command.h"
@@ -367,14 +368,17 @@ static int merge_working_tree(struct checkout_opts *opts,
367368
int ret;
368369
struct lock_file *lock_file = xcalloc(1, sizeof(struct lock_file));
369370
int newfd = hold_locked_index(lock_file, 1);
371+
int reprime_cache_tree = 0;
370372

371373
if (read_cache() < 0)
372374
return error("corrupt index file");
373375

376+
cache_tree_free(&active_cache_tree);
374377
if (opts->force) {
375378
ret = reset_tree(new->commit->tree, opts, 1);
376379
if (ret)
377380
return ret;
381+
reprime_cache_tree = 1;
378382
} else {
379383
struct tree_desc trees[2];
380384
struct tree *tree;
@@ -410,7 +414,9 @@ static int merge_working_tree(struct checkout_opts *opts,
410414
init_tree_desc(&trees[1], tree->buffer, tree->size);
411415

412416
ret = unpack_trees(2, trees, &topts);
413-
if (ret == -1) {
417+
if (ret != -1) {
418+
reprime_cache_tree = 1;
419+
} else {
414420
/*
415421
* Unpack couldn't do a trivial merge; either
416422
* give up or do a real merge, depending on
@@ -454,6 +460,8 @@ static int merge_working_tree(struct checkout_opts *opts,
454460
}
455461
}
456462

463+
if (reprime_cache_tree)
464+
prime_cache_tree(&active_cache_tree, new->commit->tree);
457465
if (write_cache(newfd, active_cache, active_nr) ||
458466
commit_locked_index(lock_file))
459467
die("unable to write new index file");

builtin-read-tree.c

Lines changed: 8 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -29,41 +29,6 @@ static int list_tree(unsigned char *sha1)
2929
return 0;
3030
}
3131

32-
static void prime_cache_tree_rec(struct cache_tree *it, struct tree *tree)
33-
{
34-
struct tree_desc desc;
35-
struct name_entry entry;
36-
int cnt;
37-
38-
hashcpy(it->sha1, tree->object.sha1);
39-
init_tree_desc(&desc, tree->buffer, tree->size);
40-
cnt = 0;
41-
while (tree_entry(&desc, &entry)) {
42-
if (!S_ISDIR(entry.mode))
43-
cnt++;
44-
else {
45-
struct cache_tree_sub *sub;
46-
struct tree *subtree = lookup_tree(entry.sha1);
47-
if (!subtree->object.parsed)
48-
parse_tree(subtree);
49-
sub = cache_tree_sub(it, entry.path);
50-
sub->cache_tree = cache_tree();
51-
prime_cache_tree_rec(sub->cache_tree, subtree);
52-
cnt += sub->cache_tree->entry_count;
53-
}
54-
}
55-
it->entry_count = cnt;
56-
}
57-
58-
static void prime_cache_tree(void)
59-
{
60-
if (!nr_trees)
61-
return;
62-
active_cache_tree = cache_tree();
63-
prime_cache_tree_rec(active_cache_tree, trees[0]);
64-
65-
}
66-
6732
static const char read_tree_usage[] = "git read-tree (<sha> | [[-m [--trivial] [--aggressive] | --reset | --prefix=<prefix>] [-u | -i]] [--exclude-per-directory=<gitignore>] [--index-output=<file>] <sha1> [<sha2> [<sha3>]])";
6833

6934
static struct lock_file lock_file;
@@ -211,7 +176,6 @@ int cmd_read_tree(int argc, const char **argv, const char *unused_prefix)
211176
case 3:
212177
default:
213178
opts.fn = threeway_merge;
214-
cache_tree_free(&active_cache_tree);
215179
break;
216180
}
217181

@@ -221,6 +185,7 @@ int cmd_read_tree(int argc, const char **argv, const char *unused_prefix)
221185
opts.head_idx = 1;
222186
}
223187

188+
cache_tree_free(&active_cache_tree);
224189
for (i = 0; i < nr_trees; i++) {
225190
struct tree *tree = trees[i];
226191
parse_tree(tree);
@@ -234,11 +199,14 @@ int cmd_read_tree(int argc, const char **argv, const char *unused_prefix)
234199
* "-m ent" or "--reset ent" form), we can obtain a fully
235200
* valid cache-tree because the index must match exactly
236201
* what came from the tree.
202+
*
203+
* The same holds true if we are switching between two trees
204+
* using read-tree -m A B. The index must match B after that.
237205
*/
238-
if (nr_trees && !opts.prefix && (!opts.merge || (stage == 2))) {
239-
cache_tree_free(&active_cache_tree);
240-
prime_cache_tree();
241-
}
206+
if (nr_trees == 1 && !opts.prefix)
207+
prime_cache_tree(&active_cache_tree, trees[0]);
208+
else if (nr_trees == 2 && opts.merge)
209+
prime_cache_tree(&active_cache_tree, trees[1]);
242210

243211
if (write_cache(newfd, active_cache, active_nr) ||
244212
commit_locked_index(&lock_file))

cache-tree.c

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
#include "cache.h"
22
#include "tree.h"
3+
#include "tree-walk.h"
34
#include "cache-tree.h"
45

56
#ifndef DEBUG
@@ -591,3 +592,36 @@ int write_cache_as_tree(unsigned char *sha1, int missing_ok, const char *prefix)
591592

592593
return 0;
593594
}
595+
596+
static void prime_cache_tree_rec(struct cache_tree *it, struct tree *tree)
597+
{
598+
struct tree_desc desc;
599+
struct name_entry entry;
600+
int cnt;
601+
602+
hashcpy(it->sha1, tree->object.sha1);
603+
init_tree_desc(&desc, tree->buffer, tree->size);
604+
cnt = 0;
605+
while (tree_entry(&desc, &entry)) {
606+
if (!S_ISDIR(entry.mode))
607+
cnt++;
608+
else {
609+
struct cache_tree_sub *sub;
610+
struct tree *subtree = lookup_tree(entry.sha1);
611+
if (!subtree->object.parsed)
612+
parse_tree(subtree);
613+
sub = cache_tree_sub(it, entry.path);
614+
sub->cache_tree = cache_tree();
615+
prime_cache_tree_rec(sub->cache_tree, subtree);
616+
cnt += sub->cache_tree->entry_count;
617+
}
618+
}
619+
it->entry_count = cnt;
620+
}
621+
622+
void prime_cache_tree(struct cache_tree **it, struct tree *tree)
623+
{
624+
cache_tree_free(it);
625+
*it = cache_tree();
626+
prime_cache_tree_rec(*it, tree);
627+
}

cache-tree.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
#ifndef CACHE_TREE_H
22
#define CACHE_TREE_H
33

4+
#include "tree.h"
5+
46
struct cache_tree;
57
struct cache_tree_sub {
68
struct cache_tree *cache_tree;
@@ -33,4 +35,6 @@ int cache_tree_update(struct cache_tree *, struct cache_entry **, int, int, int)
3335
#define WRITE_TREE_PREFIX_ERROR (-3)
3436

3537
int write_cache_as_tree(unsigned char *sha1, int missing_ok, const char *prefix);
38+
void prime_cache_tree(struct cache_tree **, struct tree *);
39+
3640
#endif

0 commit comments

Comments
 (0)