mirror of
https://github.com/git/git
synced 2024-08-27 19:49:21 +00:00
grep: allocate subrepos on heap
Currently, struct repository objects corresponding to submodules are allocated on the stack in grep_submodule(). This currently works because they will not be used once grep_submodule() exits, but a subsequent patch will require these structs to be accessible for longer (perhaps even in another thread). Allocate them on the heap and clear them only at the very end. Signed-off-by: Jonathan Tan <jonathantanmy@google.com> Reviewed-by: Matheus Tavares <matheus.bernardino@usp.br> Signed-off-by: Junio C Hamano <gitster@pobox.com>
This commit is contained in:
parent
78ca584f1c
commit
dd45471a37
|
@ -65,6 +65,9 @@ static int todo_done;
|
|||
/* Has all work items been added? */
|
||||
static int all_work_added;
|
||||
|
||||
static struct repository **repos_to_free;
|
||||
static size_t repos_to_free_nr, repos_to_free_alloc;
|
||||
|
||||
/* This lock protects all the variables above. */
|
||||
static pthread_mutex_t grep_mutex;
|
||||
|
||||
|
@ -168,6 +171,19 @@ static void work_done(struct work_item *w)
|
|||
grep_unlock();
|
||||
}
|
||||
|
||||
static void free_repos(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < repos_to_free_nr; i++) {
|
||||
repo_clear(repos_to_free[i]);
|
||||
free(repos_to_free[i]);
|
||||
}
|
||||
FREE_AND_NULL(repos_to_free);
|
||||
repos_to_free_nr = 0;
|
||||
repos_to_free_alloc = 0;
|
||||
}
|
||||
|
||||
static void *run(void *arg)
|
||||
{
|
||||
int hit = 0;
|
||||
|
@ -415,19 +431,24 @@ static int grep_submodule(struct grep_opt *opt,
|
|||
const struct object_id *oid,
|
||||
const char *filename, const char *path, int cached)
|
||||
{
|
||||
struct repository subrepo;
|
||||
struct repository *subrepo;
|
||||
struct repository *superproject = opt->repo;
|
||||
const struct submodule *sub;
|
||||
struct grep_opt subopt;
|
||||
int hit;
|
||||
int hit = 0;
|
||||
|
||||
sub = submodule_from_path(superproject, null_oid(), path);
|
||||
|
||||
if (!is_submodule_active(superproject, path))
|
||||
return 0;
|
||||
|
||||
if (repo_submodule_init(&subrepo, superproject, sub))
|
||||
subrepo = xmalloc(sizeof(*subrepo));
|
||||
if (repo_submodule_init(subrepo, superproject, sub)) {
|
||||
free(subrepo);
|
||||
return 0;
|
||||
}
|
||||
ALLOC_GROW(repos_to_free, repos_to_free_nr + 1, repos_to_free_alloc);
|
||||
repos_to_free[repos_to_free_nr++] = subrepo;
|
||||
|
||||
/*
|
||||
* NEEDSWORK: repo_read_gitmodules() might call
|
||||
|
@ -438,7 +459,7 @@ static int grep_submodule(struct grep_opt *opt,
|
|||
* subrepo's odbs to the in-memory alternates list.
|
||||
*/
|
||||
obj_read_lock();
|
||||
repo_read_gitmodules(&subrepo, 0);
|
||||
repo_read_gitmodules(subrepo, 0);
|
||||
|
||||
/*
|
||||
* NEEDSWORK: This adds the submodule's object directory to the list of
|
||||
|
@ -450,11 +471,11 @@ static int grep_submodule(struct grep_opt *opt,
|
|||
* store is no longer global and instead is a member of the repository
|
||||
* object.
|
||||
*/
|
||||
add_submodule_odb_by_path(subrepo.objects->odb->path);
|
||||
add_submodule_odb_by_path(subrepo->objects->odb->path);
|
||||
obj_read_unlock();
|
||||
|
||||
memcpy(&subopt, opt, sizeof(subopt));
|
||||
subopt.repo = &subrepo;
|
||||
subopt.repo = subrepo;
|
||||
|
||||
if (oid) {
|
||||
enum object_type object_type;
|
||||
|
@ -464,9 +485,9 @@ static int grep_submodule(struct grep_opt *opt,
|
|||
struct strbuf base = STRBUF_INIT;
|
||||
|
||||
obj_read_lock();
|
||||
object_type = oid_object_info(&subrepo, oid, NULL);
|
||||
object_type = oid_object_info(subrepo, oid, NULL);
|
||||
obj_read_unlock();
|
||||
data = read_object_with_reference(&subrepo,
|
||||
data = read_object_with_reference(subrepo,
|
||||
oid, tree_type,
|
||||
&size, NULL);
|
||||
if (!data)
|
||||
|
@ -484,7 +505,6 @@ static int grep_submodule(struct grep_opt *opt,
|
|||
hit = grep_cache(&subopt, pathspec, cached);
|
||||
}
|
||||
|
||||
repo_clear(&subrepo);
|
||||
return hit;
|
||||
}
|
||||
|
||||
|
@ -1182,5 +1202,6 @@ int cmd_grep(int argc, const char **argv, const char *prefix)
|
|||
run_pager(&opt, prefix);
|
||||
clear_pathspec(&pathspec);
|
||||
free_grep_patterns(&opt);
|
||||
free_repos();
|
||||
return !hit;
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue