Prefer use of __MINGW_PRINTF/SCANF_FORMAT if available.

Mingw headers sometimes like to define alternative scanf/printf
format attributes depending on whether they're using clang, UCRT,
MINGW_ANSI_STDIO, or the microsoft version of printf/scanf.  This
change attempts to use the right one on the given platform.

This is an attempt to fix part of #40355.
This commit is contained in:
Nick Mathewson 2021-11-05 12:08:48 -04:00
parent 1c77deca4f
commit c93114ec9e
5 changed files with 37 additions and 10 deletions

4
changes/bug40355_part2 Normal file
View File

@ -0,0 +1,4 @@
o Minor features (portability):
- Try to prevent a compiler warning about printf arguments that could
sometimes occur on MSYS2 depending on the configuration.
Closes ticket 40355.

View File

@ -689,6 +689,7 @@ AC_CHECK_FUNCS(
readpassphrase \
rint \
sigaction \
snprintf \
socketpair \
statvfs \
strncasecmp \
@ -706,7 +707,8 @@ AC_CHECK_FUNCS(
uname \
usleep \
vasprintf \
_vscprintf
_vscprintf \
vsnprintf
)
# Apple messed up when they added some functions: they

View File

@ -18,9 +18,9 @@
// Include this after the above headers, to insure that they don't
// depend on anything else.
#include "orconfig.h"
#include "lib/cc/compat_compiler.h"
#include "lib/cc/torint.h"
#include "feature/api/tor_api_internal.h"
#include "lib/cc/compat_compiler.h"
#include <stdio.h>
#include <stdlib.h>
@ -39,7 +39,9 @@
#include "lib/net/socketpair.h"
#define raw_socketpair tor_ersatz_socketpair
#define raw_closesocket closesocket
#if !defined(HAVE_SNPRINTF)
#define snprintf _snprintf
#endif
#else /* !defined(_WIN32) */
#define raw_socketpair socketpair
#define raw_closesocket close

View File

@ -15,6 +15,15 @@
#include "orconfig.h"
#include <inttypes.h>
#if defined(__MINGW32__) || defined(__MINGW64__)
#define MINGW_ANY
#endif
#ifdef MINGW_ANY
/* We need this for __MINGW_PRINTF_FORMAT, alas. */
#include <stdio.h>
#endif
#if defined(__has_feature)
# if __has_feature(address_sanitizer)
/* Some of the fancy glibc strcmp() macros include references to memory that
@ -36,16 +45,30 @@
#error "It seems that you encode characters in something other than ASCII."
#endif
/* Use the right magic attribute on mingw, which might be printf, gnu_printf,
* or ms_printf, depending on how we're set up to build.
*/
#ifdef __MINGW_PRINTF_FORMAT
#define PRINTF_FORMAT_ATTR __MINGW_PRINTF_FORMAT
#else
#define PRINTF_FORMAT_ATTR printf
#endif
#ifdef __MINGW_SCANF_FORMAT
#define SCANF_FORMAT_ATTR __MINGW_SCANF_FORMAT
#else
#define SCANF_FORMAT_ATTR scanf
#endif
/* GCC can check printf and scanf types on arbitrary functions. */
#ifdef __GNUC__
#define CHECK_PRINTF(formatIdx, firstArg) \
__attribute__ ((format(printf, formatIdx, firstArg)))
__attribute__ ((format(PRINTF_FORMAT_ATTR, formatIdx, firstArg)))
#else
#define CHECK_PRINTF(formatIdx, firstArg)
#endif /* defined(__GNUC__) */
#ifdef __GNUC__
#define CHECK_SCANF(formatIdx, firstArg) \
__attribute__ ((format(scanf, formatIdx, firstArg)))
__attribute__ ((format(SCANF_FORMAT_ATTR, formatIdx, firstArg)))
#else
#define CHECK_SCANF(formatIdx, firstArg)
#endif /* defined(__GNUC__) */
@ -191,10 +214,6 @@
#define OP_EQ ==
#define OP_NE !=
#if defined(__MINGW32__) || defined(__MINGW64__)
#define MINGW_ANY
#endif
/** Macro: yield a pointer to the field at position <b>off</b> within the
* structure <b>st</b>. Example:
* <pre>

View File

@ -8,9 +8,9 @@
* \brief Compatibility wrappers around snprintf and its friends
**/
#include "lib/cc/torint.h"
#include "lib/string/printf.h"
#include "lib/err/torerr.h"
#include "lib/cc/torint.h"
#include "lib/malloc/malloc.h"
#include <stdlib.h>
@ -45,7 +45,7 @@ tor_vsnprintf(char *str, size_t size, const char *format, va_list args)
return -1; /* no place for the NUL */
if (size > SIZE_T_CEILING)
return -1;
#ifdef _WIN32
#if defined(_WIN32) && !defined(HAVE_VSNPRINTF)
r = _vsnprintf(str, size, format, args);
#else
r = vsnprintf(str, size, format, args);