From: Rusty Russell Date: Wed, 7 Oct 2009 12:30:53 +0000 (+1030) Subject: tools/ccanlint: build tests are now compulsory X-Git-Url: https://git.ozlabs.org/?p=ccan;a=commitdiff_plain;h=5f44c8ca0eb66503db51e0df1b65ff173eb42f57 tools/ccanlint: build tests are now compulsory Offer to run debugger when test fails, with breakpoint. --- diff --git a/tools/ccanlint/ccanlint.c b/tools/ccanlint/ccanlint.c index 4590ba8c..a0fda1a8 100644 --- a/tools/ccanlint/ccanlint.c +++ b/tools/ccanlint/ccanlint.c @@ -241,7 +241,7 @@ int main(int argc, char *argv[]) { int c; bool summary = false; - unsigned int score, total_score; + unsigned int score = 0, total_score = 0; struct manifest *m; struct ccanlint *i; const char *prefix = ""; @@ -290,7 +290,6 @@ int main(int argc, char *argv[]) if (verbose) printf("\nNormal tests:\n"); - score = total_score = 0; while ((i = get_next_test(&normal_tests)) != NULL) run_test(i, summary, &score, &total_score, m); diff --git a/tools/ccanlint/compulsory_tests/build.c b/tools/ccanlint/compulsory_tests/build.c new file mode 100644 index 00000000..1b3d8789 --- /dev/null +++ b/tools/ccanlint/compulsory_tests/build.c @@ -0,0 +1,72 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static const char *can_build(struct manifest *m) +{ + if (safe_mode) + return "Safe mode enabled"; + return NULL; +} + +static char *obj_list(const struct manifest *m) +{ + char *list = talloc_strdup(m, ""); + struct ccan_file *i; + + /* Objects from all the C files. */ + list_for_each(&m->c_files, i, list) + list = talloc_asprintf_append(list, "%s ", i->compiled); + + return list; +} + +static void *do_build(struct manifest *m) +{ + char *filename, *err; + + if (list_empty(&m->c_files)) { + /* No files? No score, but we "pass". */ + build.total_score = 0; + return NULL; + } + filename = link_objects(m, obj_list(m), &err); + if (filename) { + char *realname = talloc_asprintf(m, "../%s.o", m->basename); + /* We leave this object file around, all built. */ + if (rename(filename, realname) != 0) + return talloc_asprintf(m, "Failed to rename %s to %s", + filename, realname); + return NULL; + } + return err; +} + +static const char *describe_build(struct manifest *m, void *check_result) +{ + return talloc_asprintf(check_result, + "The object file for the module didn't build:\n" + "%s", (char *)check_result); +} + +struct ccanlint build = { + .name = "Module can be built", + .total_score = 1, + .check = do_build, + .describe = describe_build, + .can_run = can_build, +}; + +REGISTER_TEST(build, &depends_built, NULL); diff --git a/tools/ccanlint/compulsory_tests/build_objs.c b/tools/ccanlint/compulsory_tests/build_objs.c new file mode 100644 index 00000000..2f189e85 --- /dev/null +++ b/tools/ccanlint/compulsory_tests/build_objs.c @@ -0,0 +1,58 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static const char *can_build(struct manifest *m) +{ + if (safe_mode) + return "Safe mode enabled"; + return NULL; +} + +static void *check_objs_build(struct manifest *m) +{ + char *report = NULL; + struct ccan_file *i; + + list_for_each(&m->c_files, i, list) { + char *err; + + /* One point for each obj file. */ + build_objs.total_score++; + + i->compiled = compile_object(m, i->name, &err); + if (!i->compiled) { + if (report) + report = talloc_append_string(report, err); + else + report = err; + } + } + return report; +} + +static const char *describe_objs_build(struct manifest *m, void *check_result) +{ + return check_result; +} + +struct ccanlint build_objs = { + .name = "Module object files can be built", + .check = check_objs_build, + .describe = describe_objs_build, + .can_run = can_build, +}; + +REGISTER_TEST(build_objs, &depends_exist, NULL); diff --git a/tools/ccanlint/compulsory_tests/check_build.c b/tools/ccanlint/compulsory_tests/check_build.c new file mode 100644 index 00000000..eb968e11 --- /dev/null +++ b/tools/ccanlint/compulsory_tests/check_build.c @@ -0,0 +1,93 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static const char *can_build(struct manifest *m) +{ + if (safe_mode) + return "Safe mode enabled"; + return NULL; +} + +static char *obj_list(const struct manifest *m) +{ + char *list = talloc_strdup(m, ""); + struct ccan_file *i; + + /* Other CCAN deps. */ + list_for_each(&m->dep_objs, i, list) + list = talloc_asprintf_append(list, "%s ", i->name); + + return list; +} + +static char *lib_list(const struct manifest *m) +{ + unsigned int i, num; + char **libs = get_libs(m, ".", ".", &num, &m->info_file->compiled); + char *ret = talloc_strdup(m, ""); + + for (i = 0; i < num; i++) + ret = talloc_asprintf_append(ret, "-l%s ", libs[i]); + return ret; +} + +static void *check_use_build(struct manifest *m) +{ + char *contents; + char *tmpfile, *err; + int fd; + + tmpfile = temp_file(m, ".c"); + + fd = open(tmpfile, O_WRONLY | O_CREAT | O_EXCL, 0600); + if (fd < 0) + return talloc_asprintf(m, "Creating temporary file: %s", + strerror(errno)); + + contents = talloc_asprintf(tmpfile, + "#include \n" + "int main(void)\n" + "{\n" + " return 0;\n" + "}\n", + m->basename, m->basename); + if (write(fd, contents, strlen(contents)) != strlen(contents)) { + close(fd); + return "Failure writing to temporary file"; + } + close(fd); + + if (!compile_and_link(m, tmpfile, obj_list(m), "", lib_list(m), &err)) + return err; + return NULL; +} + +static const char *describe_use_build(struct manifest *m, void *check_result) +{ + return talloc_asprintf(check_result, + "Linking against module:\n" + "%s", (char *)check_result); +} + +struct ccanlint check_build = { + .name = "Module can be used", + .total_score = 1, + .check = check_use_build, + .describe = describe_use_build, + .can_run = can_build, +}; + +REGISTER_TEST(check_build, &build, NULL); diff --git a/tools/ccanlint/compulsory_tests/check_depends_built.c b/tools/ccanlint/compulsory_tests/check_depends_built.c new file mode 100644 index 00000000..1392be91 --- /dev/null +++ b/tools/ccanlint/compulsory_tests/check_depends_built.c @@ -0,0 +1,103 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static const char *can_build(struct manifest *m) +{ + if (safe_mode) + return "Safe mode enabled"; + return NULL; +} + +/* FIXME: recursive ccanlint if they ask for it. */ +static bool expect_obj_file(const char *dir) +{ + char *olddir; + struct manifest *dep_man; + bool has_c_files; + + olddir = talloc_getcwd(dir); + if (!olddir) + err(1, "Getting current directory"); + + /* We will fail below if this doesn't exist. */ + if (chdir(dir) != 0) + return false; + + dep_man = get_manifest(dir); + if (chdir(olddir) != 0) + err(1, "Returning to original directory '%s'", olddir); + talloc_free(olddir); + + /* 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; +} + +static void *check_depends_built(struct manifest *m) +{ + struct ccan_file *i; + struct stat st; + char *report = NULL; + + list_for_each(&m->dep_dirs, i, list) { + char *objfile; + + if (!expect_obj_file(i->name)) + continue; + + objfile = talloc_asprintf(m, "%s.o", i->name); + if (stat(objfile, &st) != 0) { + report = talloc_asprintf_append(report, + "object file %s\n", + objfile); + } else { + struct ccan_file *f = new_ccan_file(m, objfile); + list_add_tail(&m->dep_objs, &f->list); + } + + } + + /* We may need libtap for testing, unless we're "tap" */ + if (!streq(m->basename, "tap") + && (!list_empty(&m->run_tests) || !list_empty(&m->api_tests))) { + if (stat("../tap.o", &st) != 0) { + report = talloc_asprintf_append(report, + "object file ../tap.o" + " (for tests)\n"); + } + } + + return talloc_steal(m, report); +} + +static const char *describe_depends_built(struct manifest *m, + void *check_result) +{ + return talloc_asprintf(check_result, + "The following dependencies are not built:\n" + "%s", (char *)check_result); +} + +struct ccanlint depends_built = { + .name = "CCAN dependencies are built", + .total_score = 1, + .check = check_depends_built, + .describe = describe_depends_built, + .can_run = can_build, +}; + +REGISTER_TEST(depends_built, &depends_exist, NULL); diff --git a/tools/ccanlint/compulsory_tests/check_depends_exist.c b/tools/ccanlint/compulsory_tests/check_depends_exist.c new file mode 100644 index 00000000..2ac60a2a --- /dev/null +++ b/tools/ccanlint/compulsory_tests/check_depends_exist.c @@ -0,0 +1,73 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static char *add_dep(char *sofar, struct manifest *m, const char *dep) +{ + char *dir; + struct stat st; + struct ccan_file *f; + + dir = talloc_asprintf(m, "../%s", dep); + if (stat(dir, &st) != 0) { + return talloc_asprintf_append(sofar, + "ccan/%s: expected it in" + " directory %s\n", + dep, dir); + } + + f = new_ccan_file(m, dir); + list_add_tail(&m->dep_dirs, &f->list); + return sofar; +} + +static void *check_depends_exist(struct manifest *m) +{ + unsigned int i; + char *report = NULL; + char **deps; + + if (safe_mode) + deps = get_safe_ccan_deps(m, "..", m->basename, true, + &m->info_file->compiled); + else + deps = get_deps(m, "..", m->basename, true, + &m->info_file->compiled); + + for (i = 0; deps[i]; i++) { + if (!strstarts(deps[i], "ccan/")) + continue; + + report = add_dep(report, m, deps[i] + strlen("ccan/")); + } + return report; +} + +static const char *describe_depends_exist(struct manifest *m, + void *check_result) +{ + return talloc_asprintf(check_result, + "The following dependencies are are expected:\n" + "%s", (char *)check_result); +} + +struct ccanlint depends_exist = { + .name = "CCAN dependencies are present", + .total_score = 1, + .check = check_depends_exist, + .describe = describe_depends_exist, +}; + +REGISTER_TEST(depends_exist, NULL); diff --git a/tools/ccanlint/compulsory_tests/check_includes_build.c b/tools/ccanlint/compulsory_tests/check_includes_build.c new file mode 100644 index 00000000..7e0ab945 --- /dev/null +++ b/tools/ccanlint/compulsory_tests/check_includes_build.c @@ -0,0 +1,67 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static const char *can_build(struct manifest *m) +{ + if (safe_mode) + return "Safe mode enabled"; + return NULL; +} + +static void *check_includes_build(struct manifest *m) +{ + char *contents; + char *tmpfile, *err; + int fd; + + tmpfile = temp_file(m, ".c"); + + fd = open(tmpfile, O_WRONLY | O_CREAT | O_EXCL, 0600); + if (fd < 0) + return talloc_asprintf(m, "Creating temporary file: %s", + strerror(errno)); + + contents = talloc_asprintf(tmpfile, "#include \n", + m->basename, m->basename); + if (write(fd, contents, strlen(contents)) != strlen(contents)) { + close(fd); + return "Failure writing to temporary file"; + } + close(fd); + + if (compile_object(m, tmpfile, &err)) + return NULL; + return err; +} + +static const char *describe_includes_build(struct manifest *m, + void *check_result) +{ + return talloc_asprintf(check_result, + "#include of the main header file:\n" + "%s", (char *)check_result); +} + +struct ccanlint includes_build = { + .name = "Can compile against main header", + .total_score = 1, + .check = check_includes_build, + .describe = describe_includes_build, + .can_run = can_build, +}; + +REGISTER_TEST(includes_build, &depends_exist, NULL); diff --git a/tools/ccanlint/compulsory_tests/compile_test_helpers.c b/tools/ccanlint/compulsory_tests/compile_test_helpers.c new file mode 100644 index 00000000..de8d4632 --- /dev/null +++ b/tools/ccanlint/compulsory_tests/compile_test_helpers.c @@ -0,0 +1,65 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static const char *can_build(struct manifest *m) +{ + if (safe_mode) + return "Safe mode enabled"; + return NULL; +} + +static char *compile(struct manifest *m, struct ccan_file *cfile) +{ + char *err; + + cfile->compiled = compile_object(m, cfile->name, &err); + if (cfile->compiled) + return NULL; + return err; +} + +static void *do_compile_test_helpers(struct manifest *m) +{ + char *cmdout = NULL; + struct ccan_file *i; + + list_for_each(&m->other_test_c_files, i, list) { + compile_tests.total_score++; + cmdout = compile(m, i); + if (cmdout) + return talloc_asprintf(m, + "Failed to compile helper C" + " code file %s:\n%s", + i->name, cmdout); + } + return NULL; +} + +static const char *describe_compile_test_helpers(struct manifest *m, + void *check_result) +{ + return check_result; +} + +struct ccanlint compile_test_helpers = { + .name = "Compiling test helper files", + .total_score = 1, + .check = do_compile_test_helpers, + .describe = describe_compile_test_helpers, + .can_run = can_build, +}; + +REGISTER_TEST(compile_test_helpers, &depends_built); diff --git a/tools/ccanlint/compulsory_tests/compile_tests.c b/tools/ccanlint/compulsory_tests/compile_tests.c new file mode 100644 index 00000000..57c257a2 --- /dev/null +++ b/tools/ccanlint/compulsory_tests/compile_tests.c @@ -0,0 +1,192 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static const char *can_build(struct manifest *m) +{ + if (safe_mode) + return "Safe mode enabled"; + return NULL; +} + +static char *obj_list(const struct manifest *m, bool link_with_module) +{ + char *list; + struct ccan_file *i; + + /* We expect to be linked with tap, unless that's us. */ + if (!streq(m->basename, "tap")) + list = talloc_strdup(m, "../tap.o"); + else + list = talloc_strdup(m, ""); + + /* Objects from any other C files. */ + list_for_each(&m->other_test_c_files, i, list) + list = talloc_asprintf_append(list, " %s", i->compiled); + + if (link_with_module) + list = talloc_asprintf_append(list, " ../%s.o", m->basename); + + /* Other ccan modules. */ + list_for_each(&m->dep_objs, i, list) + list = talloc_asprintf_append(list, " %s", i->name); + + return list; +} + +static char *lib_list(const struct manifest *m) +{ + unsigned int i, num; + char **libs = get_libs(m, ".", ".", &num, &m->info_file->compiled); + char *ret = talloc_strdup(m, ""); + + for (i = 0; i < num; i++) + ret = talloc_asprintf_append(ret, "-l%s ", libs[i]); + return ret; +} + +static char *compile(const void *ctx, + struct manifest *m, struct ccan_file *file, bool fail, + bool link_with_module) +{ + char *errmsg; + + file->compiled = compile_and_link(ctx, file->name, + obj_list(m, link_with_module), + fail ? "-DFAIL" : "", + lib_list(m), &errmsg); + if (!file->compiled) + return errmsg; + talloc_steal(ctx, file->compiled); + return NULL; +} + +struct compile_tests_result { + struct list_node list; + const char *filename; + const char *description; + const char *output; +}; + +static void *do_compile_tests(struct manifest *m) +{ + struct list_head *list = talloc(m, struct list_head); + char *cmdout; + struct ccan_file *i; + struct compile_tests_result *res; + + list_head_init(list); + + list_for_each(&m->compile_ok_tests, i, list) { + compile_tests.total_score++; + cmdout = compile(list, m, i, false, false); + if (cmdout) { + res = talloc(list, struct compile_tests_result); + res->filename = i->name; + res->description = "failed to compile"; + res->output = talloc_steal(res, cmdout); + list_add_tail(list, &res->list); + } + } + + list_for_each(&m->run_tests, i, list) { + compile_tests.total_score++; + cmdout = compile(m, m, i, false, false); + if (cmdout) { + res = talloc(list, struct compile_tests_result); + res->filename = i->name; + res->description = "failed to compile"; + res->output = talloc_steal(res, cmdout); + list_add_tail(list, &res->list); + } + } + + list_for_each(&m->api_tests, i, list) { + compile_tests.total_score++; + cmdout = compile(m, m, i, false, true); + if (cmdout) { + res = talloc(list, struct compile_tests_result); + res->filename = i->name; + res->description = "failed to compile"; + res->output = talloc_steal(res, cmdout); + list_add_tail(list, &res->list); + } + } + + list_for_each(&m->compile_fail_tests, i, list) { + compile_tests.total_score++; + cmdout = compile(list, m, i, false, false); + if (cmdout) { + res = talloc(list, struct compile_tests_result); + res->filename = i->name; + res->description = "failed to compile without -DFAIL"; + res->output = talloc_steal(res, cmdout); + list_add_tail(list, &res->list); + } else { + cmdout = compile(list, m, i, true, false); + if (!cmdout) { + res = talloc(list, struct compile_tests_result); + res->filename = i->name; + res->description = "compiled successfully" + " with -DFAIL"; + res->output = ""; + list_add_tail(list, &res->list); + } + } + } + + if (list_empty(list)) { + talloc_free(list); + list = NULL; + } + + return list; +} + +static unsigned int score_compile_tests(struct manifest *m, + void *check_result) +{ + struct list_head *list = check_result; + struct compile_tests_result *i; + unsigned int score = compile_tests.total_score; + + list_for_each(list, i, list) + score--; + return score; +} + +static const char *describe_compile_tests(struct manifest *m, + void *check_result) +{ + struct list_head *list = check_result; + struct compile_tests_result *i; + char *descrip = talloc_strdup(list, "Compilation tests failed:\n"); + + list_for_each(list, i, list) + descrip = talloc_asprintf_append(descrip, "%s %s\n%s", + i->filename, i->description, + i->output); + return descrip; +} + +struct ccanlint compile_tests = { + .name = "Compile tests succeed", + .score = score_compile_tests, + .check = do_compile_tests, + .describe = describe_compile_tests, + .can_run = can_build, +}; + +REGISTER_TEST(compile_tests, &compile_test_helpers, NULL); diff --git a/tools/ccanlint/compulsory_tests/run_tests.c b/tools/ccanlint/compulsory_tests/run_tests.c new file mode 100644 index 00000000..b3c1188d --- /dev/null +++ b/tools/ccanlint/compulsory_tests/run_tests.c @@ -0,0 +1,119 @@ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +static const char *can_run(struct manifest *m) +{ + if (safe_mode) + return "Safe mode enabled"; + return NULL; +} + +struct run_tests_result { + struct list_node list; + struct ccan_file *file; + const char *output; +}; + +static void *do_run_tests(struct manifest *m) +{ + struct list_head *list = talloc(m, struct list_head); + struct run_tests_result *res; + struct ccan_file *i; + char *cmdout; + + list_head_init(list); + + list_for_each(&m->run_tests, i, list) { + run_tests.total_score++; + /* FIXME: timeout here */ + cmdout = run_command(m, i->compiled); + if (cmdout) { + res = talloc(list, struct run_tests_result); + res->file = i; + res->output = talloc_steal(res, cmdout); + list_add_tail(list, &res->list); + } + } + + list_for_each(&m->api_tests, i, list) { + run_tests.total_score++; + /* FIXME: timeout here */ + cmdout = run_command(m, i->compiled); + if (cmdout) { + res = talloc(list, struct run_tests_result); + res->file = i; + res->output = talloc_steal(res, cmdout); + list_add_tail(list, &res->list); + } + } + + if (list_empty(list)) { + talloc_free(list); + list = NULL; + } + + return list; +} + +static unsigned int score_run_tests(struct manifest *m, void *check_result) +{ + struct list_head *list = check_result; + struct run_tests_result *i; + unsigned int score = run_tests.total_score; + + list_for_each(list, i, list) + score--; + return score; +} + +static const char *describe_run_tests(struct manifest *m, + void *check_result) +{ + struct list_head *list = check_result; + char *descrip = talloc_strdup(check_result, "Running tests failed:\n"); + struct run_tests_result *i; + + list_for_each(list, i, list) + descrip = talloc_asprintf_append(descrip, "Running %s:\n%s", + i->file->name, i->output); + return descrip; +} + +static void run_under_debugger(struct manifest *m, void *check_result) +{ + char *command; + struct list_head *list = check_result; + struct run_tests_result *first; + + if (!ask("Should I run the first failing test under the debugger?")) + return; + + first = list_top(list, struct run_tests_result, list); + command = talloc_asprintf(m, "gdb -ex 'break tap.c:136' -ex 'run' %s", + first->file->compiled); + system(command); +} + +struct ccanlint run_tests = { + .name = "run and api tests run successfully", + .score = score_run_tests, + .check = do_run_tests, + .describe = describe_run_tests, + .can_run = can_run, + .handle = run_under_debugger +}; + +REGISTER_TEST(run_tests, &compile_tests, NULL); diff --git a/tools/ccanlint/tests/build.c b/tools/ccanlint/tests/build.c deleted file mode 100644 index 1b3d8789..00000000 --- a/tools/ccanlint/tests/build.c +++ /dev/null @@ -1,72 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static const char *can_build(struct manifest *m) -{ - if (safe_mode) - return "Safe mode enabled"; - return NULL; -} - -static char *obj_list(const struct manifest *m) -{ - char *list = talloc_strdup(m, ""); - struct ccan_file *i; - - /* Objects from all the C files. */ - list_for_each(&m->c_files, i, list) - list = talloc_asprintf_append(list, "%s ", i->compiled); - - return list; -} - -static void *do_build(struct manifest *m) -{ - char *filename, *err; - - if (list_empty(&m->c_files)) { - /* No files? No score, but we "pass". */ - build.total_score = 0; - return NULL; - } - filename = link_objects(m, obj_list(m), &err); - if (filename) { - char *realname = talloc_asprintf(m, "../%s.o", m->basename); - /* We leave this object file around, all built. */ - if (rename(filename, realname) != 0) - return talloc_asprintf(m, "Failed to rename %s to %s", - filename, realname); - return NULL; - } - return err; -} - -static const char *describe_build(struct manifest *m, void *check_result) -{ - return talloc_asprintf(check_result, - "The object file for the module didn't build:\n" - "%s", (char *)check_result); -} - -struct ccanlint build = { - .name = "Module can be built", - .total_score = 1, - .check = do_build, - .describe = describe_build, - .can_run = can_build, -}; - -REGISTER_TEST(build, &depends_built, NULL); diff --git a/tools/ccanlint/tests/build_objs.c b/tools/ccanlint/tests/build_objs.c deleted file mode 100644 index 2f189e85..00000000 --- a/tools/ccanlint/tests/build_objs.c +++ /dev/null @@ -1,58 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static const char *can_build(struct manifest *m) -{ - if (safe_mode) - return "Safe mode enabled"; - return NULL; -} - -static void *check_objs_build(struct manifest *m) -{ - char *report = NULL; - struct ccan_file *i; - - list_for_each(&m->c_files, i, list) { - char *err; - - /* One point for each obj file. */ - build_objs.total_score++; - - i->compiled = compile_object(m, i->name, &err); - if (!i->compiled) { - if (report) - report = talloc_append_string(report, err); - else - report = err; - } - } - return report; -} - -static const char *describe_objs_build(struct manifest *m, void *check_result) -{ - return check_result; -} - -struct ccanlint build_objs = { - .name = "Module object files can be built", - .check = check_objs_build, - .describe = describe_objs_build, - .can_run = can_build, -}; - -REGISTER_TEST(build_objs, &depends_exist, NULL); diff --git a/tools/ccanlint/tests/check_build.c b/tools/ccanlint/tests/check_build.c deleted file mode 100644 index eb968e11..00000000 --- a/tools/ccanlint/tests/check_build.c +++ /dev/null @@ -1,93 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static const char *can_build(struct manifest *m) -{ - if (safe_mode) - return "Safe mode enabled"; - return NULL; -} - -static char *obj_list(const struct manifest *m) -{ - char *list = talloc_strdup(m, ""); - struct ccan_file *i; - - /* Other CCAN deps. */ - list_for_each(&m->dep_objs, i, list) - list = talloc_asprintf_append(list, "%s ", i->name); - - return list; -} - -static char *lib_list(const struct manifest *m) -{ - unsigned int i, num; - char **libs = get_libs(m, ".", ".", &num, &m->info_file->compiled); - char *ret = talloc_strdup(m, ""); - - for (i = 0; i < num; i++) - ret = talloc_asprintf_append(ret, "-l%s ", libs[i]); - return ret; -} - -static void *check_use_build(struct manifest *m) -{ - char *contents; - char *tmpfile, *err; - int fd; - - tmpfile = temp_file(m, ".c"); - - fd = open(tmpfile, O_WRONLY | O_CREAT | O_EXCL, 0600); - if (fd < 0) - return talloc_asprintf(m, "Creating temporary file: %s", - strerror(errno)); - - contents = talloc_asprintf(tmpfile, - "#include \n" - "int main(void)\n" - "{\n" - " return 0;\n" - "}\n", - m->basename, m->basename); - if (write(fd, contents, strlen(contents)) != strlen(contents)) { - close(fd); - return "Failure writing to temporary file"; - } - close(fd); - - if (!compile_and_link(m, tmpfile, obj_list(m), "", lib_list(m), &err)) - return err; - return NULL; -} - -static const char *describe_use_build(struct manifest *m, void *check_result) -{ - return talloc_asprintf(check_result, - "Linking against module:\n" - "%s", (char *)check_result); -} - -struct ccanlint check_build = { - .name = "Module can be used", - .total_score = 1, - .check = check_use_build, - .describe = describe_use_build, - .can_run = can_build, -}; - -REGISTER_TEST(check_build, &build, NULL); diff --git a/tools/ccanlint/tests/check_depends_built.c b/tools/ccanlint/tests/check_depends_built.c deleted file mode 100644 index 1392be91..00000000 --- a/tools/ccanlint/tests/check_depends_built.c +++ /dev/null @@ -1,103 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static const char *can_build(struct manifest *m) -{ - if (safe_mode) - return "Safe mode enabled"; - return NULL; -} - -/* FIXME: recursive ccanlint if they ask for it. */ -static bool expect_obj_file(const char *dir) -{ - char *olddir; - struct manifest *dep_man; - bool has_c_files; - - olddir = talloc_getcwd(dir); - if (!olddir) - err(1, "Getting current directory"); - - /* We will fail below if this doesn't exist. */ - if (chdir(dir) != 0) - return false; - - dep_man = get_manifest(dir); - if (chdir(olddir) != 0) - err(1, "Returning to original directory '%s'", olddir); - talloc_free(olddir); - - /* 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; -} - -static void *check_depends_built(struct manifest *m) -{ - struct ccan_file *i; - struct stat st; - char *report = NULL; - - list_for_each(&m->dep_dirs, i, list) { - char *objfile; - - if (!expect_obj_file(i->name)) - continue; - - objfile = talloc_asprintf(m, "%s.o", i->name); - if (stat(objfile, &st) != 0) { - report = talloc_asprintf_append(report, - "object file %s\n", - objfile); - } else { - struct ccan_file *f = new_ccan_file(m, objfile); - list_add_tail(&m->dep_objs, &f->list); - } - - } - - /* We may need libtap for testing, unless we're "tap" */ - if (!streq(m->basename, "tap") - && (!list_empty(&m->run_tests) || !list_empty(&m->api_tests))) { - if (stat("../tap.o", &st) != 0) { - report = talloc_asprintf_append(report, - "object file ../tap.o" - " (for tests)\n"); - } - } - - return talloc_steal(m, report); -} - -static const char *describe_depends_built(struct manifest *m, - void *check_result) -{ - return talloc_asprintf(check_result, - "The following dependencies are not built:\n" - "%s", (char *)check_result); -} - -struct ccanlint depends_built = { - .name = "CCAN dependencies are built", - .total_score = 1, - .check = check_depends_built, - .describe = describe_depends_built, - .can_run = can_build, -}; - -REGISTER_TEST(depends_built, &depends_exist, NULL); diff --git a/tools/ccanlint/tests/check_depends_exist.c b/tools/ccanlint/tests/check_depends_exist.c deleted file mode 100644 index 2ac60a2a..00000000 --- a/tools/ccanlint/tests/check_depends_exist.c +++ /dev/null @@ -1,73 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static char *add_dep(char *sofar, struct manifest *m, const char *dep) -{ - char *dir; - struct stat st; - struct ccan_file *f; - - dir = talloc_asprintf(m, "../%s", dep); - if (stat(dir, &st) != 0) { - return talloc_asprintf_append(sofar, - "ccan/%s: expected it in" - " directory %s\n", - dep, dir); - } - - f = new_ccan_file(m, dir); - list_add_tail(&m->dep_dirs, &f->list); - return sofar; -} - -static void *check_depends_exist(struct manifest *m) -{ - unsigned int i; - char *report = NULL; - char **deps; - - if (safe_mode) - deps = get_safe_ccan_deps(m, "..", m->basename, true, - &m->info_file->compiled); - else - deps = get_deps(m, "..", m->basename, true, - &m->info_file->compiled); - - for (i = 0; deps[i]; i++) { - if (!strstarts(deps[i], "ccan/")) - continue; - - report = add_dep(report, m, deps[i] + strlen("ccan/")); - } - return report; -} - -static const char *describe_depends_exist(struct manifest *m, - void *check_result) -{ - return talloc_asprintf(check_result, - "The following dependencies are are expected:\n" - "%s", (char *)check_result); -} - -struct ccanlint depends_exist = { - .name = "CCAN dependencies are present", - .total_score = 1, - .check = check_depends_exist, - .describe = describe_depends_exist, -}; - -REGISTER_TEST(depends_exist, NULL); diff --git a/tools/ccanlint/tests/check_includes_build.c b/tools/ccanlint/tests/check_includes_build.c deleted file mode 100644 index 7e0ab945..00000000 --- a/tools/ccanlint/tests/check_includes_build.c +++ /dev/null @@ -1,67 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static const char *can_build(struct manifest *m) -{ - if (safe_mode) - return "Safe mode enabled"; - return NULL; -} - -static void *check_includes_build(struct manifest *m) -{ - char *contents; - char *tmpfile, *err; - int fd; - - tmpfile = temp_file(m, ".c"); - - fd = open(tmpfile, O_WRONLY | O_CREAT | O_EXCL, 0600); - if (fd < 0) - return talloc_asprintf(m, "Creating temporary file: %s", - strerror(errno)); - - contents = talloc_asprintf(tmpfile, "#include \n", - m->basename, m->basename); - if (write(fd, contents, strlen(contents)) != strlen(contents)) { - close(fd); - return "Failure writing to temporary file"; - } - close(fd); - - if (compile_object(m, tmpfile, &err)) - return NULL; - return err; -} - -static const char *describe_includes_build(struct manifest *m, - void *check_result) -{ - return talloc_asprintf(check_result, - "#include of the main header file:\n" - "%s", (char *)check_result); -} - -struct ccanlint includes_build = { - .name = "Can compile against main header", - .total_score = 1, - .check = check_includes_build, - .describe = describe_includes_build, - .can_run = can_build, -}; - -REGISTER_TEST(includes_build, &depends_exist, NULL); diff --git a/tools/ccanlint/tests/compile_test_helpers.c b/tools/ccanlint/tests/compile_test_helpers.c deleted file mode 100644 index de8d4632..00000000 --- a/tools/ccanlint/tests/compile_test_helpers.c +++ /dev/null @@ -1,65 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static const char *can_build(struct manifest *m) -{ - if (safe_mode) - return "Safe mode enabled"; - return NULL; -} - -static char *compile(struct manifest *m, struct ccan_file *cfile) -{ - char *err; - - cfile->compiled = compile_object(m, cfile->name, &err); - if (cfile->compiled) - return NULL; - return err; -} - -static void *do_compile_test_helpers(struct manifest *m) -{ - char *cmdout = NULL; - struct ccan_file *i; - - list_for_each(&m->other_test_c_files, i, list) { - compile_tests.total_score++; - cmdout = compile(m, i); - if (cmdout) - return talloc_asprintf(m, - "Failed to compile helper C" - " code file %s:\n%s", - i->name, cmdout); - } - return NULL; -} - -static const char *describe_compile_test_helpers(struct manifest *m, - void *check_result) -{ - return check_result; -} - -struct ccanlint compile_test_helpers = { - .name = "Compiling test helper files", - .total_score = 1, - .check = do_compile_test_helpers, - .describe = describe_compile_test_helpers, - .can_run = can_build, -}; - -REGISTER_TEST(compile_test_helpers, &depends_built); diff --git a/tools/ccanlint/tests/compile_tests.c b/tools/ccanlint/tests/compile_tests.c deleted file mode 100644 index 57c257a2..00000000 --- a/tools/ccanlint/tests/compile_tests.c +++ /dev/null @@ -1,192 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static const char *can_build(struct manifest *m) -{ - if (safe_mode) - return "Safe mode enabled"; - return NULL; -} - -static char *obj_list(const struct manifest *m, bool link_with_module) -{ - char *list; - struct ccan_file *i; - - /* We expect to be linked with tap, unless that's us. */ - if (!streq(m->basename, "tap")) - list = talloc_strdup(m, "../tap.o"); - else - list = talloc_strdup(m, ""); - - /* Objects from any other C files. */ - list_for_each(&m->other_test_c_files, i, list) - list = talloc_asprintf_append(list, " %s", i->compiled); - - if (link_with_module) - list = talloc_asprintf_append(list, " ../%s.o", m->basename); - - /* Other ccan modules. */ - list_for_each(&m->dep_objs, i, list) - list = talloc_asprintf_append(list, " %s", i->name); - - return list; -} - -static char *lib_list(const struct manifest *m) -{ - unsigned int i, num; - char **libs = get_libs(m, ".", ".", &num, &m->info_file->compiled); - char *ret = talloc_strdup(m, ""); - - for (i = 0; i < num; i++) - ret = talloc_asprintf_append(ret, "-l%s ", libs[i]); - return ret; -} - -static char *compile(const void *ctx, - struct manifest *m, struct ccan_file *file, bool fail, - bool link_with_module) -{ - char *errmsg; - - file->compiled = compile_and_link(ctx, file->name, - obj_list(m, link_with_module), - fail ? "-DFAIL" : "", - lib_list(m), &errmsg); - if (!file->compiled) - return errmsg; - talloc_steal(ctx, file->compiled); - return NULL; -} - -struct compile_tests_result { - struct list_node list; - const char *filename; - const char *description; - const char *output; -}; - -static void *do_compile_tests(struct manifest *m) -{ - struct list_head *list = talloc(m, struct list_head); - char *cmdout; - struct ccan_file *i; - struct compile_tests_result *res; - - list_head_init(list); - - list_for_each(&m->compile_ok_tests, i, list) { - compile_tests.total_score++; - cmdout = compile(list, m, i, false, false); - if (cmdout) { - res = talloc(list, struct compile_tests_result); - res->filename = i->name; - res->description = "failed to compile"; - res->output = talloc_steal(res, cmdout); - list_add_tail(list, &res->list); - } - } - - list_for_each(&m->run_tests, i, list) { - compile_tests.total_score++; - cmdout = compile(m, m, i, false, false); - if (cmdout) { - res = talloc(list, struct compile_tests_result); - res->filename = i->name; - res->description = "failed to compile"; - res->output = talloc_steal(res, cmdout); - list_add_tail(list, &res->list); - } - } - - list_for_each(&m->api_tests, i, list) { - compile_tests.total_score++; - cmdout = compile(m, m, i, false, true); - if (cmdout) { - res = talloc(list, struct compile_tests_result); - res->filename = i->name; - res->description = "failed to compile"; - res->output = talloc_steal(res, cmdout); - list_add_tail(list, &res->list); - } - } - - list_for_each(&m->compile_fail_tests, i, list) { - compile_tests.total_score++; - cmdout = compile(list, m, i, false, false); - if (cmdout) { - res = talloc(list, struct compile_tests_result); - res->filename = i->name; - res->description = "failed to compile without -DFAIL"; - res->output = talloc_steal(res, cmdout); - list_add_tail(list, &res->list); - } else { - cmdout = compile(list, m, i, true, false); - if (!cmdout) { - res = talloc(list, struct compile_tests_result); - res->filename = i->name; - res->description = "compiled successfully" - " with -DFAIL"; - res->output = ""; - list_add_tail(list, &res->list); - } - } - } - - if (list_empty(list)) { - talloc_free(list); - list = NULL; - } - - return list; -} - -static unsigned int score_compile_tests(struct manifest *m, - void *check_result) -{ - struct list_head *list = check_result; - struct compile_tests_result *i; - unsigned int score = compile_tests.total_score; - - list_for_each(list, i, list) - score--; - return score; -} - -static const char *describe_compile_tests(struct manifest *m, - void *check_result) -{ - struct list_head *list = check_result; - struct compile_tests_result *i; - char *descrip = talloc_strdup(list, "Compilation tests failed:\n"); - - list_for_each(list, i, list) - descrip = talloc_asprintf_append(descrip, "%s %s\n%s", - i->filename, i->description, - i->output); - return descrip; -} - -struct ccanlint compile_tests = { - .name = "Compile tests succeed", - .score = score_compile_tests, - .check = do_compile_tests, - .describe = describe_compile_tests, - .can_run = can_build, -}; - -REGISTER_TEST(compile_tests, &compile_test_helpers, NULL); diff --git a/tools/ccanlint/tests/run_tests.c b/tools/ccanlint/tests/run_tests.c deleted file mode 100644 index 33daff03..00000000 --- a/tools/ccanlint/tests/run_tests.c +++ /dev/null @@ -1,90 +0,0 @@ -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -static const char *can_run(struct manifest *m) -{ - if (safe_mode) - return "Safe mode enabled"; - return NULL; -} - -static void *do_run_tests(struct manifest *m) -{ - struct list_head *list = talloc(m, struct list_head); - char *failures = talloc_strdup(m, ""); - struct ccan_file *i; - - list_head_init(list); - - list_for_each(&m->run_tests, i, list) { - char *testout; - run_tests.total_score++; - /* FIXME: timeout here */ - testout = run_command(m, i->compiled); - if (!testout) - continue; - failures = talloc_asprintf_append(failures, - "Running %s failed:\n", - i->name); - failures = talloc_append_string(failures, testout); - } - - list_for_each(&m->api_tests, i, list) { - char *testout; - run_tests.total_score++; - /* FIXME: timeout here */ - testout = run_command(m, i->compiled); - if (!testout) - continue; - failures = talloc_asprintf_append(failures, - "Running %s failed:\n", - i->name); - failures = talloc_append_string(failures, testout); - } - - if (streq(failures, "")) { - talloc_free(failures); - failures = NULL; - } - - return failures; -} - -static unsigned int score_run_tests(struct manifest *m, void *check_result) -{ - /* FIXME: be cleverer here */ - return 0; -} - -static const char *describe_run_tests(struct manifest *m, - void *check_result) -{ - char *descrip = talloc_strdup(check_result, "Running tests failed:\n"); - - return talloc_append_string(descrip, check_result); -} - -/* FIXME: Handle by offering to run under debugger... */ - -struct ccanlint run_tests = { - .name = "run and api tests run successfully", - .score = score_run_tests, - .check = do_run_tests, - .describe = describe_run_tests, - .can_run = can_run, -}; - -REGISTER_TEST(run_tests, &compile_tests, NULL); diff --git a/tools/tools.h b/tools/tools.h index cc004036..b7fe9155 100644 --- a/tools/tools.h +++ b/tools/tools.h @@ -9,7 +9,7 @@ #define SPACE_CHARS " \f\n\r\t\v" /* FIXME: Remove some -I */ -#define CFLAGS "-O -Wall -Wundef -Wstrict-prototypes -Wold-style-definition -Wmissing-prototypes -Wmissing-declarations -Werror -Iccan/ -I. -I.. -I../.." +#define CFLAGS "-g -Wall -Wundef -Wstrict-prototypes -Wold-style-definition -Wmissing-prototypes -Wmissing-declarations -Werror -Iccan/ -I. -I.. -I../.." /* This actually compiles and runs the info file to get dependencies. */ char **get_deps(const void *ctx, const char *dir, const char *name,