1 #include "talloc/talloc.h"
2 #include "string/string.h"
8 static char ** __attribute__((format(printf, 3, 4)))
9 lines_from_cmd(const void *ctx, unsigned int *num, char *format, ...)
16 cmd = talloc_vasprintf(ctx, format, ap);
21 err(1, "Executing '%s'", cmd);
23 buffer = grab_fd(ctx, fileno(p), NULL);
25 err(1, "Reading from '%s'", cmd);
28 return strsplit(ctx, buffer, "\n", num);
31 static int unlink_info(char *infofile)
37 /* Be careful about trying to compile over running programs (parallel make) */
38 static char *compile_info(const void *ctx, const char *dir)
40 char *infofile = talloc_asprintf(ctx, "%s/_info.%u", dir, getpid());
41 char *cmd = talloc_asprintf(ctx, "cc " CFLAGS " -o %s %s/_info.c",
43 talloc_set_destructor(infofile, unlink_info);
50 static char **get_one_deps(const void *ctx, const char *dir, unsigned int *num)
52 char **deps, *cmd, *infofile;
54 infofile = compile_info(ctx, dir);
56 errx(1, "Could not compile _info for '%s'", dir);
58 cmd = talloc_asprintf(ctx, "%s depends", infofile);
59 deps = lines_from_cmd(cmd, num, "%s", cmd);
61 err(1, "Could not run '%s'", cmd);
65 static bool have_dep(char **deps, unsigned int num, const char *dep)
69 for (i = 0; i < num; i++)
70 if (streq(deps[i], dep))
75 /* Gets all the dependencies, recursively. */
76 char **get_deps(const void *ctx, const char *dir)
81 deps = get_one_deps(ctx, dir, &num);
82 for (i = 0; i < num; i++) {
84 unsigned int j, newnum;
86 if (!strstarts(deps[i], "ccan/"))
89 newdeps = get_one_deps(ctx, deps[i], &newnum);
91 /* Should be short, so brute-force out dups. */
92 for (j = 0; j < newnum; j++) {
93 if (have_dep(deps, num, newdeps[j]))
96 deps = talloc_realloc(NULL, deps, char *, num + 2);
97 deps[num++] = newdeps[j];