From 46336fb4df720f36f8b91a5fe23ed5f15624394b Mon Sep 17 00:00:00 2001 From: Christine Caulfield Date: Mon, 7 Sep 2020 15:33:43 +0100 Subject: [PATCH] doxygen2man: Add option to read copyright line from the header file This should help make builds reproducible. I tried various methods of getting the date, using 'git' is no use as it could be run from a tarball, using the file date doesn't work either so this seems a reasonable compromise. --- docs/Makefile.am | 2 +- doxygen2man/doxygen2man.1 | 13 ++++++++++- doxygen2man/doxygen2man.c | 46 ++++++++++++++++++++++++++++++++++++--- 3 files changed, 56 insertions(+), 5 deletions(-) diff --git a/docs/Makefile.am b/docs/Makefile.am index c2235b654..d2d4c45ab 100644 --- a/docs/Makefile.am +++ b/docs/Makefile.am @@ -25,7 +25,7 @@ dist_man_MANS = man8/qb-blackbox.8 if HAVE_DOXYGEN if BUILD_MAN -doxygen2man_flags = -q -i qb/ -o man3/ -m -g -P -H "libqb Programmer's Manual" -p LIBQB +doxygen2man_flags = -q -i qb/ -o man3/ -m -g -P -H "libqb Programmer's Manual" -p LIBQB -c -O ../include/qb man3_MANS = \ man3/qb_array_create_2.3 \ diff --git a/doxygen2man/doxygen2man.1 b/doxygen2man/doxygen2man.1 index 89ccab719..2fb850019 100644 --- a/doxygen2man/doxygen2man.1 +++ b/doxygen2man/doxygen2man.1 @@ -6,7 +6,7 @@ .\" * Author: Christine Caulfield .\" * -.TH "DOXYGEN2MAN" "8" "2020-03-09" "" "" +.TH "DOXYGEN2MAN" "8" "2020-09-09" "" "" .SH "NAME" doxygen2man \- A tool to generate man pages from Doxygen XML files .SH "SYNOPSIS" @@ -69,6 +69,17 @@ Write all man pages to (default .) .B -d Directory for XML files (./xml/) .TP +.B -c +Use the Copyright line from the header file as the copyright line in the manpage. +This requires that doxygen2man has access to the original .h file (see option -O below) +and that the Copyright line has a defined format. It whould be within the first 10 lines +of the file and start with the text " * Copyright". If this line is not found then +the current year or that given by the -Y option will be used. +.TP +.B -O +Specifies the directory containing the original header files. This is (currently) only +used by the -c option above. +.TP .B -h Print usage text diff --git a/doxygen2man/doxygen2man.c b/doxygen2man/doxygen2man.c index 880734a17..4253aeea5 100644 --- a/doxygen2man/doxygen2man.c +++ b/doxygen2man/doxygen2man.c @@ -46,7 +46,8 @@ static int print_man = 0; static int print_params = 0; static int print_general = 0; static int num_functions = 0; -static int quiet=0; +static int quiet = 0; +static int use_header_copyright = 0; static const char *man_section="3"; static const char *package_name="Package"; static const char *header="Programmer's Manual"; @@ -57,6 +58,8 @@ static const char *xml_file; static const char *manpage_date = NULL; static const char *headerfile = NULL; static const char *header_prefix = ""; +static const char *header_src_dir = "./"; +static char header_copyright[256] = "\0"; static long manpage_year = LONG_MIN; static long start_year = 2010; static struct qb_list_head params_list; @@ -763,7 +766,11 @@ static void print_manpage(char *name, char *def, char *brief, char *args, char * fprintf(manfile, ".hy\n"); fprintf(manfile, ".SH \"COPYRIGHT\"\n"); fprintf(manfile, ".PP\n"); - fprintf(manfile, "Copyright (C) %4ld-%4ld %s, Inc. All rights reserved.\n", start_year, manpage_year, company); + if (header_copyright[0] == 'C') { + fprintf(manfile, "%s", header_copyright); /* String already contains trailing NL */ + } else { + fprintf(manfile, "Copyright (C) %4ld-%4ld %s, Inc. All rights reserved.\n", start_year, manpage_year, company); + } fclose(manfile); /* Free the params & retval info */ @@ -993,6 +1000,8 @@ static void usage(char *name) printf(" -m Write man page files to \n"); printf(" -P Print PARAMS section\n"); printf(" -g Print general man page for the whole header file\n"); + printf(" -c Use the Copyright date from the header file (if one can be found)\n"); + printf(" -O Directory for the orignal header file. Often needed by -c above\n"); printf(" -s Write man pages into section Use name. default \n"); printf(" -H
Set header (default \"Programmer's Manual\"\n"); @@ -1029,7 +1038,7 @@ int main(int argc, char *argv[]) int opt; char xml_filename[PATH_MAX]; - while ( (opt = getopt_long(argc, argv, "H:amqgPD:Y:s:S:d:o:p:f:I:i:C:h?", NULL, NULL)) != EOF) + while ( (opt = getopt_long(argc, argv, "H:amqgcPD:Y:s:S:d:o:p:f:I:i:C:O:h?", NULL, NULL)) != EOF) { switch(opt) { @@ -1050,6 +1059,9 @@ int main(int argc, char *argv[]) case 'q': quiet = 1; break; + case 'c': + use_header_copyright = 1; + break; case 'I': headerfile = optarg; break; @@ -1089,6 +1101,9 @@ int main(int argc, char *argv[]) case 'o': output_dir = optarg; break; + case 'O': + header_src_dir = optarg; + break; case '?': case 'h': usage(argv[0]); @@ -1126,7 +1141,32 @@ int main(int argc, char *argv[]) /* Get our header file name */ if (!headerfile) { traverse_node(rootdoc, "compounddef", read_headername, &headerfile); + + if (use_header_copyright) { + /* And get the copyright line from this file if we can */ + char file_path[PATH_MAX]; + char file_line[256]; + FILE *hfile; + int lineno = 0; + + snprintf(file_path, sizeof(file_path), "%s/%s", header_src_dir, headerfile); + hfile = fopen(file_path, "r"); + if (hfile) { + /* Don't look too far, this should be at the top */ + while (!feof(hfile) && (lineno++ < 10)) { + if (fgets(file_line, sizeof(file_line)-1, hfile)) { + if (strncmp(file_line, " * Copyright", 12) == 0) { + /* Keep the NL at the end of the buffer, it save us printing one */ + strncpy(header_copyright, file_line+3, sizeof(header_copyright)-1); + break; + } + } + } + fclose(hfile); + } + } } + /* Default to *something* if it all goes wrong */ if (!headerfile) { headerfile = "unknown.h";