update-index/diff-index: use core.preloadindex to improve performance

'update-index --refresh' and 'diff-index' (without --cached) don't honor the core.preloadindex setting yet. Porcelain commands using these (such as git [svn] rebase) suffer from this, especially on Windows. Use read_cache_preload to improve performance. Additionally, in builtin/diff.c, don't preload index status if we don't access the working copy (--cached). Results with msysgit on WebKit repo (2GB in 200k files): | update-index | diff-index | rebase ----------------+--------------+------------+--------- msysgit-v1.8.0 | 9.157s | 10.536s | 42.791s + preloadindex | 9.157s | 10.536s | 28.725s + this patch | 2.329s | 2.752s | 15.152s + fscache [1] | 0.731s | 1.171s | 8.877s [1] https://github.com/kblees/git/tree/kb/fscache-v3 Thanks-to: Albert Krawczyk <pro-logic@optusnet.com.au> Signed-off-by: Karsten Blees <blees@dcon.de> Signed-off-by: Jeff King <peff@peff.net>

Karsten Blees committed Oct 30, 2012 at 10:50 UTC 7349afd20e3b0ce3da6f192f593390472acec9d3
3 files changed +15 -6
builtin/diff-index.c
+6 -2
@@ -41,9 +41,13 @@ int cmd_diff_index(int argc, const char **argv, const char *prefix)
41 if (rev.pending.nr != 1 ||
42 rev.max_count != -1 || rev.min_age != -1 || rev.max_age != -1)
43 usage(diff_cache_usage);
44 - if (!cached)
44 + if (!cached) {
45 setup_work_tree();
46 - if (read_cache() < 0) {
46 + if (read_cache_preload(rev.diffopt.pathspec.raw) < 0) {
47 + perror("read_cache_preload");
48 + return -1;
49 + }
50 + } else if (read_cache() < 0) {
51 perror("read_cache");
52 return -1;
53 }
builtin/diff.c
+8 -4
@@ -130,8 +130,6 @@ static int builtin_diff_index(struct rev_info *revs,
130 usage(builtin_diff_usage);
131 argv++; argc--;
132 }
133 - if (!cached)
134 - setup_work_tree();
133 /*
134 * Make sure there is one revision (i.e. pending object),
135 * and there is no revision filtering parameters.
@@ -140,8 +138,14 @@ static int builtin_diff_index(struct rev_info *revs,
138 revs->max_count != -1 || revs->min_age != -1 ||
139 revs->max_age != -1)
140 usage(builtin_diff_usage);
143 - if (read_cache_preload(revs->diffopt.pathspec.raw) < 0) {
144 - perror("read_cache_preload");
141 + if (!cached) {
142 + setup_work_tree();
143 + if (read_cache_preload(revs->diffopt.pathspec.raw) < 0) {
144 + perror("read_cache_preload");
145 + return -1;
146 + }
147 + } else if (read_cache() < 0) {
148 + perror("read_cache");
149 return -1;
150 }
151 return run_diff_index(revs, cached);
builtin/update-index.c
+1
@@ -593,6 +593,7 @@ struct refresh_params {
593 static int refresh(struct refresh_params *o, unsigned int flag)
594 {
595 setup_work_tree();
596 + read_cache_preload(NULL);
597 *o->has_errors |= refresh_cache(o->flags | flag);
598 return 0;
599 }