summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLibravatar Pierre Habouzit <madcoder@debian.org>2007-09-17 14:00:38 +0200
committerLibravatar Junio C Hamano <gitster@pobox.com>2007-09-18 00:55:25 -0700
commit0557656930d41f10c90bccf90e3c5bd87bd53661 (patch)
tree7760bf79e58acdc0ba9305aa368b87b44fbb1686
parentfast-import was using dbuf's, replace them with strbuf's. (diff)
downloadtgif-0557656930d41f10c90bccf90e3c5bd87bd53661.tar.xz
fast-import optimization:
Now that cmd_data acts on a strbuf, make last_object stashed buffer be a strbuf as well. On new stash, don't free the last stashed buffer, rather swap it with the one you will stash, this way, callers of store_object can act on static strbufs, and at some point, fast-import won't allocate new memory for objects buffers. Signed-off-by: Junio C Hamano <gitster@pobox.com>
-rw-r--r--fast-import.c52
1 files changed, 20 insertions, 32 deletions
diff --git a/fast-import.c b/fast-import.c
index e456eab17c..e2a4834706 100644
--- a/fast-import.c
+++ b/fast-import.c
@@ -182,11 +182,10 @@ struct mark_set
struct last_object
{
- void *data;
- unsigned long len;
+ struct strbuf data;
uint32_t offset;
unsigned int depth;
- unsigned no_free:1;
+ unsigned no_swap : 1;
};
struct mem_pool
@@ -310,7 +309,7 @@ static struct mark_set *marks;
static const char* mark_file;
/* Our last blob */
-static struct last_object last_blob;
+static struct last_object last_blob = { STRBUF_INIT, 0, 0, 0 };
/* Tree management */
static unsigned int tree_entry_alloc = 1000;
@@ -950,9 +949,7 @@ static void end_packfile(void)
free(old_p);
/* We can't carry a delta across packfiles. */
- free(last_blob.data);
- last_blob.data = NULL;
- last_blob.len = 0;
+ strbuf_release(&last_blob.data);
last_blob.offset = 0;
last_blob.depth = 0;
}
@@ -1024,8 +1021,8 @@ static int store_object(
return 1;
}
- if (last && last->data && last->depth < max_depth) {
- delta = diff_delta(last->data, last->len,
+ if (last && last->data.buf && last->depth < max_depth) {
+ delta = diff_delta(last->data.buf, last->data.len,
dat->buf, dat->len,
&deltalen, 0);
if (delta && deltalen >= dat->len) {
@@ -1111,11 +1108,14 @@ static int store_object(
free(out);
free(delta);
if (last) {
- if (!last->no_free)
- free(last->data);
+ if (last->no_swap) {
+ last->data = *dat;
+ } else {
+ struct strbuf tmp = *dat;
+ *dat = last->data;
+ last->data = tmp;
+ }
last->offset = e->offset;
- last->data = dat->buf;
- last->len = dat->len;
}
return 0;
}
@@ -1242,7 +1242,7 @@ static void store_tree(struct tree_entry *root)
{
struct tree_content *t = root->tree;
unsigned int i, j, del;
- struct last_object lo;
+ struct last_object lo = { STRBUF_INIT, 0, 0, /* no_swap */ 1 };
struct object_entry *le;
if (!is_null_sha1(root->versions[1].sha1))
@@ -1254,19 +1254,11 @@ static void store_tree(struct tree_entry *root)
}
le = find_object(root->versions[0].sha1);
- if (!S_ISDIR(root->versions[0].mode)
- || !le
- || le->pack_id != pack_id) {
- lo.data = NULL;
- lo.depth = 0;
- lo.no_free = 0;
- } else {
+ if (S_ISDIR(root->versions[0].mode) && le && le->pack_id == pack_id) {
mktree(t, 0, &old_tree);
- lo.len = old_tree.len;
- lo.data = old_tree.buf;
+ lo.data = old_tree;
lo.offset = le->offset;
lo.depth = t->delta_depth;
- lo.no_free = 1;
}
mktree(t, 1, &new_tree);
@@ -1714,14 +1706,12 @@ static char *parse_ident(const char *buf)
static void cmd_new_blob(void)
{
- struct strbuf buf;
+ static struct strbuf buf = STRBUF_INIT;
read_next_command();
cmd_mark();
- strbuf_init(&buf, 0);
cmd_data(&buf);
- if (store_object(OBJ_BLOB, &buf, &last_blob, NULL, next_mark))
- strbuf_release(&buf);
+ store_object(OBJ_BLOB, &buf, &last_blob, NULL, next_mark);
}
static void unload_one_branch(void)
@@ -1817,15 +1807,13 @@ static void file_change_m(struct branch *b)
}
if (inline_data) {
- struct strbuf buf;
+ static struct strbuf buf = STRBUF_INIT;
if (!p_uq)
p = p_uq = xstrdup(p);
read_next_command();
- strbuf_init(&buf, 0);
cmd_data(&buf);
- if (store_object(OBJ_BLOB, &buf, &last_blob, sha1, 0))
- strbuf_release(&buf);
+ store_object(OBJ_BLOB, &buf, &last_blob, sha1, 0);
} else if (oe) {
if (oe->type != OBJ_BLOB)
die("Not a blob (actually a %s): %s",