From 2ea90b45cf37292aba7c81b34736661c080497de Mon Sep 17 00:00:00 2001 From: Rusty Russell Date: Mon, 10 Nov 2014 15:00:26 +1030 Subject: [PATCH] ccanlint: offer to insert license comments where they're missing. Signed-off-by: Rusty Russell --- tools/ccanlint/licenses.c | 19 +++++++++++++ tools/ccanlint/licenses.h | 4 +++ tools/ccanlint/tests/license_comment.c | 39 ++++++++++++++++++++++++++ 3 files changed, 62 insertions(+) diff --git a/tools/ccanlint/licenses.c b/tools/ccanlint/licenses.c index 45684974..ca8bc73d 100644 --- a/tools/ccanlint/licenses.c +++ b/tools/ccanlint/licenses.c @@ -6,75 +6,88 @@ const struct license_info licenses[] = { { "LGPLv2+", "LGPL", + "GNU LGPL version 2 (or later)", { "gnu lesser general public license", "version 2", "or at your option any later version" } }, { "LGPLv2", "LGPL", + "GNU LGPL version 2", { "gnu lesser general public license", "version 2", NULL } }, { "LGPLv3", "LGPL", + "GNU LGPL version 3", { "gnu lesser general public license", "version 3", NULL } }, { "LGPL", "LGPL", + "GNU LGPL", { "gnu lesser general public license", NULL, NULL } }, { "GPLv2+", "GPL", + "GNU GPL version 2 (or later)", { "gnu general public license", "version 2", "or at your option any later version" } }, { "GPLv2", "GPL", + "GNU GPL version 2", { "gnu general public license", "version 2", NULL } }, { "GPLv3", "GPL", + "GNU GPL version 3 (or later)", { "gnu general public license", "version 3", NULL } }, { "GPL", "GPL", + "GNU GPL", { "gnu general public license", NULL, NULL } }, { "BSD-3CLAUSE", "BSD", + "3-clause BSD license", { "redistributions of source code must retain", "redistributions in binary form must reproduce", "endorse or promote" } }, { "BSD-MIT", "MIT", + "MIT (BSD) license", { "without restriction", "above copyright notice", "without warranty" } }, { "CC0", "CC0", + "CC0 license (public domain)", { "Waiver.", "unconditionally waives", NULL } }, { "Public domain", "Public domain", + NULL, { NULL, NULL, NULL } }, { "Unknown license", "Unknown license", + NULL, { NULL, NULL, NULL } }, }; @@ -216,3 +229,9 @@ struct doc_section *find_license_tag(const struct manifest *m) } return NULL; } + +const char *get_license_oneliner(const tal_t *ctx, enum license license) +{ + return tal_fmt(ctx, "/* %s - see LICENSE file for details */", + licenses[license].describe); +} diff --git a/tools/ccanlint/licenses.h b/tools/ccanlint/licenses.h index ed1e9ad7..60d20376 100644 --- a/tools/ccanlint/licenses.h +++ b/tools/ccanlint/licenses.h @@ -1,6 +1,7 @@ #ifndef CCANLINT_LICENSES_H #define CCANLINT_LICENSES_H #include +#include enum license { LICENSE_LGPLv2_PLUS, @@ -23,6 +24,7 @@ enum license { struct license_info { const char *name; const char *shortname; + const char *describe; /* Edit distance is expensive, and this works quite well. */ const char *clause[NUM_CLAUSES]; }; @@ -41,4 +43,6 @@ enum license which_license(struct doc_section *d); struct manifest; struct doc_section *find_license_tag(const struct manifest *m); +const char *get_license_oneliner(const tal_t *ctx, enum license license); + #endif /* CCANLINT_LICENSES_H */ diff --git a/tools/ccanlint/tests/license_comment.c b/tools/ccanlint/tests/license_comment.c index 18a60813..9548d87c 100644 --- a/tools/ccanlint/tests/license_comment.c +++ b/tools/ccanlint/tests/license_comment.c @@ -57,10 +57,49 @@ static void check_license_comment(struct manifest *m, } } +static void add_license_comment(struct manifest *m, struct score *score) +{ + struct file_error *e; + const char *license_desc = get_license_oneliner(score, m->license); + char *files = tal_strdup(score, ""), *q; + + list_for_each(&score->per_file_errors, e, list) + tal_append_fmt(&files, " %s\n", e->file->name); + + q = tal_fmt(score, "The following files don't have a comment:\n%s\n" + "Should I prepend '%s'?", files, license_desc); + if (!ask(q)) + return; + + list_for_each(&score->per_file_errors, e, list) { + char *tmpname; + FILE *out; + unsigned int i; + + tmpname = temp_file(score, ".licensed", e->file->name); + out = fopen(tmpname, "w"); + if (!out) + err(1, "Opening %s", tmpname); + if (fprintf(out, "%s\n", license_desc) < 0) + err(1, "Writing %s", tmpname); + + for (i = 0; e->file->lines[i]; i++) + if (fprintf(out, "%s\n", e->file->lines[i]) < 0) + err(1, "Writing %s", tmpname); + + if (fclose(out) != 0) + err(1, "Closing %s", tmpname); + + if (!move_file(tmpname, e->file->fullname)) + err(1, "Moving %s to %s", tmpname, e->file->fullname); + } +} + struct ccanlint license_comment = { .key = "license_comment", .name = "Source and header files refer to LICENSE", .check = check_license_comment, + .handle = add_license_comment, .needs = "license_exists" }; REGISTER_TEST(license_comment); -- 2.39.2