revision.c: update show_object_with_name() without using malloc()

Allocating and then immediately freeing temporary memory a million times
when listing a million objects is distasteful.

Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:
Junio C Hamano 2011-08-17 14:30:35 -07:00
Родитель 91f175165a
Коммит beba25abbc
1 изменённых файлов: 36 добавлений и 14 удалений

Просмотреть файл

@ -40,23 +40,45 @@ char *path_name(const struct name_path *path, const char *name)
return n;
}
static int show_path_component_truncated(FILE *out, const char *name, int len)
{
int cnt;
for (cnt = 0; cnt < len; cnt++) {
int ch = name[cnt];
if (!ch || ch == '\n')
return -1;
fputc(ch, out);
}
return len;
}
static int show_path_truncated(FILE *out, const struct name_path *path)
{
int emitted, ours;
if (!path)
return 0;
emitted = show_path_truncated(out, path->up);
if (emitted < 0)
return emitted;
if (emitted)
fputc('/', out);
ours = show_path_component_truncated(out, path->elem, path->elem_len);
if (ours < 0)
return ours;
return ours || emitted;
}
void show_object_with_name(FILE *out, struct object *obj, const struct name_path *path, const char *component)
{
char *name = path_name(path, component);
const char *ep = strchr(name, '\n');
struct name_path leaf;
leaf.up = (struct name_path *)path;
leaf.elem = component;
leaf.elem_len = strlen(component);
/*
* An object with name "foo\n0000000..." can be used to
* confuse downstream "git pack-objects" very badly.
*/
if (ep) {
fprintf(out, "%s %.*s\n", sha1_to_hex(obj->sha1),
(int) (ep - name),
name);
}
else
fprintf(out, "%s %s\n", sha1_to_hex(obj->sha1), name);
free(name);
fprintf(out, "%s ", sha1_to_hex(obj->sha1));
show_path_truncated(out, &leaf);
fputc('\n', out);
}
void add_object(struct object *obj,