Merge branch 'mk/maint-parse-careful'
authorJunio C Hamano <gitster@pobox.com>
Tue, 19 Feb 2008 04:56:01 +0000 (20:56 -0800)
committerJunio C Hamano <gitster@pobox.com>
Tue, 19 Feb 2008 04:56:01 +0000 (20:56 -0800)
* mk/maint-parse-careful:
peel_onion: handle NULL
check return value from parse_commit() in various functions
parse_commit: don't fail, if object is NULL
revision.c: handle tag->tagged == NULL
reachable.c::process_tree/blob: check for NULL
process_tag: handle tag->tagged == NULL
check results of parse_commit in merge_bases
list-objects.c::process_tree/blob: check for NULL
reachable.c::add_one_tree: handle NULL from lookup_tree
mark_blob/tree_uninteresting: check for NULL
get_sha1_oneline: check return value of parse_object
read_object_with_reference: don't read beyond the buffer

commit.c
list-objects.c
reachable.c
revision.c
sha1_file.c
sha1_name.c
shallow.c
upload-pack.c
index 8b8fb04d1f6107da15cb142485d80cabe7a3828e..22ce7768639465f896e52b08a73cf5605940700b 100644 (file)
--- a/commit.c
+++ b/commit.c
@@ -311,6 +311,8 @@ int parse_commit(struct commit *item)
        unsigned long size;
        int ret;
 
+       if (!item)
+               return -1;
        if (item->object.parsed)
                return 0;
        buffer = read_sha1_file(item->object.sha1, &type, &size);
@@ -385,8 +387,7 @@ struct commit *pop_most_recent_commit(struct commit_list **list,
 
        while (parents) {
                struct commit *commit = parents->item;
-               parse_commit(commit);
-               if (!(commit->object.flags & mark)) {
+               if (!parse_commit(commit) && !(commit->object.flags & mark)) {
                        commit->object.flags |= mark;
                        insert_by_date(commit, list);
                }
@@ -552,8 +553,10 @@ static struct commit_list *merge_bases(struct commit *one, struct commit *two)
                 */
                return commit_list_insert(one, &result);
 
-       parse_commit(one);
-       parse_commit(two);
+       if (parse_commit(one))
+               return NULL;
+       if (parse_commit(two))
+               return NULL;
 
        one->object.flags |= PARENT1;
        two->object.flags |= PARENT2;
@@ -586,7 +589,8 @@ static struct commit_list *merge_bases(struct commit *one, struct commit *two)
                        parents = parents->next;
                        if ((p->object.flags & flags) == flags)
                                continue;
-                       parse_commit(p);
+                       if (parse_commit(p))
+                               return NULL;
                        p->object.flags |= flags;
                        insert_by_date(p, &list);
                }
index 4ef58e7ec01ebdfc6f036ccafaf837b2b38ed7a5..c8b8375e4983794e601ba69a1c217a3c711835e9 100644 (file)
@@ -18,6 +18,8 @@ static void process_blob(struct rev_info *revs,
 
        if (!revs->blob_objects)
                return;
+       if (!obj)
+               die("bad blob object");
        if (obj->flags & (UNINTERESTING | SEEN))
                return;
        obj->flags |= SEEN;
@@ -69,6 +71,8 @@ static void process_tree(struct rev_info *revs,
 
        if (!revs->tree_objects)
                return;
+       if (!obj)
+               die("bad tree object");
        if (obj->flags & (UNINTERESTING | SEEN))
                return;
        if (parse_tree(tree) < 0)
index 823e3242ec126a5d55c36b24eb8699a2efecad52..3b1c18ff9b9060d0dd437ce89aedb8871c66c54c 100644 (file)
@@ -15,6 +15,8 @@ static void process_blob(struct blob *blob,
 {
        struct object *obj = &blob->object;
 
+       if (!blob)
+               die("bad blob object");
        if (obj->flags & SEEN)
                return;
        obj->flags |= SEEN;
@@ -39,6 +41,8 @@ static void process_tree(struct tree *tree,
        struct name_entry entry;
        struct name_path me;
 
+       if (!tree)
+               die("bad tree object");
        if (obj->flags & SEEN)
                return;
        obj->flags |= SEEN;
@@ -79,7 +83,8 @@ static void process_tag(struct tag *tag, struct object_array *p, const char *nam
 
        if (parse_tag(tag) < 0)
                die("bad tag object %s", sha1_to_hex(obj->sha1));
-       add_object(tag->tagged, p, NULL, name);
+       if (tag->tagged)
+               add_object(tag->tagged, p, NULL, name);
 }
 
 static void walk_commit_list(struct rev_info *revs)
@@ -150,7 +155,8 @@ static int add_one_reflog(const char *path, const unsigned char *sha1, int flag,
 static void add_one_tree(const unsigned char *sha1, struct rev_info *revs)
 {
        struct tree *tree = lookup_tree(sha1);
-       add_pending_object(revs, &tree->object, "");
+       if (tree)
+               add_pending_object(revs, &tree->object, "");
 }
 
 static void add_cache_tree(struct cache_tree *it, struct rev_info *revs)
index 6e85aaa3fb30e98f3b02f094af7f1763577cdb8d..b1aebf8999b5a9ba80cba659a28f9152c05da85c 100644 (file)
@@ -46,6 +46,8 @@ void add_object(struct object *obj,
 
 static void mark_blob_uninteresting(struct blob *blob)
 {
+       if (!blob)
+               return;
        if (blob->object.flags & UNINTERESTING)
                return;
        blob->object.flags |= UNINTERESTING;
@@ -57,6 +59,8 @@ void mark_tree_uninteresting(struct tree *tree)
        struct name_entry entry;
        struct object *obj = &tree->object;
 
+       if (!tree)
+               return;
        if (obj->flags & UNINTERESTING)
                return;
        obj->flags |= UNINTERESTING;
@@ -173,6 +177,8 @@ static struct commit *handle_commit(struct rev_info *revs, struct object *object
                struct tag *tag = (struct tag *) object;
                if (revs->tag_objects && !(flags & UNINTERESTING))
                        add_pending_object(revs, object, tag->tag);
+               if (!tag->tagged)
+                       die("bad tag");
                object = parse_object(tag->tagged->sha1);
                if (!object)
                        die("bad object %s", sha1_to_hex(tag->tagged->sha1));
@@ -685,6 +691,8 @@ static int add_parents_only(struct rev_info *revs, const char *arg, int flags)
                it = get_reference(revs, arg, sha1, 0);
                if (it->type != OBJ_TAG)
                        break;
+               if (!((struct tag*)it)->tagged)
+                       return 0;
                hashcpy(sha1, ((struct tag*)it)->tagged->sha1);
        }
        if (it->type != OBJ_COMMIT)
index 41799492f909e19d907fe5d954463f9fba177a4e..d9da7c8f75c8f44a62661d92b6f8e5266df83a73 100644 (file)
@@ -1943,7 +1943,8 @@ void *read_object_with_reference(const unsigned char *sha1,
                }
                ref_length = strlen(ref_type);
 
-               if (memcmp(buffer, ref_type, ref_length) ||
+               if (ref_length + 40 > isize ||
+                   memcmp(buffer, ref_type, ref_length) ||
                    get_sha1_hex((char *) buffer + ref_length, actual_sha1)) {
                        free(buffer);
                        return NULL;
index ed3c867d6ad5ed181033950fbcca8daa605e6f20..c2805e736b3086a0e33271a4b5c73cea7d2c55cd 100644 (file)
@@ -494,8 +494,11 @@ static int peel_onion(const char *name, int len, unsigned char *sha1)
                                return error("%.*s: expected %s type, but the object dereferences to %s type",
                                             len, name, typename(expected_type),
                                             typename(o->type));
+                       if (!o)
+                               return -1;
                        if (!o->parsed)
-                               parse_object(o->sha1);
+                               if (!parse_object(o->sha1))
+                                       return -1;
                }
        }
        return 0;
@@ -620,7 +623,8 @@ static int get_sha1_oneline(const char *prefix, unsigned char *sha1)
                unsigned long size;
 
                commit = pop_most_recent_commit(&list, ONELINE_SEEN);
-               parse_object(commit->object.sha1);
+               if (!parse_object(commit->object.sha1))
+                       continue;
                if (temp_commit_buffer)
                        free(temp_commit_buffer);
                if (commit->buffer)
index 212e62b77ceea1f81c1938f012099e828f45aa85..4d90eda19efe0a80c1cb39e8897ab3ed5e6fcf56 100644 (file)
--- a/shallow.c
+++ b/shallow.c
@@ -70,7 +70,8 @@ struct commit_list *get_shallow_commits(struct object_array *heads, int depth,
                                cur_depth = *(int *)commit->util;
                        }
                }
-               parse_commit(commit);
+               if (parse_commit(commit))
+                       die("invalid commit");
                commit->object.flags |= not_shallow_flag;
                cur_depth++;
                for (p = commit->parents, commit = NULL; p; p = p->next) {
index de147853b5546f90190654844c765b0ea44902af..b26d05331d7eeab4efea01594ecf196bc5fb50ed 100644 (file)
@@ -534,7 +534,8 @@ static void receive_needs(void)
                                /* make sure the real parents are parsed */
                                unregister_shallow(object->sha1);
                                object->parsed = 0;
-                               parse_commit((struct commit *)object);
+                               if (parse_commit((struct commit *)object))
+                                       die("invalid commit");
                                parents = ((struct commit *)object)->parents;
                                while (parents) {
                                        add_object_array(&parents->item->object,