Add commit parents to parsed commits and commit lists to the revpool.

Basic support for iterating the revpool.

The following functions of the revwalk API have been partially
implemented:

    void gitrp_reset(git_revpool *pool);
    void gitrp_push(git_revpool *pool, git_commit *commit);
    void gitrp_prepare_walk(git_revpool *pool);
    git_commit *gitrp_next(git_revpool *pool);

Parsed commits' parents are now also parsed and stored in a
"git_commit_list" structure (linked list).

Signed-off-by: Vicent Marti <tanoku@gmail.com>
Signed-off-by: Andreas Ericsson <ae@op5.se>
This commit is contained in:
Vicent Marti 2010-05-18 20:55:19 +02:00 committed by Andreas Ericsson
parent 42281e007e
commit 08d5d00056
4 changed files with 114 additions and 1 deletions

View File

@ -35,6 +35,22 @@ const git_oid *git_commit_id(git_commit *c)
return &c->id;
}
void git_commit_mark_uninteresting(git_commit *commit)
{
git_commit_list *parents = commit->parents;
commit->flags |= GIT_COMMIT_HIDE;
/*
* FIXME: mark recursively the parents' parents?
* They are most likely not parsed yet...
*/
while (parents) {
parents->commit->flags |= GIT_COMMIT_HIDE;
parents = parents->next;
}
}
git_commit *git_commit_lookup(git_revpool *pool, const git_oid *id)
{
git_obj commit_obj;
@ -141,7 +157,7 @@ int git_commit__parse_buffer(git_commit *commit, void *data, size_t len)
if ((parent = git_commit_lookup(commit->pool, &oid)) == NULL)
return -1;
// TODO: push the new commit into the revpool
git_commit_list_insert(&commit->parents, parent);
}
if (git_commit__parse_time(&commit->commit_time, buffer, buffer_end) < 0)
@ -152,3 +168,30 @@ int git_commit__parse_buffer(git_commit *commit, void *data, size_t len)
return 0;
}
void git_commit_list_insert(git_commit_list **list, git_commit *commit)
{
if (*list == NULL)
{
*list = git__malloc(sizeof(git_commit_list));
if (*list == NULL)
return;
(*list)->commit = commit;
(*list)->next = NULL;
}
else
{
git_commit_list *new_list = NULL;
new_list = git__malloc(sizeof(git_commit_list));
if (new_list == NULL)
return;
new_list->commit = commit;
new_list->next = *list;
*list = new_list;
}
}

View File

@ -9,10 +9,19 @@
#define GIT_COMMIT_HIDE (1 << 1)
#define GIT_COMMIT_DELAY (1 << 2)
struct git_commit_list {
struct git_commit *commit;
struct git_commit_list *next;
};
typedef struct git_commit_list git_commit_list;
struct git_commit {
git_oid id;
time_t commit_time;
git_revpool *pool;
git_commit_list *parents;
unsigned parsed:1,
flags:26;
};
@ -21,4 +30,6 @@ int git_commit__parse_oid(git_oid *oid, char **buffer_out, const char *buffer_en
int git_commit__parse_buffer(git_commit *commit, void *data, size_t len);
int git_commit__parse_time(time_t *commit_time, char *buffer, const char *buffer_end);
void git_commit_list_insert(git_commit_list **list, git_commit *commit);
#endif

View File

@ -24,6 +24,7 @@
*/
#include "common.h"
#include "commit.h"
#include "revwalk.h"
git_revpool *gitrp_alloc(git_odb *db)
@ -32,6 +33,8 @@ git_revpool *gitrp_alloc(git_odb *db)
if (!walk)
return NULL;
memset(walk, 0x0, sizeof(git_revpool));
walk->db = db;
return walk;
}
@ -40,3 +43,54 @@ void gitrp_free(git_revpool *walk)
{
free(walk);
}
void gitrp_push(git_revpool *pool, git_commit *commit)
{
if ((commit->flags & GIT_COMMIT_SEEN) != 0)
return;
/* FIXME:
* Unparsed commit objects? Where do these come from?
* Do we need to handle them?
*/
if (!commit->parsed)
return;
commit->flags |= GIT_COMMIT_SEEN;
git_commit_list_insert(&pool->commits, commit);
}
void gitrp_prepare_walk(git_revpool *pool)
{
// TODO: sort commit list based on walk ordering
pool->iterator = pool->commits;
pool->walking = 1;
}
git_commit *gitrp_next(git_revpool *pool)
{
git_commit *next;
if (!pool->walking)
gitrp_prepare_walk(pool);
// Iteration finished
if (pool->iterator == NULL)
{
gitrp_reset(pool);
return NULL;
}
next = pool->iterator->commit;
pool->iterator = pool->iterator->next;
return next;
}
void gitrp_reset(git_revpool *pool)
{
pool->iterator = NULL;
pool->walking = 0;
}

View File

@ -6,6 +6,11 @@
struct git_revpool {
git_odb *db;
git_commit_list *iterator;
git_commit_list *commits;
unsigned walking:1,
topological_sort:1;
};
#endif /* INCLUDE_revwalk_h__ */