Merge branch 'jk/parse-object-cached'
authorJunio C Hamano <gitster@pobox.com>
Sun, 29 Jan 2012 21:18:55 +0000 (13:18 -0800)
committerJunio C Hamano <gitster@pobox.com>
Sun, 29 Jan 2012 21:18:55 +0000 (13:18 -0800)
* jk/parse-object-cached:
upload-pack: avoid parsing tag destinations
upload-pack: avoid parsing objects during ref advertisement
parse_object: try internal cache before reading object db

object.c
tag.c
tag.h
upload-pack.c
index d8d09f92aacd114e23378af2cfbeb78a3dd785a0..6b06297a5f06cc35cb266d6dd36c92df75a82de7 100644 (file)
--- a/object.c
+++ b/object.c
@@ -191,10 +191,15 @@ struct object *parse_object(const unsigned char *sha1)
        enum object_type type;
        int eaten;
        const unsigned char *repl = lookup_replace_object(sha1);
-       void *buffer = read_sha1_file(sha1, &type, &size);
+       void *buffer;
+       struct object *obj;
+
+       obj = lookup_object(sha1);
+       if (obj && obj->parsed)
+               return obj;
 
+       buffer = read_sha1_file(sha1, &type, &size);
        if (buffer) {
-               struct object *obj;
                if (check_sha1_signature(repl, buffer, size, typename(type)) < 0) {
                        free(buffer);
                        error("sha1 mismatch %s\n", sha1_to_hex(repl));
diff --git a/tag.c b/tag.c
index 3aa186df628331e74e8a84d3cc2d313f4518a626..78d272b863f22285048cf54b9dcb03f80cb36f00 100644 (file)
--- a/tag.c
+++ b/tag.c
@@ -24,6 +24,18 @@ struct object *deref_tag(struct object *o, const char *warn, int warnlen)
        return o;
 }
 
+struct object *deref_tag_noverify(struct object *o)
+{
+       while (o && o->type == OBJ_TAG) {
+               o = parse_object(o->sha1);
+               if (o && o->type == OBJ_TAG && ((struct tag *)o)->tagged)
+                       o = ((struct tag *)o)->tagged;
+               else
+                       o = NULL;
+       }
+       return o;
+}
+
 struct tag *lookup_tag(const unsigned char *sha1)
 {
        struct object *obj = lookup_object(sha1);
diff --git a/tag.h b/tag.h
index 5ee88e6550cafa78b7e4acaa1285d5805974a037..bc8a1e40f04e87a6d502ab9d96022f734c57f4eb 100644 (file)
--- a/tag.h
+++ b/tag.h
@@ -16,6 +16,7 @@ extern struct tag *lookup_tag(const unsigned char *sha1);
 extern int parse_tag_buffer(struct tag *item, const void *data, unsigned long size);
 extern int parse_tag(struct tag *item);
 extern struct object *deref_tag(struct object *, const char *, int);
+extern struct object *deref_tag_noverify(struct object *);
 extern size_t parse_signature(const char *buf, unsigned long size);
 
 #endif /* TAG_H */
index 0d11e21a68b227101d6c7f6f4d7b305d08f77d95..bb08e2eb0dc52f68807a83b671fa61a2c2224f41 100644 (file)
@@ -724,11 +724,14 @@ static int send_ref(const char *refname, const unsigned char *sha1, int flag, vo
        static const char *capabilities = "multi_ack thin-pack side-band"
                " side-band-64k ofs-delta shallow no-progress"
                " include-tag multi_ack_detailed";
-       struct object *o = parse_object(sha1);
+       struct object *o = lookup_unknown_object(sha1);
        const char *refname_nons = strip_namespace(refname);
 
-       if (!o)
-               die("git upload-pack: cannot find object %s:", sha1_to_hex(sha1));
+       if (o->type == OBJ_NONE) {
+               o->type = sha1_object_info(sha1, NULL);
+               if (o->type < 0)
+                   die("git upload-pack: cannot find object %s:", sha1_to_hex(sha1));
+       }
 
        if (capabilities)
                packet_write(1, "%s %s%c%s%s\n", sha1_to_hex(sha1), refname_nons,
@@ -742,7 +745,7 @@ static int send_ref(const char *refname, const unsigned char *sha1, int flag, vo
                nr_our_refs++;
        }
        if (o->type == OBJ_TAG) {
-               o = deref_tag(o, refname, 0);
+               o = deref_tag_noverify(o);
                if (o)
                        packet_write(1, "%s %s^{}\n", sha1_to_hex(o->sha1), refname_nons);
        }