mirror of
https://git.proxmox.com/git/libgit2
synced 2025-05-09 20:29:27 +00:00
Fixed brace placement and converted spaces to tabs.
Signed-off-by: Vicent Marti <tanoku@gmail.com> Signed-off-by: Andreas Ericsson <ae@op5.se>
This commit is contained in:
parent
0cf02ff92d
commit
9b3577eda0
445
src/commit.c
445
src/commit.c
@ -43,381 +43,368 @@ const git_oid *git_commit_id(git_commit *c)
|
|||||||
|
|
||||||
void git_commit__mark_uninteresting(git_commit *commit)
|
void git_commit__mark_uninteresting(git_commit *commit)
|
||||||
{
|
{
|
||||||
if (commit == NULL)
|
if (commit == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
git_commit_node *parents = commit->parents.head;
|
git_commit_node *parents = commit->parents.head;
|
||||||
|
|
||||||
commit->uninteresting = 1;
|
commit->uninteresting = 1;
|
||||||
|
|
||||||
while (parents)
|
while (parents) {
|
||||||
{
|
parents->commit->uninteresting = 1;
|
||||||
parents->commit->uninteresting = 1;
|
|
||||||
parents = parents->next;
|
parents = parents->next;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
git_commit *git_commit_parse(git_revpool *pool, const git_oid *id)
|
git_commit *git_commit_parse(git_revpool *pool, const git_oid *id)
|
||||||
{
|
{
|
||||||
git_commit *commit = NULL;
|
git_commit *commit = NULL;
|
||||||
|
|
||||||
if ((commit = git_commit_lookup(pool, id)) == NULL)
|
if ((commit = git_commit_lookup(pool, id)) == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
if (git_commit_parse_existing(commit) < 0)
|
if (git_commit_parse_existing(commit) < 0)
|
||||||
goto error_cleanup;
|
goto error_cleanup;
|
||||||
|
|
||||||
return commit;
|
return commit;
|
||||||
|
|
||||||
error_cleanup:
|
error_cleanup:
|
||||||
free(commit);
|
free(commit);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
int git_commit_parse_existing(git_commit *commit)
|
int git_commit_parse_existing(git_commit *commit)
|
||||||
{
|
{
|
||||||
git_obj commit_obj;
|
git_obj commit_obj;
|
||||||
|
|
||||||
if (commit->parsed)
|
if (commit->parsed)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (git_odb_read(&commit_obj, commit->object.pool->db, &commit->object.id) < 0)
|
if (git_odb_read(&commit_obj, commit->object.pool->db, &commit->object.id) < 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (commit_obj.type != GIT_OBJ_COMMIT)
|
if (commit_obj.type != GIT_OBJ_COMMIT)
|
||||||
goto error_cleanup;
|
goto error_cleanup;
|
||||||
|
|
||||||
if (git_commit__parse_buffer(commit, commit_obj.data, commit_obj.len) < 0)
|
if (git_commit__parse_buffer(commit, commit_obj.data, commit_obj.len) < 0)
|
||||||
goto error_cleanup;
|
goto error_cleanup;
|
||||||
|
|
||||||
git_obj_close(&commit_obj);
|
git_obj_close(&commit_obj);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
error_cleanup:
|
error_cleanup:
|
||||||
git_obj_close(&commit_obj);
|
git_obj_close(&commit_obj);
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
git_commit *git_commit_lookup(git_revpool *pool, const git_oid *id)
|
git_commit *git_commit_lookup(git_revpool *pool, const git_oid *id)
|
||||||
{
|
{
|
||||||
git_commit *commit = NULL;
|
git_commit *commit = NULL;
|
||||||
|
|
||||||
if (pool == NULL)
|
if (pool == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
commit = (git_commit *)git_revpool_table_lookup(pool->commits, id);
|
commit = (git_commit *)git_revpool_table_lookup(pool->commits, id);
|
||||||
if (commit != NULL)
|
if (commit != NULL)
|
||||||
return commit;
|
return commit;
|
||||||
|
|
||||||
commit = git__malloc(sizeof(git_commit));
|
commit = git__malloc(sizeof(git_commit));
|
||||||
|
|
||||||
if (commit == NULL)
|
if (commit == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
memset(commit, 0x0, sizeof(git_commit));
|
memset(commit, 0x0, sizeof(git_commit));
|
||||||
|
|
||||||
// Initialize parent object
|
// Initialize parent object
|
||||||
git_oid_cpy(&commit->object.id, id);
|
git_oid_cpy(&commit->object.id, id);
|
||||||
commit->object.pool = pool;
|
commit->object.pool = pool;
|
||||||
|
|
||||||
git_revpool_table_insert(pool->commits, (git_revpool_object *)commit);
|
git_revpool_table_insert(pool->commits, (git_revpool_object *)commit);
|
||||||
|
|
||||||
return commit;
|
return commit;
|
||||||
}
|
}
|
||||||
|
|
||||||
int git_commit__parse_time(time_t *commit_time, char *buffer, const char *buffer_end)
|
int git_commit__parse_time(time_t *commit_time, char *buffer, const char *buffer_end)
|
||||||
{
|
{
|
||||||
if (memcmp(buffer, "author ", 7) != 0)
|
if (memcmp(buffer, "author ", 7) != 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
buffer = memchr(buffer, '\n', buffer_end - buffer);
|
buffer = memchr(buffer, '\n', buffer_end - buffer);
|
||||||
if (buffer == 0 || ++buffer >= buffer_end)
|
if (buffer == 0 || ++buffer >= buffer_end)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (memcmp(buffer, "committer ", 10) != 0)
|
if (memcmp(buffer, "committer ", 10) != 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
buffer = memchr(buffer, '>', buffer_end - buffer);
|
buffer = memchr(buffer, '>', buffer_end - buffer);
|
||||||
if (buffer == 0 || ++buffer >= buffer_end)
|
if (buffer == 0 || ++buffer >= buffer_end)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
*commit_time = strtol(buffer, &buffer, 10);
|
*commit_time = strtol(buffer, &buffer, 10);
|
||||||
|
|
||||||
if (*commit_time == 0)
|
if (*commit_time == 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
buffer = memchr(buffer, '\n', buffer_end - buffer);
|
buffer = memchr(buffer, '\n', buffer_end - buffer);
|
||||||
if (buffer == 0 || ++buffer >= buffer_end)
|
if (buffer == 0 || ++buffer >= buffer_end)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
return (buffer < buffer_end) ? 0 : -1;
|
return (buffer < buffer_end) ? 0 : -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
int git_commit__parse_oid(git_oid *oid, char **buffer_out, const char *buffer_end, const char *header)
|
int git_commit__parse_oid(git_oid *oid, char **buffer_out, const char *buffer_end, const char *header)
|
||||||
{
|
{
|
||||||
const size_t sha_len = GIT_OID_HEXSZ;
|
const size_t sha_len = GIT_OID_HEXSZ;
|
||||||
const size_t header_len = strlen(header);
|
const size_t header_len = strlen(header);
|
||||||
|
|
||||||
char *buffer = *buffer_out;
|
char *buffer = *buffer_out;
|
||||||
|
|
||||||
if (buffer + (header_len + sha_len + 1) > buffer_end)
|
if (buffer + (header_len + sha_len + 1) > buffer_end)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (memcmp(buffer, header, header_len) != 0)
|
if (memcmp(buffer, header, header_len) != 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (buffer[header_len + sha_len] != '\n')
|
if (buffer[header_len + sha_len] != '\n')
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (git_oid_mkstr(oid, buffer + header_len) < 0)
|
if (git_oid_mkstr(oid, buffer + header_len) < 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
*buffer_out = buffer + (header_len + sha_len + 1);
|
*buffer_out = buffer + (header_len + sha_len + 1);
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
int git_commit__parse_buffer(git_commit *commit, void *data, size_t len)
|
int git_commit__parse_buffer(git_commit *commit, void *data, size_t len)
|
||||||
{
|
{
|
||||||
char *buffer = (char *)data;
|
char *buffer = (char *)data;
|
||||||
const char *buffer_end = (char *)data + len;
|
const char *buffer_end = (char *)data + len;
|
||||||
|
|
||||||
git_oid oid;
|
git_oid oid;
|
||||||
|
|
||||||
if (commit->parsed)
|
if (commit->parsed)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (git_commit__parse_oid(&oid, &buffer, buffer_end, "tree ") < 0)
|
if (git_commit__parse_oid(&oid, &buffer, buffer_end, "tree ") < 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* TODO: load tree into commit object
|
* TODO: load tree into commit object
|
||||||
* TODO: commit grafts!
|
* TODO: commit grafts!
|
||||||
*/
|
*/
|
||||||
|
|
||||||
while (git_commit__parse_oid(&oid, &buffer, buffer_end, "parent ") == 0) {
|
while (git_commit__parse_oid(&oid, &buffer, buffer_end, "parent ") == 0) {
|
||||||
git_commit *parent;
|
git_commit *parent;
|
||||||
|
|
||||||
if ((parent = git_commit_lookup(commit->object.pool, &oid)) == NULL)
|
if ((parent = git_commit_lookup(commit->object.pool, &oid)) == NULL)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
// Inherit uninteresting flag
|
// Inherit uninteresting flag
|
||||||
if (commit->uninteresting)
|
if (commit->uninteresting)
|
||||||
parent->uninteresting = 1;
|
parent->uninteresting = 1;
|
||||||
|
|
||||||
git_commit_list_push_back(&commit->parents, parent);
|
git_commit_list_push_back(&commit->parents, parent);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (git_commit__parse_time(&commit->commit_time, buffer, buffer_end) < 0)
|
if (git_commit__parse_time(&commit->commit_time, buffer, buffer_end) < 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
commit->parsed = 1;
|
commit->parsed = 1;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void git_commit_list_push_back(git_commit_list *list, git_commit *commit)
|
void git_commit_list_push_back(git_commit_list *list, git_commit *commit)
|
||||||
{
|
{
|
||||||
git_commit_node *node = NULL;
|
git_commit_node *node = NULL;
|
||||||
|
|
||||||
node = git__malloc(sizeof(git_commit_list));
|
node = git__malloc(sizeof(git_commit_list));
|
||||||
|
|
||||||
if (node == NULL)
|
if (node == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
node->commit = commit;
|
node->commit = commit;
|
||||||
node->next = NULL;
|
node->next = NULL;
|
||||||
node->prev = list->tail;
|
node->prev = list->tail;
|
||||||
|
|
||||||
if (list->tail == NULL)
|
if (list->tail == NULL) {
|
||||||
{
|
list->head = list->tail = node;
|
||||||
list->head = list->tail = node;
|
} else {
|
||||||
}
|
list->tail->next = node;
|
||||||
else
|
list->tail = node;
|
||||||
{
|
}
|
||||||
list->tail->next = node;
|
|
||||||
list->tail = node;
|
|
||||||
}
|
|
||||||
|
|
||||||
list->size++;
|
list->size++;
|
||||||
}
|
}
|
||||||
|
|
||||||
void git_commit_list_push_front(git_commit_list *list, git_commit *commit)
|
void git_commit_list_push_front(git_commit_list *list, git_commit *commit)
|
||||||
{
|
{
|
||||||
git_commit_node *node = NULL;
|
git_commit_node *node = NULL;
|
||||||
|
|
||||||
node = git__malloc(sizeof(git_commit_list));
|
node = git__malloc(sizeof(git_commit_list));
|
||||||
|
|
||||||
if (node == NULL)
|
if (node == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
node->commit = commit;
|
node->commit = commit;
|
||||||
node->next = list->head;
|
node->next = list->head;
|
||||||
node->prev = NULL;
|
node->prev = NULL;
|
||||||
|
|
||||||
if (list->head == NULL)
|
if (list->head == NULL) {
|
||||||
{
|
list->head = list->tail = node;
|
||||||
list->head = list->tail = node;
|
} else {
|
||||||
}
|
list->head->prev = node;
|
||||||
else
|
list->head = node;
|
||||||
{
|
}
|
||||||
list->head->prev = node;
|
|
||||||
list->head = node;
|
|
||||||
}
|
|
||||||
|
|
||||||
list->size++;
|
list->size++;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
git_commit *git_commit_list_pop_back(git_commit_list *list)
|
git_commit *git_commit_list_pop_back(git_commit_list *list)
|
||||||
{
|
{
|
||||||
git_commit_node *node;
|
git_commit_node *node;
|
||||||
git_commit *commit;
|
git_commit *commit;
|
||||||
|
|
||||||
if (list->tail == NULL)
|
if (list->tail == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
node = list->tail;
|
node = list->tail;
|
||||||
list->tail = list->tail->prev;
|
list->tail = list->tail->prev;
|
||||||
if (list->tail == NULL)
|
if (list->tail == NULL)
|
||||||
list->head = NULL;
|
list->head = NULL;
|
||||||
|
|
||||||
commit = node->commit;
|
commit = node->commit;
|
||||||
free(node);
|
free(node);
|
||||||
|
|
||||||
list->size--;
|
list->size--;
|
||||||
|
|
||||||
return commit;
|
return commit;
|
||||||
}
|
}
|
||||||
|
|
||||||
git_commit *git_commit_list_pop_front(git_commit_list *list)
|
git_commit *git_commit_list_pop_front(git_commit_list *list)
|
||||||
{
|
{
|
||||||
git_commit_node *node;
|
git_commit_node *node;
|
||||||
git_commit *commit;
|
git_commit *commit;
|
||||||
|
|
||||||
if (list->head == NULL)
|
if (list->head == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
node = list->head;
|
node = list->head;
|
||||||
list->head = list->head->next;
|
list->head = list->head->next;
|
||||||
if (list->head == NULL)
|
if (list->head == NULL)
|
||||||
list->tail = NULL;
|
list->tail = NULL;
|
||||||
|
|
||||||
commit = node->commit;
|
commit = node->commit;
|
||||||
free(node);
|
free(node);
|
||||||
|
|
||||||
list->size--;
|
list->size--;
|
||||||
|
|
||||||
return commit;
|
return commit;
|
||||||
}
|
}
|
||||||
|
|
||||||
void git_commit_list_clear(git_commit_list *list, int free_commits)
|
void git_commit_list_clear(git_commit_list *list, int free_commits)
|
||||||
{
|
{
|
||||||
git_commit_node *node, *next_node;
|
git_commit_node *node, *next_node;
|
||||||
|
|
||||||
node = list->head;
|
node = list->head;
|
||||||
while (node)
|
while (node) {
|
||||||
{
|
if (free_commits)
|
||||||
if (free_commits)
|
free(node->commit);
|
||||||
free(node->commit);
|
|
||||||
|
|
||||||
next_node = node->next;
|
next_node = node->next;
|
||||||
free(node);
|
free(node);
|
||||||
node = next_node;
|
node = next_node;
|
||||||
}
|
}
|
||||||
|
|
||||||
list->head = list->tail = NULL;
|
list->head = list->tail = NULL;
|
||||||
list->size = 0;
|
list->size = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void git_commit_list_timesort(git_commit_list *list)
|
void git_commit_list_timesort(git_commit_list *list)
|
||||||
{
|
{
|
||||||
git_commit_node *p, *q, *e;
|
git_commit_node *p, *q, *e;
|
||||||
int in_size, p_size, q_size, merge_count, i;
|
int in_size, p_size, q_size, merge_count, i;
|
||||||
|
|
||||||
if (list->head == NULL)
|
if (list->head == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
in_size = 1;
|
in_size = 1;
|
||||||
|
|
||||||
do
|
do {
|
||||||
{
|
p = list->head;
|
||||||
p = list->head;
|
list->tail = NULL;
|
||||||
list->tail = NULL;
|
merge_count = 0;
|
||||||
merge_count = 0;
|
|
||||||
|
|
||||||
while (p != NULL)
|
while (p != NULL) {
|
||||||
{
|
merge_count++;
|
||||||
merge_count++;
|
q = p;
|
||||||
q = p;
|
p_size = 0;
|
||||||
p_size = 0;
|
q_size = in_size;
|
||||||
q_size = in_size;
|
|
||||||
|
|
||||||
for (i = 0; i < in_size && q; ++i, q = q->next)
|
for (i = 0; i < in_size && q; ++i, q = q->next)
|
||||||
p_size++;
|
p_size++;
|
||||||
|
|
||||||
while (p_size > 0 || (q_size > 0 && q))
|
while (p_size > 0 || (q_size > 0 && q)) {
|
||||||
{
|
|
||||||
if (p_size == 0)
|
|
||||||
e = q, q = q->next, q_size--;
|
|
||||||
|
|
||||||
else if (q_size == 0 || q == NULL ||
|
if (p_size == 0)
|
||||||
p->commit->commit_time >= q->commit->commit_time)
|
e = q, q = q->next, q_size--;
|
||||||
e = p, p = p->next, p_size--;
|
|
||||||
|
|
||||||
else
|
else if (q_size == 0 || q == NULL ||
|
||||||
e = q, q = q->next, q_size--;
|
p->commit->commit_time >= q->commit->commit_time)
|
||||||
|
e = p, p = p->next, p_size--;
|
||||||
|
|
||||||
if (list->tail != NULL)
|
else
|
||||||
list->tail->next = e;
|
e = q, q = q->next, q_size--;
|
||||||
else
|
|
||||||
list->head = e;
|
|
||||||
|
|
||||||
e->prev = list->tail;
|
if (list->tail != NULL)
|
||||||
list->tail = e;
|
list->tail->next = e;
|
||||||
}
|
else
|
||||||
|
list->head = e;
|
||||||
|
|
||||||
p = q;
|
e->prev = list->tail;
|
||||||
}
|
list->tail = e;
|
||||||
|
}
|
||||||
|
|
||||||
list->tail->next = NULL;
|
p = q;
|
||||||
in_size *= 2;
|
}
|
||||||
|
|
||||||
} while (merge_count > 1);
|
list->tail->next = NULL;
|
||||||
|
in_size *= 2;
|
||||||
|
|
||||||
|
} while (merge_count > 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
void git_commit_list_toposort(git_commit_list *list)
|
void git_commit_list_toposort(git_commit_list *list)
|
||||||
{
|
{
|
||||||
git_commit *commit;
|
git_commit *commit;
|
||||||
git_commit_list topo;
|
git_commit_list topo;
|
||||||
memset(&topo, 0x0, sizeof(git_commit_list));
|
memset(&topo, 0x0, sizeof(git_commit_list));
|
||||||
|
|
||||||
while ((commit = git_commit_list_pop_back(list)) != NULL)
|
while ((commit = git_commit_list_pop_back(list)) != NULL) {
|
||||||
{
|
git_commit_node *p;
|
||||||
git_commit_node *p;
|
|
||||||
|
|
||||||
if (commit->in_degree > 0)
|
if (commit->in_degree > 0) {
|
||||||
{
|
commit->topo_delay = 1;
|
||||||
commit->topo_delay = 1;
|
continue;
|
||||||
continue;
|
}
|
||||||
}
|
|
||||||
|
|
||||||
for (p = commit->parents.head; p != NULL; p = p->next)
|
for (p = commit->parents.head; p != NULL; p = p->next) {
|
||||||
{
|
p->commit->in_degree--;
|
||||||
p->commit->in_degree--;
|
|
||||||
|
|
||||||
if (p->commit->in_degree == 0 && p->commit->topo_delay)
|
if (p->commit->in_degree == 0 && p->commit->topo_delay) {
|
||||||
{
|
p->commit->topo_delay = 0;
|
||||||
p->commit->topo_delay = 0;
|
git_commit_list_push_back(list, p->commit);
|
||||||
git_commit_list_push_back(list, p->commit);
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
git_commit_list_push_back(&topo, commit);
|
git_commit_list_push_back(&topo, commit);
|
||||||
}
|
}
|
||||||
|
|
||||||
list->head = topo.head;
|
list->head = topo.head;
|
||||||
list->tail = topo.tail;
|
list->tail = topo.tail;
|
||||||
list->size = topo.size;
|
list->size = topo.size;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
30
src/commit.h
30
src/commit.h
@ -7,33 +7,33 @@
|
|||||||
#include <time.h>
|
#include <time.h>
|
||||||
|
|
||||||
struct git_commit_node {
|
struct git_commit_node {
|
||||||
struct git_commit *commit;
|
struct git_commit *commit;
|
||||||
|
|
||||||
struct git_commit_node *next;
|
struct git_commit_node *next;
|
||||||
struct git_commit_node *prev;
|
struct git_commit_node *prev;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct git_commit_list {
|
struct git_commit_list {
|
||||||
struct git_commit_node *head;
|
struct git_commit_node *head;
|
||||||
struct git_commit_node *tail;
|
struct git_commit_node *tail;
|
||||||
size_t size;
|
size_t size;
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef struct git_commit_list git_commit_list;
|
typedef struct git_commit_list git_commit_list;
|
||||||
typedef struct git_commit_node git_commit_node;
|
typedef struct git_commit_node git_commit_node;
|
||||||
|
|
||||||
struct git_commit {
|
struct git_commit {
|
||||||
git_revpool_object object;
|
git_revpool_object object;
|
||||||
|
|
||||||
time_t commit_time;
|
time_t commit_time;
|
||||||
git_commit_list parents;
|
git_commit_list parents;
|
||||||
|
|
||||||
unsigned short in_degree;
|
unsigned short in_degree;
|
||||||
unsigned parsed:1,
|
unsigned parsed:1,
|
||||||
seen:1,
|
seen:1,
|
||||||
uninteresting:1,
|
uninteresting:1,
|
||||||
topo_delay:1,
|
topo_delay:1,
|
||||||
flags:26;
|
flags:26;
|
||||||
};
|
};
|
||||||
|
|
||||||
int git_commit__parse_oid(git_oid *oid, char **buffer_out, const char *buffer_end, const char *header);
|
int git_commit__parse_oid(git_oid *oid, char **buffer_out, const char *buffer_end, const char *header);
|
||||||
|
212
src/revobject.c
212
src/revobject.c
@ -34,10 +34,9 @@ unsigned int git_revpool_table__hash(const git_oid *id)
|
|||||||
const int r = 24;
|
const int r = 24;
|
||||||
|
|
||||||
unsigned int h = 0xA8A3D5;
|
unsigned int h = 0xA8A3D5;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
for (i = 0; i < GIT_OID_RAWSZ / 4; ++i)
|
for (i = 0; i < GIT_OID_RAWSZ / 4; ++i) {
|
||||||
{
|
|
||||||
unsigned int k = ((unsigned int *)id->id)[i];
|
unsigned int k = ((unsigned int *)id->id)[i];
|
||||||
|
|
||||||
k *= m;
|
k *= m;
|
||||||
@ -45,7 +44,7 @@ unsigned int git_revpool_table__hash(const git_oid *id)
|
|||||||
k *= m;
|
k *= m;
|
||||||
h *= m;
|
h *= m;
|
||||||
h ^= k;
|
h ^= k;
|
||||||
}
|
}
|
||||||
|
|
||||||
h ^= h >> 13;
|
h ^= h >> 13;
|
||||||
h *= m;
|
h *= m;
|
||||||
@ -56,169 +55,162 @@ unsigned int git_revpool_table__hash(const git_oid *id)
|
|||||||
|
|
||||||
git_revpool_table *git_revpool_table_create(unsigned int min_size)
|
git_revpool_table *git_revpool_table_create(unsigned int min_size)
|
||||||
{
|
{
|
||||||
git_revpool_table *table;
|
git_revpool_table *table;
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
table = git__malloc(sizeof(table));
|
table = git__malloc(sizeof(table));
|
||||||
|
|
||||||
if (table == NULL)
|
if (table == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
// round up size to closest power of 2
|
// round up size to closest power of 2
|
||||||
min_size--;
|
min_size--;
|
||||||
min_size |= min_size >> 1;
|
min_size |= min_size >> 1;
|
||||||
min_size |= min_size >> 2;
|
min_size |= min_size >> 2;
|
||||||
min_size |= min_size >> 4;
|
min_size |= min_size >> 4;
|
||||||
min_size |= min_size >> 8;
|
min_size |= min_size >> 8;
|
||||||
min_size |= min_size >> 16;
|
min_size |= min_size >> 16;
|
||||||
|
|
||||||
table->size_mask = min_size;
|
table->size_mask = min_size;
|
||||||
table->count = 0;
|
table->count = 0;
|
||||||
table->max_count = (min_size + 1) * max_load_factor;
|
table->max_count = (min_size + 1) * max_load_factor;
|
||||||
|
|
||||||
table->nodes = git__malloc((min_size + 1) * sizeof(git_revpool_node *));
|
table->nodes = git__malloc((min_size + 1) * sizeof(git_revpool_node *));
|
||||||
|
|
||||||
if (table->nodes == NULL)
|
if (table->nodes == NULL) {
|
||||||
{
|
free(table);
|
||||||
free(table);
|
return NULL;
|
||||||
return NULL;
|
}
|
||||||
}
|
|
||||||
|
|
||||||
for (i = 0; i <= min_size; ++i)
|
for (i = 0; i <= min_size; ++i)
|
||||||
table->nodes[i] = NULL;
|
table->nodes[i] = NULL;
|
||||||
|
|
||||||
return table;
|
return table;
|
||||||
}
|
}
|
||||||
|
|
||||||
int git_revpool_table_insert(git_revpool_table *table, git_revpool_object *object)
|
int git_revpool_table_insert(git_revpool_table *table, git_revpool_object *object)
|
||||||
{
|
{
|
||||||
git_revpool_node *node;
|
git_revpool_node *node;
|
||||||
unsigned int index, hash;
|
unsigned int index, hash;
|
||||||
|
|
||||||
if (table == NULL)
|
if (table == NULL)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
if (table->count + 1 > table->max_count)
|
if (table->count + 1 > table->max_count)
|
||||||
git_revpool_table_resize(table);
|
git_revpool_table_resize(table);
|
||||||
|
|
||||||
node = git__malloc(sizeof(git_revpool_node));
|
node = git__malloc(sizeof(git_revpool_node));
|
||||||
if (node == NULL)
|
if (node == NULL)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
hash = git_revpool_table__hash(&object->id);
|
hash = git_revpool_table__hash(&object->id);
|
||||||
index = (hash & table->size_mask);
|
index = (hash & table->size_mask);
|
||||||
|
|
||||||
node->object = object;
|
node->object = object;
|
||||||
node->hash = hash;
|
node->hash = hash;
|
||||||
node->next = table->nodes[index];
|
node->next = table->nodes[index];
|
||||||
|
|
||||||
table->nodes[index] = node;
|
table->nodes[index] = node;
|
||||||
table->count++;
|
table->count++;
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
git_revpool_object *git_revpool_table_lookup(git_revpool_table *table, const git_oid *id)
|
git_revpool_object *git_revpool_table_lookup(git_revpool_table *table, const git_oid *id)
|
||||||
{
|
{
|
||||||
git_revpool_node *node;
|
git_revpool_node *node;
|
||||||
unsigned int index, hash;
|
unsigned int index, hash;
|
||||||
|
|
||||||
if (table == NULL)
|
if (table == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
hash = git_revpool_table__hash(id);
|
hash = git_revpool_table__hash(id);
|
||||||
index = (hash & table->size_mask);
|
index = (hash & table->size_mask);
|
||||||
node = table->nodes[index];
|
node = table->nodes[index];
|
||||||
|
|
||||||
while (node != NULL)
|
while (node != NULL) {
|
||||||
{
|
if (node->hash == hash && git_oid_cmp(id, &node->object->id) == 0)
|
||||||
if (node->hash == hash && git_oid_cmp(id, &node->object->id) == 0)
|
return node->object;
|
||||||
return node->object;
|
|
||||||
|
|
||||||
node = node->next;
|
node = node->next;
|
||||||
}
|
}
|
||||||
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
void git_revpool_table_resize(git_revpool_table *table)
|
void git_revpool_table_resize(git_revpool_table *table)
|
||||||
{
|
{
|
||||||
git_revpool_node **new_nodes;
|
git_revpool_node **new_nodes;
|
||||||
unsigned int new_size, i;
|
unsigned int new_size, i;
|
||||||
|
|
||||||
new_size = (table->size_mask + 1) * 2;
|
new_size = (table->size_mask + 1) * 2;
|
||||||
|
|
||||||
new_nodes = git__malloc(new_size * sizeof(git_revpool_node *));
|
new_nodes = git__malloc(new_size * sizeof(git_revpool_node *));
|
||||||
if (new_nodes == NULL)
|
if (new_nodes == NULL)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
memset(new_nodes, 0x0, new_size * sizeof(git_revpool_node *));
|
memset(new_nodes, 0x0, new_size * sizeof(git_revpool_node *));
|
||||||
|
|
||||||
for (i = 0; i <= table->size_mask; ++i)
|
for (i = 0; i <= table->size_mask; ++i) {
|
||||||
{
|
git_revpool_node *n;
|
||||||
git_revpool_node *n;
|
unsigned int index;
|
||||||
unsigned int index;
|
|
||||||
|
|
||||||
while ((n = table->nodes[i]) != NULL)
|
while ((n = table->nodes[i]) != NULL) {
|
||||||
{
|
table->nodes[i] = n->next;
|
||||||
table->nodes[i] = n->next;
|
index = n->hash & (new_size - 1);
|
||||||
index = n->hash & (new_size - 1);
|
n->next = new_nodes[index];
|
||||||
n->next = new_nodes[index];
|
new_nodes[index] = n;
|
||||||
new_nodes[index] = n;
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
free(table->nodes);
|
free(table->nodes);
|
||||||
table->nodes = new_nodes;
|
table->nodes = new_nodes;
|
||||||
table->size_mask = (new_size - 1);
|
table->size_mask = (new_size - 1);
|
||||||
table->max_count = new_size * max_load_factor;
|
table->max_count = new_size * max_load_factor;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void git_revpool_table_free(git_revpool_table *table)
|
void git_revpool_table_free(git_revpool_table *table)
|
||||||
{
|
{
|
||||||
int index;
|
int index;
|
||||||
|
|
||||||
for (index = 0; index <= table->size_mask; ++index)
|
for (index = 0; index <= table->size_mask; ++index) {
|
||||||
{
|
git_revpool_node *node, *next_node;
|
||||||
git_revpool_node *node, *next_node;
|
|
||||||
|
|
||||||
node = table->nodes[index];
|
node = table->nodes[index];
|
||||||
while (node != NULL)
|
while (node != NULL) {
|
||||||
{
|
next_node = node->next;
|
||||||
next_node = node->next;
|
free(node);
|
||||||
free(node);
|
node = next_node;
|
||||||
node = next_node;
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
free(table);
|
free(table);
|
||||||
}
|
}
|
||||||
|
|
||||||
void git_revpool_tableit_init(git_revpool_table *table, git_revpool_tableit *it)
|
void git_revpool_tableit_init(git_revpool_table *table, git_revpool_tableit *it)
|
||||||
{
|
{
|
||||||
memset(it, 0x0, sizeof(git_revpool_tableit));
|
memset(it, 0x0, sizeof(git_revpool_tableit));
|
||||||
|
|
||||||
it->nodes = table->nodes;
|
it->nodes = table->nodes;
|
||||||
it->current_node = NULL;
|
it->current_node = NULL;
|
||||||
it->current_pos = 0;
|
it->current_pos = 0;
|
||||||
it->size = table->size_mask + 1;
|
it->size = table->size_mask + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
git_revpool_object *git_revpool_tableit_next(git_revpool_tableit *it)
|
git_revpool_object *git_revpool_tableit_next(git_revpool_tableit *it)
|
||||||
{
|
{
|
||||||
git_revpool_node *next = NULL;
|
git_revpool_node *next = NULL;
|
||||||
|
|
||||||
while (it->current_node == NULL)
|
while (it->current_node == NULL) {
|
||||||
{
|
if (it->current_pos >= it->size)
|
||||||
if (it->current_pos >= it->size)
|
return NULL;
|
||||||
return NULL;
|
|
||||||
|
|
||||||
it->current_node = it->nodes[it->current_pos++];
|
it->current_node = it->nodes[it->current_pos++];
|
||||||
}
|
}
|
||||||
|
|
||||||
next = it->current_node;
|
next = it->current_node;
|
||||||
it->current_node = it->current_node->next;
|
it->current_node = it->current_node->next;
|
||||||
|
|
||||||
return next->object;
|
return next->object;
|
||||||
}
|
}
|
||||||
|
@ -4,34 +4,30 @@
|
|||||||
#include "git/common.h"
|
#include "git/common.h"
|
||||||
#include "git/oid.h"
|
#include "git/oid.h"
|
||||||
|
|
||||||
struct git_revpool_object
|
struct git_revpool_object {
|
||||||
{
|
git_oid id;
|
||||||
git_oid id;
|
git_revpool *pool;
|
||||||
git_revpool *pool;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
struct git_revpool_node
|
struct git_revpool_node {
|
||||||
{
|
struct git_revpool_object *object;
|
||||||
struct git_revpool_object *object;
|
unsigned int hash;
|
||||||
unsigned int hash;
|
struct git_revpool_node *next;
|
||||||
struct git_revpool_node *next;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
struct git_revpool_table
|
struct git_revpool_table {
|
||||||
{
|
struct git_revpool_node **nodes;
|
||||||
struct git_revpool_node **nodes;
|
|
||||||
|
|
||||||
unsigned int size_mask;
|
unsigned int size_mask;
|
||||||
unsigned int count;
|
unsigned int count;
|
||||||
unsigned int max_count;
|
unsigned int max_count;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct git_revpool_tableit
|
struct git_revpool_tableit {
|
||||||
{
|
struct git_revpool_node **nodes;
|
||||||
struct git_revpool_node **nodes;
|
struct git_revpool_node *current_node;
|
||||||
struct git_revpool_node *current_node;
|
unsigned int current_pos;
|
||||||
unsigned int current_pos;
|
unsigned int size;
|
||||||
unsigned int size;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
@ -50,5 +46,4 @@ void git_revpool_table_free(git_revpool_table *table);
|
|||||||
git_revpool_object *git_revpool_tableit_next(git_revpool_tableit *it);
|
git_revpool_object *git_revpool_tableit_next(git_revpool_tableit *it);
|
||||||
void git_revpool_tableit_init(git_revpool_table *table, git_revpool_tableit *it);
|
void git_revpool_tableit_init(git_revpool_table *table, git_revpool_tableit *it);
|
||||||
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
144
src/revwalk.c
144
src/revwalk.c
@ -35,9 +35,9 @@ git_revpool *gitrp_alloc(git_odb *db)
|
|||||||
if (!walk)
|
if (!walk)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
memset(walk, 0x0, sizeof(git_revpool));
|
memset(walk, 0x0, sizeof(git_revpool));
|
||||||
|
|
||||||
walk->commits = git_revpool_table_create(default_table_size);
|
walk->commits = git_revpool_table_create(default_table_size);
|
||||||
|
|
||||||
walk->db = db;
|
walk->db = db;
|
||||||
return walk;
|
return walk;
|
||||||
@ -45,130 +45,126 @@ git_revpool *gitrp_alloc(git_odb *db)
|
|||||||
|
|
||||||
void gitrp_free(git_revpool *walk)
|
void gitrp_free(git_revpool *walk)
|
||||||
{
|
{
|
||||||
git_commit_list_clear(&(walk->iterator), 0);
|
git_commit_list_clear(&(walk->iterator), 0);
|
||||||
git_commit_list_clear(&(walk->roots), 0);
|
git_commit_list_clear(&(walk->roots), 0);
|
||||||
|
|
||||||
git_revpool_table_free(walk->commits);
|
git_revpool_table_free(walk->commits);
|
||||||
|
|
||||||
free(walk);
|
free(walk);
|
||||||
}
|
}
|
||||||
|
|
||||||
void gitrp_sorting(git_revpool *pool, unsigned int sort_mode)
|
void gitrp_sorting(git_revpool *pool, unsigned int sort_mode)
|
||||||
{
|
{
|
||||||
if (pool->walking)
|
if (pool->walking)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
pool->sorting = sort_mode;
|
pool->sorting = sort_mode;
|
||||||
gitrp_reset(pool);
|
gitrp_reset(pool);
|
||||||
}
|
}
|
||||||
|
|
||||||
void gitrp_push(git_revpool *pool, git_commit *commit)
|
void gitrp_push(git_revpool *pool, git_commit *commit)
|
||||||
{
|
{
|
||||||
if (commit == NULL || commit->seen)
|
if (commit == NULL || commit->seen)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (commit->object.pool != pool || pool->walking)
|
if (commit->object.pool != pool || pool->walking)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (!commit->parsed)
|
if (!commit->parsed) {
|
||||||
{
|
if (git_commit_parse_existing(commit) < 0)
|
||||||
if (git_commit_parse_existing(commit) < 0)
|
return;
|
||||||
return;
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// Sanity check: make sure that if the commit
|
// Sanity check: make sure that if the commit
|
||||||
// has been manually marked as uninteresting,
|
// has been manually marked as uninteresting,
|
||||||
// all the parent commits are too.
|
// all the parent commits are too.
|
||||||
if (commit->uninteresting)
|
if (commit->uninteresting)
|
||||||
git_commit__mark_uninteresting(commit);
|
git_commit__mark_uninteresting(commit);
|
||||||
|
|
||||||
git_commit_list_push_back(&pool->roots, commit);
|
git_commit_list_push_back(&pool->roots, commit);
|
||||||
}
|
}
|
||||||
|
|
||||||
void gitrp_hide(git_revpool *pool, git_commit *commit)
|
void gitrp_hide(git_revpool *pool, git_commit *commit)
|
||||||
{
|
{
|
||||||
if (pool->walking)
|
if (pool->walking)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
git_commit__mark_uninteresting(commit);
|
git_commit__mark_uninteresting(commit);
|
||||||
gitrp_push(pool, commit);
|
gitrp_push(pool, commit);
|
||||||
}
|
}
|
||||||
|
|
||||||
void gitrp__enroot(git_revpool *pool, git_commit *commit)
|
void gitrp__enroot(git_revpool *pool, git_commit *commit)
|
||||||
{
|
{
|
||||||
git_commit_node *parents;
|
git_commit_node *parents;
|
||||||
|
|
||||||
if (commit->seen)
|
if (commit->seen)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (commit->parsed == 0)
|
if (commit->parsed == 0)
|
||||||
git_commit_parse_existing(commit);
|
git_commit_parse_existing(commit);
|
||||||
|
|
||||||
commit->seen = 1;
|
commit->seen = 1;
|
||||||
|
|
||||||
for (parents = commit->parents.head; parents != NULL; parents = parents->next)
|
for (parents = commit->parents.head; parents != NULL; parents = parents->next) {
|
||||||
{
|
parents->commit->in_degree++;
|
||||||
parents->commit->in_degree++;
|
gitrp__enroot(pool, parents->commit);
|
||||||
gitrp__enroot(pool, parents->commit);
|
}
|
||||||
}
|
|
||||||
|
|
||||||
git_commit_list_push_back(&pool->iterator, commit);
|
git_commit_list_push_back(&pool->iterator, commit);
|
||||||
}
|
}
|
||||||
|
|
||||||
void gitrp__prepare_walk(git_revpool *pool)
|
void gitrp__prepare_walk(git_revpool *pool)
|
||||||
{
|
{
|
||||||
git_commit_node *it;
|
git_commit_node *it;
|
||||||
|
|
||||||
for (it = pool->roots.head; it != NULL; it = it->next)
|
for (it = pool->roots.head; it != NULL; it = it->next)
|
||||||
gitrp__enroot(pool, it->commit);
|
gitrp__enroot(pool, it->commit);
|
||||||
|
|
||||||
if (pool->sorting & GIT_RPSORT_TIME)
|
if (pool->sorting & GIT_RPSORT_TIME)
|
||||||
git_commit_list_timesort(&pool->iterator);
|
git_commit_list_timesort(&pool->iterator);
|
||||||
|
|
||||||
if (pool->sorting & GIT_RPSORT_TOPOLOGICAL)
|
if (pool->sorting & GIT_RPSORT_TOPOLOGICAL)
|
||||||
git_commit_list_toposort(&pool->iterator);
|
git_commit_list_toposort(&pool->iterator);
|
||||||
|
|
||||||
if (pool->sorting & GIT_RPSORT_REVERSE)
|
if (pool->sorting & GIT_RPSORT_REVERSE)
|
||||||
pool->next_commit = &git_commit_list_pop_back;
|
pool->next_commit = &git_commit_list_pop_back;
|
||||||
else
|
else
|
||||||
pool->next_commit = &git_commit_list_pop_front;
|
pool->next_commit = &git_commit_list_pop_front;
|
||||||
|
|
||||||
pool->walking = 1;
|
pool->walking = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
git_commit *gitrp_next(git_revpool *pool)
|
git_commit *gitrp_next(git_revpool *pool)
|
||||||
{
|
{
|
||||||
git_commit *next;
|
git_commit *next;
|
||||||
|
|
||||||
if (!pool->walking)
|
if (!pool->walking)
|
||||||
gitrp__prepare_walk(pool);
|
gitrp__prepare_walk(pool);
|
||||||
|
|
||||||
while ((next = pool->next_commit(&pool->iterator)) != NULL)
|
while ((next = pool->next_commit(&pool->iterator)) != NULL) {
|
||||||
{
|
if (!next->uninteresting)
|
||||||
if (!next->uninteresting)
|
return next;
|
||||||
return next;
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// No commits left to iterate
|
// No commits left to iterate
|
||||||
gitrp_reset(pool);
|
gitrp_reset(pool);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
void gitrp_reset(git_revpool *pool)
|
void gitrp_reset(git_revpool *pool)
|
||||||
{
|
{
|
||||||
git_commit *commit;
|
git_commit *commit;
|
||||||
git_revpool_tableit it;
|
git_revpool_tableit it;
|
||||||
|
|
||||||
git_revpool_tableit_init(pool->commits, &it);
|
git_revpool_tableit_init(pool->commits, &it);
|
||||||
|
|
||||||
while ((commit = (git_commit *)git_revpool_tableit_next(&it)) != NULL)
|
while ((commit = (git_commit *)git_revpool_tableit_next(&it)) != NULL) {
|
||||||
{
|
commit->seen = 0;
|
||||||
commit->seen = 0;
|
commit->topo_delay = 0;
|
||||||
commit->topo_delay = 0;
|
commit->in_degree = 0;
|
||||||
commit->in_degree = 0;
|
}
|
||||||
}
|
|
||||||
|
|
||||||
git_commit_list_clear(&pool->iterator, 0);
|
git_commit_list_clear(&pool->iterator, 0);
|
||||||
pool->walking = 0;
|
pool->walking = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -7,14 +7,14 @@
|
|||||||
struct git_revpool {
|
struct git_revpool {
|
||||||
git_odb *db;
|
git_odb *db;
|
||||||
|
|
||||||
git_commit_list iterator;
|
git_commit_list iterator;
|
||||||
git_commit *(*next_commit)(git_commit_list *);
|
git_commit *(*next_commit)(git_commit_list *);
|
||||||
|
|
||||||
git_commit_list roots;
|
git_commit_list roots;
|
||||||
git_revpool_table *commits;
|
git_revpool_table *commits;
|
||||||
|
|
||||||
unsigned walking:1;
|
unsigned walking:1;
|
||||||
unsigned char sorting;
|
unsigned char sorting;
|
||||||
};
|
};
|
||||||
|
|
||||||
void gitrp__prepare_walk(git_revpool *pool);
|
void gitrp__prepare_walk(git_revpool *pool);
|
||||||
|
Loading…
Reference in New Issue
Block a user