From: Ralph Corderoy Date: Wed, 9 Aug 2017 13:32:29 +0000 (+0100) Subject: Teach gcc(1) that adios() and friends take printf formats. X-Git-Url: https://diplodocus.org/git/nmh/commitdiff_plain/bdf27468d23eade733c0afb4327c9b88444b9058?ds=sidebyside Teach gcc(1) that adios() and friends take printf formats. It then checks their arguments. Correct the resulting warnings, e.g. C89 doesn't have `%zu', but does say size_t shouldn't be wider than long. Perhaps an autoconf test can detect if the `format' __attribute__ is supported. --- diff --git a/h/mh.h b/h/mh.h index d3c37c72..dda0c3d2 100644 --- a/h/mh.h +++ b/h/mh.h @@ -30,14 +30,15 @@ #endif typedef unsigned char boolean; /* not int so we can pack in a structure */ -/* If we're using gcc then give it some information about - * functions that abort. - */ +/* If we're using gcc then tell it extra information so it can do more + * compile-time checks. */ #if __GNUC__ > 2 #define NORETURN __attribute__((__noreturn__)) +#define CHECK_PRINTF(fmt, arg) __attribute__((format(printf, fmt, arg))) #define NMH_UNUSED(i) (void) i #else #define NORETURN +#define CHECK_PRINTF(fmt, arg) #define NMH_UNUSED(i) i #endif diff --git a/h/prototypes.h b/h/prototypes.h index 97c6cc13..64bd847b 100644 --- a/h/prototypes.h +++ b/h/prototypes.h @@ -16,11 +16,11 @@ char *etcpath(char *); struct msgs_array; void add_profile_entry (const char *, const char *); -void inform(char *fmt, ...); -void adios (const char *, const char *, ...) NORETURN; -void admonish (char *, char *, ...); -void advertise (const char *, char *, const char *, va_list); -void advise (const char *, const char *, ...); +void inform(char *fmt, ...) CHECK_PRINTF(1, 2); +void adios (const char *, const char *, ...) CHECK_PRINTF(2, 3) NORETURN; +void admonish (char *, char *, ...) CHECK_PRINTF(2, 3); +void advertise (const char *, char *, const char *, va_list) CHECK_PRINTF(3, 0); +void advise (const char *, const char *, ...) CHECK_PRINTF(2, 3); char **argsplit (char *, char **, int *); void argsplit_msgarg (struct msgs_array *, char *, char **); void argsplit_insert (struct msgs_array *, char *, char **); diff --git a/sbr/m_getfld.c b/sbr/m_getfld.c index 9ea6f070..e8043928 100644 --- a/sbr/m_getfld.c +++ b/sbr/m_getfld.c @@ -446,7 +446,7 @@ enter_getfld (m_getfld_state_t *gstate, FILE *iob) { chunks of size MSG_INPUT_SIZE. */ off = pos / MSG_INPUT_SIZE * MSG_INPUT_SIZE; if (fseeko(iob, off, SEEK_SET) == -1) - adios("getfld's iob", "failed to set offset to skip: %d", + adios("getfld's iob", "failed to set offset to skip: %ld", off); num_read = fread (s->msg_buf, 1, MSG_INPUT_SIZE, iob); s->readpos = s->msg_buf + pos % MSG_INPUT_SIZE; @@ -456,7 +456,7 @@ enter_getfld (m_getfld_state_t *gstate, FILE *iob) { } if (fseeko(iob, pos, SEEK_SET) == -1) - adios("getfld's iob", "failed to set offset on entry: %d", pos); + adios("getfld's iob", "failed to set offset on entry: %ld", pos); } static void @@ -470,7 +470,7 @@ leave_getfld (m_getfld_state_t s) { /* Set file stream position so that callers can use ftell(). */ if (fseeko(s->iob, s->total_bytes_read, SEEK_SET) == -1) - adios("getfld's iob", "failed to set offset: %d", + adios("getfld's iob", "failed to set offset: %ld", s->total_bytes_read); if ((s->last_caller_pos = ftello(s->iob)) == -1) adios("getfld's iob", "failed to get offset after seek"); diff --git a/sbr/utils.c b/sbr/utils.c index 90f36bd3..205c8592 100644 --- a/sbr/utils.c +++ b/sbr/utils.c @@ -35,7 +35,7 @@ void *mh_xmalloc(size_t size) size = 1; /* Some mallocs don't like 0. */ p = malloc(size); if (!p) - adios(NULL, "malloc failed, size wanted: %zu", size); + adios(NULL, "malloc failed, size wanted: %lu", (unsigned long)size); return p; } @@ -55,7 +55,7 @@ void *mh_xrealloc(void *ptr, size_t size) new = realloc(ptr, size); if (!new) - adios(NULL, "realloc failed, size wanted: %zu", size); + adios(NULL, "realloc failed, size wanted: %lu", (unsigned long)size); return new; } @@ -70,7 +70,8 @@ void *mh_xcalloc(size_t nelem, size_t elsize) p = calloc(nelem, elsize); if (!p) - adios(NULL, "calloc failed, size wanted: %zu * %zu", nelem, elsize); + adios(NULL, "calloc failed, size wanted: %lu * %lu", + (unsigned long)nelem, (unsigned long)elsize); return p; } diff --git a/uip/fmttest.c b/uip/fmttest.c index ccfe25c0..3dfdf9b6 100644 --- a/uip/fmttest.c +++ b/uip/fmttest.c @@ -287,8 +287,7 @@ main (int argc, char **argv) */ if (!dump && compargs.size == 0 && msgs.size == 0) { - adios (NULL, "usage: [switches] [+folder] msgs | strings...", - invo_name); + adios(NULL, "usage: [switches] [+folder] msgs | strings..."); } /* diff --git a/uip/mhparse.c b/uip/mhparse.c index bab4e5b6..d927885a 100644 --- a/uip/mhparse.c +++ b/uip/mhparse.c @@ -865,7 +865,7 @@ magic_skip: } else inform("extraneous information in message %s's %s: field\n%*s(%s)", - ct->c_file, TYPE_FIELD, strlen(invo_name) + 2, "", cp); + ct->c_file, TYPE_FIELD, (int)strlen(invo_name) + 2, "", cp); } return OK; @@ -934,7 +934,7 @@ get_dispo (char *cp, CT ct, int buildflag) } } else if (*cp) { inform("extraneous information in message %s's %s: field\n%*s(%s)", - ct->c_file, DISPO_FIELD, strlen(invo_name) + 2, "", cp); + ct->c_file, DISPO_FIELD, (int)strlen(invo_name) + 2, "", cp); } if (buildflag) @@ -3305,8 +3305,9 @@ parse_header_attrs (const char *filename, const char *fieldname, dp++; if (dp == cp || *dp != '=') { inform("invalid parameter in message %s's %s: " - "field\n%*sparameter %s (error detected at offset %d)", - filename, fieldname, strlen(invo_name) + 2, "",cp, dp - cp); + "field\n%*sparameter %s (error detected at offset %ld)", + filename, fieldname, (int)strlen(invo_name) + 2, "", + cp, dp - cp); return NOTOK; } @@ -3339,7 +3340,7 @@ parse_header_attrs (const char *filename, const char *fieldname, else { inform("invalid parameter index in message %s's " "%s: field\n%*s(parameter %s)", filename, - fieldname, strlen(invo_name) + 2, "", cp); + fieldname, (int)strlen(invo_name) + 2, "", cp); return NOTOK; } } else { @@ -3383,7 +3384,7 @@ parse_header_attrs (const char *filename, const char *fieldname, } else { inform("missing charset in message %s's %s: " "field\n%*s(parameter %s)", filename, fieldname, - strlen(invo_name) + 2, "", nameptr); + (int)strlen(invo_name) + 2, "", nameptr); free(nameptr); return NOTOK; } @@ -3406,7 +3407,7 @@ parse_header_attrs (const char *filename, const char *fieldname, } else { inform("missing language tag in message %s's %s: " "field\n%*s(parameter %s)", filename, fieldname, - strlen(invo_name) + 2, "", nameptr); + (int)strlen(invo_name) + 2, "", nameptr); free(nameptr); mh_xfree(charset); return NOTOK; @@ -3430,8 +3431,8 @@ parse_header_attrs (const char *filename, const char *fieldname, !isxdigit((unsigned char) *(vp + 2))) { inform("invalid encoded sequence in message " "%s's %s: field\n%*s(parameter %s)", - filename, fieldname, strlen(invo_name) + 2, - "", nameptr); + filename, fieldname, + (int)strlen(invo_name) + 2, "", nameptr); free(nameptr); mh_xfree(charset); mh_xfree(lang); @@ -3472,8 +3473,8 @@ parse_header_attrs (const char *filename, const char *fieldname, case '\0': bad_quote: inform("invalid quoted-string in message %s's %s: " - "field\n%*s(parameter %s)", filename, - fieldname, strlen(invo_name) + 2, "", nameptr); + "field\n%*s(parameter %s)", filename, fieldname, + (int)strlen(invo_name) + 2, "", nameptr); free(nameptr); mh_xfree(charset); mh_xfree(lang); @@ -3559,8 +3560,8 @@ bad_quote: if (sp2->index == sp->index) { inform("duplicate index (%d) in message " "%s's %s: field\n%*s(parameter %s)", sp->index, - filename, fieldname, strlen(invo_name) + 2, "", - nameptr); + filename, fieldname, + (int)strlen(invo_name) + 2, "", nameptr); return NOTOK; } if (sp2->index < sp->index && @@ -3574,8 +3575,8 @@ bad_quote: if (sp2 == NULL) { inform("Internal error: cannot insert partial " "param in message %s's %s: field\n%*s(parameter %s)", - filename, fieldname, strlen(invo_name) + 2, "", - nameptr); + filename, fieldname, + (int)strlen(invo_name) + 2, "", nameptr); return NOTOK; } } @@ -3617,8 +3618,8 @@ bad_quote: if (sp->index != pindex++) { inform("missing section %d for parameter in " "message %s's %s: field\n%*s(parameter %s)", pindex - 1, - filename, fieldname, strlen(invo_name) + 2, "", - pp->name); + filename, fieldname, + (int)strlen(invo_name) + 2, "", pp->name); return NOTOK; } tlen += sp->len;