X-Git-Url: https://git.verplant.org/?a=blobdiff_plain;f=commit.c;h=56efc69f1f4bf1568eaa549bed16f7cc2cd669ba;hb=5a2282de13c4da13f979185e652c8a08e2481fd1;hp=ebf4db6416497ba6586d359c6d37c8ee942a1395;hpb=2ed02887bda74871bad64f1be36fb4f60d07706e;p=git.git diff --git a/commit.c b/commit.c index ebf4db64..56efc69f 100644 --- a/commit.c +++ b/commit.c @@ -1,6 +1,6 @@ +#include "cache.h" #include "tag.h" #include "commit.h" -#include "cache.h" int save_commit_buffer = 1; @@ -204,6 +204,7 @@ int parse_commit_buffer(struct commit *item, void *buffer, unsigned long size) unsigned char parent[20]; struct commit_list **pptr; struct commit_graft *graft; + unsigned n_refs = 0; if (item->object.parsed) return 0; @@ -214,7 +215,7 @@ int parse_commit_buffer(struct commit *item, void *buffer, unsigned long size) return error("bad tree pointer in commit %s\n", sha1_to_hex(item->object.sha1)); item->tree = lookup_tree(parent); if (item->tree) - add_ref(&item->object, &item->tree->object); + n_refs++; bufptr += 46; /* "tree " + "hex sha1" + "\n" */ pptr = &item->parents; @@ -230,7 +231,7 @@ int parse_commit_buffer(struct commit *item, void *buffer, unsigned long size) new_parent = lookup_commit(parent); if (new_parent) { pptr = &commit_list_insert(new_parent, pptr)->next; - add_ref(&item->object, &new_parent->object); + n_refs++; } } if (graft) { @@ -241,10 +242,22 @@ int parse_commit_buffer(struct commit *item, void *buffer, unsigned long size) if (!new_parent) continue; pptr = &commit_list_insert(new_parent, pptr)->next; - add_ref(&item->object, &new_parent->object); + n_refs++; } } item->date = parse_commit_date(bufptr); + + if (track_object_refs) { + unsigned i = 0; + struct commit_list *p; + struct object_refs *refs = alloc_object_refs(n_refs); + if (item->tree) + refs->ref[i++] = &item->tree->object; + for (p = item->parents; p; p = p->next) + refs->ref[i++] = &p->item->object; + set_object_refs(&item->object, refs); + } + return 0; } @@ -339,6 +352,19 @@ struct commit *pop_most_recent_commit(struct commit_list **list, return ret; } +void clear_commit_marks(struct commit *commit, unsigned int mark) +{ + struct commit_list *parents; + + parents = commit->parents; + commit->object.flags &= ~mark; + while (parents) { + if (parents->item && parents->item->object.parsed) + clear_commit_marks(parents->item, mark); + parents = parents->next; + } +} + /* * Generic support for pretty-printing the header */ @@ -547,6 +573,9 @@ void sort_in_topological_order(struct commit_list ** list) next = next->next; count++; } + + if (!count) + return; /* allocate an array to help sort the list */ nodes = xcalloc(count, sizeof(*nodes)); /* link the list to the array */