Create and use a snprintf wrapper in the core code
Use a wrapper around snprintf to consilidate all use, add error checking, and remove gcc 9 warnings about not checking the result. Replace the prevous use of snprintf added to weapon.c with the new scheme. Update a second spot that has a gcc sprintf warning. While there, simplify the code.
This commit is contained in:
@@ -953,6 +953,12 @@ E void FDECL(strbuf_nl_to_crlf, (strbuf_t *));
|
||||
E char *FDECL(nonconst, (const char *, char *));
|
||||
E int FDECL(swapbits, (int, int, int));
|
||||
E void FDECL(shuffle_int_array, (int *, int));
|
||||
/* note: the snprintf CPP wrapper includes the "fmt" argument in "..."
|
||||
(__VA_ARGS__) to allow for zero arguments after fmt */
|
||||
#define Snprintf(str, size, ...) \
|
||||
nh_snprintf(__func__, __LINE__, str, size, __VA_ARGS__)
|
||||
extern void nh_snprintf(const char *func, int line, char *str, size_t size,
|
||||
const char *fmt, ...);
|
||||
|
||||
/* ### insight.c ### */
|
||||
|
||||
|
||||
@@ -74,6 +74,8 @@
|
||||
char * nonconst (const char *, char *)
|
||||
int swapbits (int, int, int)
|
||||
void shuffle_int_array (int *, int)
|
||||
void nh_snprintf (const char *, int, char *, size_t,
|
||||
const char *, ...)
|
||||
=*/
|
||||
#ifdef LINT
|
||||
#define Static /* pacify lint */
|
||||
@@ -1319,4 +1321,39 @@ int count;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Wrap snprintf for use in the main code.
|
||||
*
|
||||
* Wrap reasons:
|
||||
* 1. If there are any platform issues, we have one spot to fix them -
|
||||
* snprintf is a routine with a troubling history of bad implementations.
|
||||
* 2. Add combersome error checking in one spot. Problems with text wrangling
|
||||
* do not have to be fatal.
|
||||
* 3. Gcc 9+ will issue a warning unless the return value is used.
|
||||
* Annoyingly, explicitly casting to void does not remove the error.
|
||||
* So, use the result - see reason #2.
|
||||
*/
|
||||
void
|
||||
nh_snprintf(const char *func, int line, char *str, size_t size,
|
||||
const char *fmt, ...)
|
||||
{
|
||||
va_list ap;
|
||||
int n;
|
||||
|
||||
va_start(ap, fmt);
|
||||
#ifdef NO_VSNPRINTF
|
||||
n = vsprintf(str, fmt, ap);
|
||||
#else
|
||||
n = vsnprintf(str, size, fmt, ap);
|
||||
#endif
|
||||
va_end(ap);
|
||||
if (n < 0 || (size_t)n >= size) { /* is there a problem? */
|
||||
impossible("snprintf %s: func %s, file line %d",
|
||||
n < 0 ? "format error"
|
||||
: "overflow",
|
||||
func, line);
|
||||
str[size-1] = 0; /* make sure it is nul terminated */
|
||||
}
|
||||
}
|
||||
|
||||
/*hacklib.c*/
|
||||
|
||||
@@ -251,19 +251,23 @@ void
|
||||
early_version_info(pastebuf)
|
||||
boolean pastebuf;
|
||||
{
|
||||
char buf[BUFSZ], buf2[BUFSZ];
|
||||
char *tmp = getversionstring(buf);
|
||||
char buf1[BUFSZ], buf2[BUFSZ];
|
||||
char *buf, *tmp;
|
||||
|
||||
/* this is early enough that we have to do
|
||||
our own line-splitting */
|
||||
Snprintf(buf1, sizeof(buf1), "test");
|
||||
/* this is early enough that we have to do our own line-splitting */
|
||||
getversionstring(buf1);
|
||||
tmp = strstri(buf1, " ("); /* split at start of version info */
|
||||
if (tmp) {
|
||||
tmp = strstri(buf," (");
|
||||
if (tmp) *tmp++ = '\0';
|
||||
/* retain one buffer so that it all goes into the paste buffer */
|
||||
*tmp++ = '\0';
|
||||
Snprintf(buf2, sizeof(buf2), "%s\n%s", buf1, tmp);
|
||||
buf = buf2;
|
||||
} else {
|
||||
buf = buf1;
|
||||
}
|
||||
|
||||
Sprintf(buf2, "%s\n", buf);
|
||||
if (tmp) Sprintf(eos(buf2), "%s\n", tmp);
|
||||
raw_printf("%s", buf2);
|
||||
raw_printf("%s", buf);
|
||||
|
||||
if (pastebuf) {
|
||||
#if defined(RUNTIME_PASTEBUF_SUPPORT) && !defined(LIBNH)
|
||||
@@ -272,7 +276,7 @@ boolean pastebuf;
|
||||
* version information into a paste buffer. Useful for
|
||||
* easy inclusion in bug reports.
|
||||
*/
|
||||
port_insert_pastebuf(buf2);
|
||||
port_insert_pastebuf(buf);
|
||||
#else
|
||||
raw_printf("%s", "Paste buffer copy is not available.\n");
|
||||
#endif
|
||||
|
||||
22
src/weapon.c
22
src/weapon.c
@@ -1271,23 +1271,21 @@ enhance_weapon_skill()
|
||||
(void) skill_level_name(i, sklnambuf);
|
||||
if (wizard) {
|
||||
if (!iflags.menu_tab_sep)
|
||||
n = snprintf(buf, sizeof(buf), " %s%-*s %-12s %5d(%4d)", prefix,
|
||||
longest, P_NAME(i), sklnambuf, P_ADVANCE(i),
|
||||
practice_needed_to_advance(P_SKILL(i)));
|
||||
Snprintf(buf, sizeof(buf), " %s%-*s %-12s %5d(%4d)", prefix,
|
||||
longest, P_NAME(i), sklnambuf, P_ADVANCE(i),
|
||||
practice_needed_to_advance(P_SKILL(i)));
|
||||
else
|
||||
n = snprintf(buf, sizeof(buf), " %s%s\t%s\t%5d(%4d)", prefix, P_NAME(i),
|
||||
sklnambuf, P_ADVANCE(i),
|
||||
practice_needed_to_advance(P_SKILL(i)));
|
||||
Snprintf(buf, sizeof(buf), " %s%s\t%s\t%5d(%4d)", prefix, P_NAME(i),
|
||||
sklnambuf, P_ADVANCE(i),
|
||||
practice_needed_to_advance(P_SKILL(i)));
|
||||
} else {
|
||||
if (!iflags.menu_tab_sep)
|
||||
n = snprintf(buf, sizeof(buf), " %s %-*s [%s]", prefix, longest,
|
||||
P_NAME(i), sklnambuf);
|
||||
Snprintf(buf, sizeof(buf), " %s %-*s [%s]", prefix, longest,
|
||||
P_NAME(i), sklnambuf);
|
||||
else
|
||||
n = snprintf(buf, sizeof(buf), " %s%s\t[%s]", prefix, P_NAME(i),
|
||||
sklnambuf);
|
||||
Snprintf(buf, sizeof(buf), " %s%s\t[%s]", prefix, P_NAME(i),
|
||||
sklnambuf);
|
||||
}
|
||||
if (n >= sizeof(buf)) /* check for overflow */
|
||||
buf[sizeof(buf)-1] = 0; /* terminate string */
|
||||
any.a_int = can_advance(i, speedy) ? i + 1 : 0;
|
||||
add_menu(win, &nul_glyphinfo, &any, 0, 0,
|
||||
ATR_NONE, buf, MENU_ITEMFLAGS_NONE);
|
||||
|
||||
Reference in New Issue
Block a user