fix overslow :/no-such-string-ever-existed diagnostics

"git cmd :/no-such-string-ever-existed" runs an extra round of get_sha1() since 009fee4 (Detailed diagnosis when parsing an object name fails., 2009-12-07). Once without error diagnosis to see there is no commit with such a string in the log message (hence "it cannot be a ref"), and after seeing that :/no-such-string-ever-existed is not a filename (hence "it cannot be a path, either"), another time to give "better diagnosis". The thing is, the second time it runs, we already know that traversing the history all the way down to the root will _not_ find any matching commit. Rename misguided "gently" parameter, which is turned off _only_ when the "detailed diagnosis" codepath knows that it cannot be a ref and making the call only for the caller to die with a message. Flip its meaning (and adjust the callers) and call it "only_to_die", which is not a great name, but it describes far more clearly what the codepaths that switches their behaviour based on this variable do. On my box, the command spends ~1.8 seconds without the patch to make the report; with the patch it spends ~1.12 seconds. Signed-off-by: Junio C Hamano <gitster@pobox.com>

Junio C Hamano committed May 10, 2011 at 12:02 UTC 2e83b66c32c1d482575fd8caed80680a2f69c5f1
3 files changed +14 -13
cache.h
+4 -4
@@ -785,15 +785,15 @@ struct object_context {
785 };
786
787 extern int get_sha1(const char *str, unsigned char *sha1);
788 -extern int get_sha1_with_mode_1(const char *str, unsigned char *sha1, unsigned *mode, int gently, const char *prefix);
788 +extern int get_sha1_with_mode_1(const char *str, unsigned char *sha1, unsigned *mode, int only_to_die, const char *prefix);
789 static inline int get_sha1_with_mode(const char *str, unsigned char *sha1, unsigned *mode)
790 {
791 - return get_sha1_with_mode_1(str, sha1, mode, 1, NULL);
791 + return get_sha1_with_mode_1(str, sha1, mode, 0, NULL);
792 }
793 -extern int get_sha1_with_context_1(const char *name, unsigned char *sha1, struct object_context *orc, int gently, const char *prefix);
793 +extern int get_sha1_with_context_1(const char *name, unsigned char *sha1, struct object_context *orc, int only_to_die, const char *prefix);
794 static inline int get_sha1_with_context(const char *str, unsigned char *sha1, struct object_context *orc)
795 {
796 - return get_sha1_with_context_1(str, sha1, orc, 1, NULL);
796 + return get_sha1_with_context_1(str, sha1, orc, 0, NULL);
797 }
798 extern int get_sha1_hex(const char *hex, unsigned char *sha1);
799 extern char *sha1_to_hex(const unsigned char *sha1); /* static buffer result! */
setup.c
+1 -1
@@ -86,7 +86,7 @@ static void NORETURN die_verify_filename(const char *prefix, const char *arg)
86 unsigned char sha1[20];
87 unsigned mode;
88 /* try a detailed diagnostic ... */
89 - get_sha1_with_mode_1(arg, sha1, &mode, 0, prefix);
89 + get_sha1_with_mode_1(arg, sha1, &mode, 1, prefix);
90 /* ... or fall back the most general message. */
91 die("ambiguous argument '%s': unknown revision or path not in the working tree.\n"
92 "Use '--' to separate paths from revisions", arg);
sha1_name.c
+9 -8
@@ -1080,11 +1080,12 @@ static void diagnose_invalid_index_path(int stage,
1080 }
1081
1082
1083 -int get_sha1_with_mode_1(const char *name, unsigned char *sha1, unsigned *mode, int gently, const char *prefix)
1083 +int get_sha1_with_mode_1(const char *name, unsigned char *sha1, unsigned *mode,
1084 + int only_to_die, const char *prefix)
1085 {
1086 struct object_context oc;
1087 int ret;
1087 - ret = get_sha1_with_context_1(name, sha1, &oc, gently, prefix);
1088 + ret = get_sha1_with_context_1(name, sha1, &oc, only_to_die, prefix);
1089 *mode = oc.mode;
1090 return ret;
1091 }
@@ -1108,7 +1109,7 @@ static char *resolve_relative_path(const char *rel)
1109
1110 int get_sha1_with_context_1(const char *name, unsigned char *sha1,
1111 struct object_context *oc,
1111 - int gently, const char *prefix)
1112 + int only_to_die, const char *prefix)
1113 {
1114 int ret, bracket_depth;
1115 int namelen = strlen(name);
@@ -1130,7 +1131,7 @@ int get_sha1_with_context_1(const char *name, unsigned char *sha1,
1131 struct cache_entry *ce;
1132 char *new_path = NULL;
1133 int pos;
1133 - if (namelen > 2 && name[1] == '/') {
1134 + if (!only_to_die && namelen > 2 && name[1] == '/') {
1135 struct commit_list *list = NULL;
1136 for_each_ref(handle_one_ref, &list);
1137 return get_sha1_oneline(name + 2, sha1, list);
@@ -1173,7 +1174,7 @@ int get_sha1_with_context_1(const char *name, unsigned char *sha1,
1174 }
1175 pos++;
1176 }
1176 - if (!gently && name[1] && name[1] != '/')
1177 + if (only_to_die && name[1] && name[1] != '/')
1178 diagnose_invalid_index_path(stage, prefix, cp);
1179 free(new_path);
1180 return -1;
@@ -1189,7 +1190,7 @@ int get_sha1_with_context_1(const char *name, unsigned char *sha1,
1190 if (*cp == ':') {
1191 unsigned char tree_sha1[20];
1192 char *object_name = NULL;
1192 - if (!gently) {
1193 + if (only_to_die) {
1194 object_name = xmalloc(cp-name+1);
1195 strncpy(object_name, name, cp-name);
1196 object_name[cp-name] = '\0';
@@ -1202,7 +1203,7 @@ int get_sha1_with_context_1(const char *name, unsigned char *sha1,
1203 if (new_filename)
1204 filename = new_filename;
1205 ret = get_tree_entry(tree_sha1, filename, sha1, &oc->mode);
1205 - if (!gently) {
1206 + if (only_to_die) {
1207 diagnose_invalid_sha1_path(prefix, filename,
1208 tree_sha1, object_name);
1209 free(object_name);
@@ -1215,7 +1216,7 @@ int get_sha1_with_context_1(const char *name, unsigned char *sha1,
1216 free(new_filename);
1217 return ret;
1218 } else {
1218 - if (!gently)
1219 + if (only_to_die)
1220 die("Invalid object name '%s'.", object_name);
1221 }
1222 }