From 2d4243996a4ace6d4eac1da460dd5bbcb31304ce Mon Sep 17 00:00:00 2001 From: Rusty Russell Date: Tue, 4 Jan 2011 21:11:47 +1030 Subject: [PATCH] ccanlint: compile modules required by examples. If an example #includes we assume it needs module foo, but we would fail instead of building it if it isn't built. --- tools/ccanlint/compulsory_tests/build.h | 1 + .../compulsory_tests/check_depends_built.c | 55 ++++++---- tools/ccanlint/tests/examples_compile.c | 102 +++++++++--------- 3 files changed, 86 insertions(+), 72 deletions(-) diff --git a/tools/ccanlint/compulsory_tests/build.h b/tools/ccanlint/compulsory_tests/build.h index 64abca44..633060db 100644 --- a/tools/ccanlint/compulsory_tests/build.h +++ b/tools/ccanlint/compulsory_tests/build.h @@ -1,4 +1,5 @@ #ifndef CCANLINT_BUILD_H #define CCANLINT_BUILD_H char *build_module(struct manifest *m, bool keep, char **errstr); +char *build_submodule(struct manifest *m); #endif /* CCANLINT_BUILD_H */ diff --git a/tools/ccanlint/compulsory_tests/check_depends_built.c b/tools/ccanlint/compulsory_tests/check_depends_built.c index 3bd82f83..b1ba40cb 100644 --- a/tools/ccanlint/compulsory_tests/check_depends_built.c +++ b/tools/ccanlint/compulsory_tests/check_depends_built.c @@ -50,41 +50,54 @@ static char *build_subdir_objs(struct manifest *m) return NULL; } +char *build_submodule(struct manifest *m) +{ + char *errstr; + struct stat st; + + if (m->compiled) + return NULL; + + if (!expect_obj_file(m)) + return NULL; + + m->compiled = talloc_asprintf(m, "%s.o", m->dir); + if (stat(m->compiled, &st) == 0) + return NULL; + + if (verbose >= 2) + printf(" Building dependency %s\n", m->dir); + + errstr = build_subdir_objs(m); + if (errstr) + return errstr; + + m->compiled = build_module(m, false, &errstr); + if (!m->compiled) + return errstr; + return NULL; +} + static void check_depends_built(struct manifest *m, bool keep, unsigned int *timeleft, struct score *score) { struct manifest *i; - struct stat st; list_for_each(&m->deps, i, list) { - char *errstr; - if (!expect_obj_file(i)) - continue; - - i->compiled = talloc_asprintf(i, "%s.o", i->dir); - if (stat(i->compiled, &st) == 0) - continue; - - if (verbose >= 2) - printf(" Building dependency %s\n", i->dir); - score->error = build_subdir_objs(i); - if (score->error) - return; - i->compiled = build_module(i, keep, &errstr); - if (!i->compiled) { + char *errstr = build_submodule(i); + + if (errstr) { score->error = talloc_asprintf(score, "Dependency %s" " did not build:\n%s", i->basename, errstr); return; - } + } } - if (!score->error) { - score->pass = true; - score->score = score->total; - } + score->pass = true; + score->score = score->total; } struct ccanlint depends_built = { diff --git a/tools/ccanlint/tests/examples_compile.c b/tools/ccanlint/tests/examples_compile.c index 768e96ae..5b0195d6 100644 --- a/tools/ccanlint/tests/examples_compile.c +++ b/tools/ccanlint/tests/examples_compile.c @@ -10,6 +10,8 @@ #include #include #include +#include +#include "../compulsory_tests/build.h" static const char *can_run(struct manifest *m) { @@ -20,85 +22,83 @@ static const char *can_run(struct manifest *m) return NULL; } -/* FIXME: We should build if it doesn't exist... */ -static bool expect_obj_file(const char *dir) +static void add_mod(struct manifest ***deps, struct manifest *m) { - struct manifest *dep_man; - bool has_c_files; - - dep_man = get_manifest(dir, dir); - - /* If it has C files, we expect an object file built from them. */ - has_c_files = !list_empty(&dep_man->c_files); - talloc_free(dep_man); - return has_c_files; + unsigned int num = talloc_get_size(*deps) / sizeof(*deps); + *deps = talloc_realloc(NULL, *deps, struct manifest *, num + 1); + (*deps)[num] = m; } -static char *add_dep(const struct manifest *m, char *list, const char *mod) +static bool have_mod(struct manifest *deps[], const char *basename) { - char **deps, *obj; unsigned int i; - /* Not ourselves. */ - if (streq(m->basename, mod)) - return list; + for (i = 0; i < talloc_get_size(deps) / sizeof(*deps); i++) + if (strcmp(deps[i]->basename, basename) == 0) + return true; + return false; +} - /* Not if there's no object file for that module */ - if (!expect_obj_file(talloc_asprintf(list, "%s/ccan/%s", ccan_dir,mod))) - return list; +static void add_dep(struct manifest ***deps, const char *basename) +{ + unsigned int i; + struct manifest *m; + char *errstr; - obj = talloc_asprintf(list, "%s/ccan/%s.o", ccan_dir, mod); + if (have_mod(*deps, basename)) + return; - /* Not anyone we've already included. */ - if (strstr(list, obj)) - return list; + m = get_manifest(*deps, talloc_asprintf(*deps, "%s/ccan/%s", + ccan_dir, basename)); + errstr = build_submodule(m); + if (errstr) + errx(1, "%s", errstr); - list = talloc_asprintf_append(list, " %s", obj); + add_mod(deps, m); /* Get that modules depends as well... */ assert(!safe_mode); - deps = get_deps(m, talloc_asprintf(list, "%s/ccan/%s", ccan_dir, mod), - false, NULL); + if (m->info_file) { + char **infodeps; + + infodeps = get_deps(m, m->dir, false, &m->info_file->compiled); - for (i = 0; deps[i]; i++) { - if (strstarts(deps[i], "ccan/")) - list = add_dep(m, list, deps[i] + strlen("ccan/")); + for (i = 0; infodeps[i]; i++) { + if (strstarts(infodeps[i], "ccan/")) + add_dep(deps, infodeps[i] + strlen("ccan/")); + } } - return list; } -/* FIXME: Merge this into one place. */ -static char *obj_list(const struct manifest *m, struct ccan_file *f) +static char *obj_list(struct manifest *m, struct ccan_file *f) { - char *list = talloc_strdup(m, ""); - struct manifest *subm; - char **lines; - - /* This module. */ - if (m->compiled) - list = talloc_asprintf_append(list, " %s", m->compiled); + struct manifest **deps = talloc_array(f, struct manifest *, 0); + char **lines, *list; + unsigned int i; - /* Other ccan modules we depend on. */ - list_for_each(&m->deps, subm, list) { - if (subm->compiled) - list = talloc_asprintf_append(list, " %s", - subm->compiled); - } + /* This one for a start. */ + add_dep(&deps, m->basename); /* Other modules implied by includes. */ for (lines = get_ccan_file_lines(f); *lines; lines++) { unsigned preflen = strspn(*lines, " \t"); if (strstarts(*lines + preflen, "#include compiled) + list = talloc_asprintf_append(list, " %s", + deps[i]->compiled); + } return list; } -- 2.39.2