Commit 501b31cd authored by Rusty Russell's avatar Rusty Russell

Implementation of auto-depends, based on Idris's start.

parent 9ca74a8e
......@@ -10,10 +10,11 @@ CORE_OBJS := tools/ccanlint/ccanlint.o \
OBJS := $(CORE_OBJS) $(TEST_OBJS)
tools/ccanlint/generated-init-tests: $(OBJS)
cat $(OBJS:.o=.c) | sed -n 's/^struct ccanlint \([A-Za-z0-9_]*\) = {/{ extern struct ccanlint \1; list_add(\&tests, \&\1.list); }/p' >$@
# FIXME: write a trivial C program to do this
tools/ccanlint/generated-init-tests: $(TEST_CFILES)
cat $(TEST_CFILES) | grep ^REGISTER_TEST > $@
tools/ccanlint/ccanlint.o: tools/ccanlint/generated-init-tests
$(TEST_OBJS): tools/ccanlint/generated-init-tests
tools/ccanlint/ccanlint: $(OBJS)
......
......@@ -19,6 +19,7 @@
#include "ccanlint.h"
#include <unistd.h>
#include <getopt.h>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
......@@ -27,11 +28,7 @@
static unsigned int verbose = 0;
static LIST_HEAD(tests);
static void init_tests(void)
{
#include "generated-init-tests"
}
static LIST_HEAD(finished_tests);
static void usage(const char *name)
{
......@@ -111,6 +108,53 @@ static bool run_test(const struct ccanlint *i,
return false;
}
static void register_test(struct ccanlint *test, ...)
{
va_list ap;
struct ccanlint *depends;
struct dependent *dchild;
list_add(&tests, &test->list);
va_start(ap, test);
/* Careful: we might have been initialized by a dependent. */
if (test->dependencies.n.next == NULL)
list_head_init(&test->dependencies);
//dependant(s) args (if any), last one is NULL
while ((depends = va_arg(ap, struct ccanlint *)) != NULL) {
dchild = malloc(sizeof(*dchild));
dchild->dependent = test;
/* The thing we depend on might not be initialized yet! */
if (depends->dependencies.n.next == NULL)
list_head_init(&depends->dependencies);
list_add_tail(&depends->dependencies, &dchild->node);
test->num_depends++;
}
va_end(ap);
}
static void init_tests(void)
{
const struct ccanlint *i;
#undef REGISTER_TEST
#define REGISTER_TEST(name, ...) register_test(&name, __VA_ARGS__)
#include "generated-init-tests"
if (!verbose)
return;
list_for_each(&tests, i, list) {
printf("%s depends on %u others\n", i->name, i->num_depends);
if (!list_empty(&i->dependencies)) {
const struct dependent *d;
printf("These depend on us:\n");
list_for_each(&i->dependencies, d, node)
printf("\t%s\n", d->dependent->name);
}
}
}
int main(int argc, char *argv[])
{
int c;
......
......@@ -4,6 +4,12 @@
#include <stdbool.h>
#include "../doc_extract.h"
#define REGISTER_TEST(name, ...) extern struct ccanlint name
#include "generated-init-tests"
#undef REGISTER_TEST
#define REGISTER_TEST(name, ...)
struct manifest {
char *basename;
struct ccan_file *info_file;
......@@ -44,6 +50,12 @@ struct ccanlint {
/* Can we do something about it? (NULL if not) */
void (*handle)(struct manifest *m, void *check_result);
/* Internal use fields: */
/* Who depends on us? */
struct list_head dependencies;
/* How many things do we (still) depend on? */
unsigned int num_depends;
};
/* Ask the user a yes/no question: the answer is NO if there's an error. */
......@@ -134,10 +146,13 @@ char *report_on_lines(struct list_head *files,
char *(*report)(const char *),
char *sofar);
/* The critical tests which mean fail if they don't pass. */
extern struct ccanlint no_info;
extern struct ccanlint has_main_header;
/* Normal tests. */
extern struct ccanlint trailing_whitespace;
/* Dependencies */
struct dependent {
struct list_node node;
struct ccanlint *dependent;
};
#endif /* CCAN_LINT_H */
......@@ -76,3 +76,5 @@ struct ccanlint has_info = {
.describe = describe_has_info,
.handle = create_info_template,
};
REGISTER_TEST(has_info, NULL);
......@@ -39,3 +39,5 @@ struct ccanlint has_main_header = {
.check = check_has_main_header,
.describe = describe_has_main_header,
};
REGISTER_TEST(has_main_header, NULL);
......@@ -128,3 +128,5 @@ struct ccanlint has_tests = {
.describe = describe_has_tests,
.handle = handle_no_tests,
};
REGISTER_TEST(has_tests, NULL);
......@@ -128,3 +128,5 @@ struct ccanlint has_info_documentation = {
.check = check_has_info_documentation,
.describe = describe_has_info_documentation,
};
REGISTER_TEST(has_info_documentation, NULL);
......@@ -137,3 +137,5 @@ struct ccanlint idempotent = {
.check = check_idempotent,
.describe = describe_idempotent,
};
REGISTER_TEST(idempotent, &trailing_whitespace, NULL);
......@@ -45,3 +45,6 @@ struct ccanlint trailing_whitespace = {
.check = check_trailing_whitespace,
.describe = describe_trailing_whitespace,
};
REGISTER_TEST(trailing_whitespace, NULL);
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment