From: Martin Quinson Date: Fri, 26 Feb 2016 01:02:37 +0000 (+0100) Subject: snprintf is C99, we require C11. kill the portability code X-Git-Tag: v3_13~671 X-Git-Url: http://info.iut-bm.univ-fcomte.fr/pub/gitweb/simgrid.git/commitdiff_plain/40538f98176832207ec50cc7b9413363bb4f4963 snprintf is C99, we require C11. kill the portability code --- diff --git a/CMakeLists.txt b/CMakeLists.txt index b79a0131a9..5d6c4064d9 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -319,8 +319,6 @@ CHECK_FUNCTION_EXISTS(getdtablesize HAVE_GETDTABLESIZE) CHECK_FUNCTION_EXISTS(sysconf HAVE_SYSCONF) CHECK_FUNCTION_EXISTS(popen HAVE_POPEN) -CHECK_SYMBOL_EXISTS(snprintf stdio.h HAVE_SNPRINTF) -CHECK_SYMBOL_EXISTS(vsnprintf stdio.h HAVE_VSNPRINTF) CHECK_SYMBOL_EXISTS(asprintf stdio.h HAVE_ASPRINTF) CHECK_SYMBOL_EXISTS(vasprintf stdio.h HAVE_VASPRINTF) @@ -328,8 +326,6 @@ if(MINGW) # The detection of asprintf fails on MinGW, assumingly because it's # defined as an inline function in stdio.h instead of a regular # function. So force the result to be 1 despite of the test. - set(HAVE_SNPRINTF 1) - set(HAVE_VSNPRINTF 1) set(HAVE_ASPRINTF 1) set(HAVE_VASPRINTF 1) endif() @@ -751,37 +747,6 @@ endif() ## System checks ## -### check for a working snprintf -if(HAVE_SNPRINTF AND HAVE_VSNPRINTF OR WIN32) - if(CMAKE_CROSSCOMPILING) - set(RUN_SNPRINTF_FUNC "cross") - #set(PREFER_PORTABLE_SNPRINTF 1) - else() - try_run(RUN_SNPRINTF_FUNC_VAR COMPILE_SNPRINTF_FUNC_VAR - ${CMAKE_BINARY_DIR} - ${CMAKE_HOME_DIRECTORY}/tools/cmake/test_prog/prog_snprintf.c - ) - endif() - - if(CMAKE_CROSSCOMPILING) - set(RUN_VSNPRINTF_FUNC "cross") - set(PREFER_PORTABLE_VSNPRINTF 1) - else() - try_run(RUN_VSNPRINTF_FUNC_VAR COMPILE_VSNPRINTF_FUNC_VAR - ${CMAKE_BINARY_DIR} - ${CMAKE_HOME_DIRECTORY}/tools/cmake/test_prog/prog_vsnprintf.c - ) - endif() - - set(PREFER_PORTABLE_SNPRINTF 0) - if(RUN_VSNPRINTF_FUNC_VAR MATCHES "FAILED_TO_RUN") - set(PREFER_PORTABLE_SNPRINTF 1) - endif() - if(RUN_SNPRINTF_FUNC_VAR MATCHES "FAILED_TO_RUN") - set(PREFER_PORTABLE_SNPRINTF 1) - endif() -endif() - ### check for asprintf function familly if(HAVE_ASPRINTF) SET(simgrid_need_asprintf "") diff --git a/src/portable.h b/src/portable.h index 7ccd0a7d64..7e7acfbec7 100644 --- a/src/portable.h +++ b/src/portable.h @@ -89,40 +89,12 @@ # include #endif -/**** - **** string handling (parts from http://www.ijs.si/software/snprintf/) - ****/ - -/* prototype of C99 functions */ -#if defined(HAVE_SNPRINTF) -#include -#else -XBT_PUBLIC(int) snprintf(char *, size_t, const char *, /*args */ ...); -XBT_PUBLIC(int) vsnprintf(char *, size_t, const char *, va_list); -#endif - - -/* use internal functions when OS provided ones are borken */ -#if defined(HAVE_SNPRINTF) && defined(PREFER_PORTABLE_SNPRINTF) -XBT_PRIVATE int portable_snprintf(char *str, size_t str_m, const char *fmt, - /*args */ ...); -XBT_PRIVATE int portable_vsnprintf(char *str, size_t str_m, const char *fmt, - va_list ap); -#define snprintf portable_snprintf -#define vsnprintf portable_vsnprintf -#endif - /* prototype of GNU functions */ #if (defined(__GNUC__) && !defined(__cplusplus)) XBT_PUBLIC(int) asprintf(char **ptr, const char *fmt, /*args */ ...); XBT_PUBLIC(int) vasprintf(char **ptr, const char *fmt, va_list ap); #endif -extern int asnprintf(char **ptr, size_t str_m, const char *fmt, /*args */ - ...); -extern int vasnprintf(char **ptr, size_t str_m, const char *fmt, - va_list ap); - /* * What we need to extract the backtrace in exception handling code */ diff --git a/src/xbt/dict.c b/src/xbt/dict.c index 5d220dcd3e..46d7509ad7 100644 --- a/src/xbt/dict.c +++ b/src/xbt/dict.c @@ -642,7 +642,6 @@ void xbt_dict_postexit(void) #include "xbt/ex.h" #include "src/portable.h" -#define PRINTF_STR(a) (a)?:"(null)" XBT_LOG_EXTERNAL_DEFAULT_CATEGORY(xbt_dict); @@ -653,8 +652,7 @@ static void debuged_add_ext(xbt_dict_t head, const char *key, { char *data = xbt_strdup(data_to_fill); - xbt_test_log("Add %s under %s", PRINTF_STR(data_to_fill), - PRINTF_STR(key)); + xbt_test_log("Add %s under %s", data_to_fill, key); xbt_dict_set(head, key, data, free_f); if (XBT_LOG_ISENABLED(xbt_dict, xbt_log_priority_debug)) { @@ -717,7 +715,7 @@ static void search(xbt_dict_t head, const char *key) static void debuged_remove(xbt_dict_t head, const char *key) { - xbt_test_add("Remove '%s'", PRINTF_STR(key)); + xbt_test_add("Remove '%s'", key); xbt_dict_remove(head, key); /* xbt_dict_dump(head,(void (*)(void*))&printf); */ } @@ -732,10 +730,9 @@ static void traverse(xbt_dict_t head) xbt_dict_foreach(head, cursor, key, data) { if (!key || !data || strcmp(key, data)) { - xbt_test_log("Seen #%d: %s->%s", ++i, PRINTF_STR(key), - PRINTF_STR(data)); + xbt_test_log("Seen #%d: %s->%s", ++i, key, data); } else { - xbt_test_log("Seen #%d: %s", ++i, PRINTF_STR(key)); + xbt_test_log("Seen #%d: %s", ++i, key); } xbt_test_assert(!data || !strcmp(key, data), "Key(%s) != value(%s). Aborting", key, data); @@ -1012,9 +1009,9 @@ XBT_TEST_UNIT("nulldata", test_dict_nulldata, "NULL data management") xbt_dict_foreach(head, cursor, key, data) { if (!key || !data || strcmp(key, data)) { - xbt_test_log("Seen: %s->%s", PRINTF_STR(key), PRINTF_STR(data)); + xbt_test_log("Seen: %s->%s", key, data); } else { - xbt_test_log("Seen: %s", PRINTF_STR(key)); + xbt_test_log("Seen: %s", key); } if (!strcmp(key, "null")) diff --git a/src/xbt/snprintf.c b/src/xbt/snprintf.c index 89df5fbaae..605231415f 100644 --- a/src/xbt/snprintf.c +++ b/src/xbt/snprintf.c @@ -190,45 +190,6 @@ * not used; */ - -/* Define HAVE_SNPRINTF if your system already has snprintf and vsnprintf. - * - * If HAVE_SNPRINTF is defined this module will not produce code for - * snprintf and vsnprintf, unless PREFER_PORTABLE_SNPRINTF is defined as well, - * causing this portable version of snprintf to be called portable_snprintf - * (and portable_vsnprintf). - */ -/* #define HAVE_SNPRINTF */ - -/* Define PREFER_PORTABLE_SNPRINTF if your system does have snprintf and - * vsnprintf but you would prefer to use the portable routine(s) instead. - * In this case the portable routine is declared as portable_snprintf - * (and portable_vsnprintf) and a macro 'snprintf' (and 'vsnprintf') - * is defined to expand to 'portable_v?snprintf' - see file snprintf.h . - * Defining this macro is only useful if HAVE_SNPRINTF is also defined, - * but does does no harm if defined nevertheless. - */ -/* #define PREFER_PORTABLE_SNPRINTF */ - -/* Define SNPRINTF_LONGLONG_SUPPORT if you want to support - * data type (long long int) and length modifier 'll' (e.g. %lld). - * If undefined, 'll' is recognized but treated as a single 'l'. - * - * If the system's sprintf does not handle 'll' - * the SNPRINTF_LONGLONG_SUPPORT must not be defined! - * - * This is off by default as (long long int) is a language extension. - */ -/* #define SNPRINTF_LONGLONG_SUPPORT */ - -/* Define NEED_SNPRINTF_ONLY if you only need snprintf, and not vsnprintf. - * If NEED_SNPRINTF_ONLY is defined, the snprintf will be defined directly, - * otherwise both snprintf and vsnprintf routines will be defined - * and snprintf will be a simple wrapper around vsnprintf, at the expense - * of an extra procedure call. - */ -/* #define NEED_SNPRINTF_ONLY */ - /* Define NEED_V?ASN?PRINTF macros if you need library extension * routines asprintf, vasprintf, asnprintf, vasnprintf respectively, * and your system library does not provide them. They are all small @@ -252,75 +213,10 @@ /* #define NEED_VASNPRINTF */ -/* Define the following macros if desired: - * SOLARIS_COMPATIBLE, SOLARIS_BUG_COMPATIBLE, - * HPUX_COMPATIBLE, HPUX_BUG_COMPATIBLE, LINUX_COMPATIBLE, - * DIGITAL_UNIX_COMPATIBLE, DIGITAL_UNIX_BUG_COMPATIBLE, - * PERL_COMPATIBLE, PERL_BUG_COMPATIBLE, - * - * - For portable applications it is best not to rely on peculiarities - * of a given implementation so it may be best not to define any - * of the macros that select compatibility and to avoid features - * that vary among the systems. - * - * - Selecting compatibility with more than one operating system - * is not strictly forbidden but is not recommended. - * - * - 'x'_BUG_COMPATIBLE implies 'x'_COMPATIBLE . - * - * - 'x'_COMPATIBLE refers to (and enables) a behaviour that is - * documented in a sprintf man page on a given operating system - * and actually adhered to by the system's sprintf (but not on - * most other operating systems). It may also refer to and enable - * a behaviour that is declared 'undefined' or 'implementation specific' - * in the man page but a given implementation behaves predictably - * in a certain way. - * - * - 'x'_BUG_COMPATIBLE refers to (and enables) a behaviour of system's sprintf - * that contradicts the sprintf man page on the same operating system. - * - * - I do not claim that the 'x'_COMPATIBLE and 'x'_BUG_COMPATIBLE - * conditionals take into account all idiosyncrasies of a particular - * implementation, there may be other incompatibilities. - */ - - /* ============================================= */ /* NO USER SERVICABLE PARTS FOLLOWING THIS POINT */ /* ============================================= */ -#define PORTABLE_SNPRINTF_VERSION_MAJOR 2 -#define PORTABLE_SNPRINTF_VERSION_MINOR 2 - -#if defined(NEED_ASPRINTF) || defined(NEED_ASNPRINTF) || defined(NEED_VASPRINTF) || defined(NEED_VASNPRINTF) -# if defined(NEED_SNPRINTF_ONLY) -# undef NEED_SNPRINTF_ONLY -# endif -# if !defined(PREFER_PORTABLE_SNPRINTF) -# define PREFER_PORTABLE_SNPRINTF -# endif -#endif - -#if defined(SOLARIS_BUG_COMPATIBLE) && !defined(SOLARIS_COMPATIBLE) -#define SOLARIS_COMPATIBLE -#endif - -#if defined(HPUX_BUG_COMPATIBLE) && !defined(HPUX_COMPATIBLE) -#define HPUX_COMPATIBLE -#endif - -#if defined(DIGITAL_UNIX_BUG_COMPATIBLE) && !defined(DIGITAL_UNIX_COMPATIBLE) -#define DIGITAL_UNIX_COMPATIBLE -#endif - -#if defined(PERL_BUG_COMPATIBLE) && !defined(PERL_COMPATIBLE) -#define PERL_COMPATIBLE -#endif - -#if defined(LINUX_BUG_COMPATIBLE) && !defined(LINUX_COMPATIBLE) -#define LINUX_COMPATIBLE -#endif - #include "src/portable.h" /* to get a working stdarg.h */ #include @@ -333,59 +229,6 @@ #include #include "xbt/str.h" -#ifdef isdigit -#undef isdigit -#endif -#define isdigit(c) ((c) >= '0' && (c) <= '9') - -/* For copying strings longer or equal to 'breakeven_point' - * it is more efficient to call memcpy() than to do it inline. - * The value depends mostly on the processor architecture, - * but also on the compiler and its optimization capabilities. - * The value is not critical, some small value greater than zero - * will be just fine if you don't care to squeeze every drop - * of performance out of the code. - * - * Small values favor memcpy, large values favor inline code. - */ -#if defined(__alpha__) || defined(__alpha) -# define breakeven_point 2 /* AXP (DEC Alpha) - gcc or cc or egcs */ -#endif -#if defined(__i386__) || defined(__i386) -# define breakeven_point 12 /* Intel Pentium/Linux - gcc 2.96 */ -#endif -#if defined(__hppa) -# define breakeven_point 10 /* HP-PA - gcc */ -#endif -#if defined(__sparc__) || defined(__sparc) -# define breakeven_point 33 /* Sun Sparc 5 - gcc 2.8.1 */ -#endif - -/* some other values of possible interest: */ - /* #define breakeven_point 8 *//* VAX 4000 - vaxc */ - /* #define breakeven_point 19 *//* VAX 4000 - gcc 2.7.0 */ - -#ifndef breakeven_point -# define breakeven_point 6 /* some reasonable one-size-fits-all value */ -#endif - -#define fast_memcpy(d,s,n) \ - { size_t nn = (size_t)(n); \ - if (nn >= breakeven_point) memcpy((d), (s), nn); \ - else if (nn > 0) { /* proc call overhead is worth only for large strings*/\ - char *dd; const char *ss; \ - for (ss=(s), dd=(d); nn>0; nn--) *dd++ = *ss++; } } - -#define fast_memset(d,c,n) \ - { size_t nn = (size_t)(n); \ - if (nn >= breakeven_point) memset((d), (int)(c), nn); \ - else if (nn > 0) { /* proc call overhead is worth only for large strings*/\ - char *dd; const int cc=(int)(c); \ - for (dd=(d); nn>0; nn--) *dd++ = cc; } } - -/* prototypes */ - - #if defined(NEED_ASPRINTF) int asprintf(char **ptr, const char *fmt, /*args */ ...); #endif @@ -393,39 +236,6 @@ int asprintf(char **ptr, const char *fmt, /*args */ ...); int vasprintf(char **ptr, const char *fmt, va_list ap); #endif -#if defined(NEED_ASNPRINTF) -int asnprintf(char **ptr, size_t str_m, const char *fmt, /*args */ ...); -#endif -#if defined(NEED_VASNPRINTF) -int vasnprintf(char **ptr, size_t str_m, const char *fmt, va_list ap); -#endif - -#if defined(HAVE_SNPRINTF) -/* declare our portable snprintf routine under name portable_snprintf */ -/* declare our portable vsnprintf routine under name portable_vsnprintf */ -# if defined(_MSC_VER) && (_MSC_VER >= 1400) -# define portable_snprintf _snprintf -# define portable_vsnprintf vsnprintf -# else -# define portable_snprintf snprintf -# define portable_vsnprintf vsnprintf -# endif -#else -/* declare our portable routines under names snprintf and vsnprintf */ -#define portable_snprintf snprintf -#if !defined(NEED_SNPRINTF_ONLY) -#define portable_vsnprintf vsnprintf -#endif -#endif - -#if !defined(HAVE_SNPRINTF) || defined(PREFER_PORTABLE_SNPRINTF) -int portable_snprintf(char *str, size_t str_m, const char *fmt, /*args */ - ...); -#if !defined(NEED_SNPRINTF_ONLY) -int portable_vsnprintf(char *str, size_t str_m, const char *fmt, - va_list ap); -#endif -#endif /* FIXME: better place */ #include "xbt/sysdep.h" @@ -555,618 +365,6 @@ int vasnprintf(char **ptr, size_t str_m, const char *fmt, va_list ap) } #endif -/* - * If the system does have snprintf and the portable routine is not - * specifically required, this module produces no code for snprintf/vsnprintf. - */ -#if !defined(HAVE_SNPRINTF) || defined(PREFER_PORTABLE_SNPRINTF) - -#if !defined(NEED_SNPRINTF_ONLY) -int portable_snprintf(char *str, size_t str_m, const char *fmt, /*args */ - ...) -{ - va_list ap; - int str_l; - - va_start(ap, fmt); - str_l = portable_vsnprintf(str, str_m, fmt, ap); - va_end(ap); - return str_l; -} -#endif - -#if defined(NEED_SNPRINTF_ONLY) -int portable_snprintf(char *str, size_t str_m, const char *fmt, /*args */ - ...) -{ -#else -int portable_vsnprintf(char *str, size_t str_m, const char *fmt, - va_list ap) -{ -#endif - -#if defined(NEED_SNPRINTF_ONLY) - va_list ap; -#endif - size_t str_l = 0; - const char *p = fmt; - - /* In contrast with POSIX, the ISO C99 now says - * that str can be NULL and str_m can be 0. - * This is more useful than the old: if (str_m < 1) return -1; */ - -#if defined(NEED_SNPRINTF_ONLY) - va_start(ap, fmt); -#endif - if (!p) - p = ""; - while (*p) { - if (*p != '%') { - /* if (str_l < str_m) str[str_l++] = *p++; -- this would be sufficient */ - /* but the following code achieves better performance for cases - * where format string is long and contains few conversions */ - const char *q = strchr(p + 1, '%'); - size_t n = !q ? strlen(p) : (q - p); - if (str_l < str_m) { - size_t avail = str_m - str_l; - fast_memcpy(str + str_l, p, (n > avail ? avail : n)); - } - p += n; - str_l += n; - } else { - const char *starting_p; - size_t min_field_width = 0, precision = 0; - int zero_padding = 0, precision_specified = 0, justify_left = 0; - int alternate_form = 0, force_sign = 0; - int space_for_positive = 1; /* If both the ' ' and '+' flags appear, - the ' ' flag should be ignored. */ - char length_modifier = '\0'; /* allowed values: \0, h, l, L */ - char tmp[32]; /* temporary buffer for simple numeric->string conversion */ - - const char *str_arg; /* string address in case of string argument */ - size_t str_arg_l; /* natural field width of arg without padding - and sign */ - unsigned char uchar_arg; - /* unsigned char argument value - only defined for c conversion. - N.B. standard explicitly states the char argument for - the c conversion is unsigned */ - - size_t number_of_zeros_to_pad = 0; - /* number of zeros to be inserted for numeric conversions - as required by the precision or minimal field width */ - - size_t zero_padding_insertion_ind = 0; - /* index into tmp where zero padding is to be inserted */ - - char fmt_spec = '\0'; - /* current conversion specifier character */ - - str_arg = credits; /* just to make compiler happy (defined but not used) */ - str_arg = NULL; - starting_p = p; - p++; /* skip '%' */ - /* parse flags */ - while (*p == '0' || *p == '-' || *p == '+' || - *p == ' ' || *p == '#' || *p == '\'') { - switch (*p) { - case '0': - zero_padding = 1; - break; - case '-': - justify_left = 1; - break; - case '+': - force_sign = 1; - space_for_positive = 0; - break; - case ' ': - force_sign = 1; - /* If both the ' ' and '+' flags appear, the ' ' flag should be ignored */ -#ifdef PERL_COMPATIBLE - /* ... but in Perl the last of ' ' and '+' applies */ - space_for_positive = 1; -#endif - break; - case '#': - alternate_form = 1; - break; - case '\'': - break; - } - p++; - } - /* If the '0' and '-' flags both appear, the '0' flag should be ignored. */ - - /* parse field width */ - if (*p == '*') { - int j; - p++; - j = va_arg(ap, int); - if (j >= 0) - min_field_width = j; - else { - min_field_width = -j; - justify_left = 1; - } - } else if (isdigit((int) (*p))) { - /* size_t could be wider than unsigned int; - make sure we treat argument like common implementations do */ - unsigned int uj = *p++ - '0'; - while (isdigit((int) (*p))) - uj = 10 * uj + (unsigned int) (*p++ - '0'); - min_field_width = uj; - } - /* parse precision */ - if (*p == '.') { - p++; - precision_specified = 1; - if (*p == '*') { - int j = va_arg(ap, int); - p++; - if (j >= 0) - precision = j; - else { - precision_specified = 0; - precision = 0; - /* NOTE: - * Solaris 2.6 man page claims that in this case the precision - * should be set to 0. Digital Unix 4.0, HPUX 10 and BSD man page - * claim that this case should be treated as unspecified precision, - * which is what we do here. - */ - } - } else if (isdigit((int) (*p))) { - /* size_t could be wider than unsigned int; - make sure we treat argument like common implementations do */ - unsigned int uj = *p++ - '0'; - while (isdigit((int) (*p))) - uj = 10 * uj + (unsigned int) (*p++ - '0'); - precision = uj; - } - } - /* parse 'h', 'l' and 'll' length modifiers */ - if (*p == 'h' || *p == 'l') { - length_modifier = *p; - p++; - if (length_modifier == 'l' && *p == 'l') { /* double l = long long */ -#ifdef SNPRINTF_LONGLONG_SUPPORT - length_modifier = '2'; /* double l encoded as '2' */ -#else - length_modifier = 'l'; /* treat it as a single 'l' */ -#endif - p++; - } - } - fmt_spec = *p; - /* common synonyms: */ - switch (fmt_spec) { - case 'i': - fmt_spec = 'd'; - break; - case 'D': - fmt_spec = 'd'; - length_modifier = 'l'; - break; - case 'U': - fmt_spec = 'u'; - length_modifier = 'l'; - break; - case 'O': - fmt_spec = 'o'; - length_modifier = 'l'; - break; - default: - break; - } - /* get parameter value, do initial processing */ - switch (fmt_spec) { - case '%': /* % behaves similar to 's' regarding flags and field widths */ - case 'c': /* c behaves similar to 's' regarding flags and field widths */ - case 's': - length_modifier = '\0'; /* wint_t and wchar_t not supported */ - /* the result of zero padding flag with non-numeric conversion specifier */ - /* is undefined. Solaris and HPUX 10 does zero padding in this case, */ - /* Digital Unix and Linux does not. */ -#if !defined(SOLARIS_COMPATIBLE) && !defined(HPUX_COMPATIBLE) - zero_padding = 0; /* turn zero padding off for string conversions */ -#endif - str_arg_l = 1; - switch (fmt_spec) { - case '%': - str_arg = p; - break; - case 'c':{ - int j = va_arg(ap, int); - uchar_arg = (unsigned char) j; /* standard demands unsigned char */ - str_arg = (const char *) &uchar_arg; - break; - } - case 's': - str_arg = va_arg(ap, const char *); - if (!str_arg) - str_arg_l = 0; - /* make sure not to address string beyond the specified precision !!! */ - else if (!precision_specified) - str_arg_l = strlen(str_arg); - /* truncate string if necessary as requested by precision */ - else if (precision == 0) - str_arg_l = 0; - else { - /* memchr on HP does not like n > 2^31 !!! */ - char *q = (char *) memchr(str_arg, '\0', - precision <= - 0x7fffffff ? precision : 0x7fffffff); - str_arg_l = !q ? precision : (q - str_arg); - } - break; - default: - break; - } - break; - case 'd': - case 'u': - case 'o': - case 'x': - case 'X': - case 'p':{ - /* NOTE: the u, o, x, X and p conversion specifiers imply - the value is unsigned; d implies a signed value */ - - int arg_sign = 0; - /* 0 if numeric argument is zero (or if pointer is NULL for 'p'), - +1 if greater than zero (or nonzero for unsigned arguments), - -1 if negative (unsigned argument is never negative) */ - - int int_arg = 0; - unsigned int uint_arg = 0; - /* only defined for length modifier h, or for no length modifiers */ - - long int long_arg = 0; - unsigned long int ulong_arg = 0; - /* only defined for length modifier l */ - - void *ptr_arg = NULL; - /* pointer argument value -only defined for p conversion */ - -#ifdef SNPRINTF_LONGLONG_SUPPORT - long long int long_long_arg = 0; - unsigned long long int ulong_long_arg = 0; - /* only defined for length modifier ll */ -#endif - if (fmt_spec == 'p') { - /* HPUX 10: An l, h, ll or L before any other conversion character - * (other than d, i, u, o, x, or X) is ignored. - * Digital Unix: - * not specified, but seems to behave as HPUX does. - * Solaris: If an h, l, or L appears before any other conversion - * specifier (other than d, i, u, o, x, or X), the behavior - * is undefined. (Actually %hp converts only 16-bits of address - * and %llp treats address as 64-bit data which is incompatible - * with (void *) argument on a 32-bit system). - */ -#ifdef SOLARIS_COMPATIBLE -# ifdef SOLARIS_BUG_COMPATIBLE - /* keep length modifiers even if it represents 'll' */ -# else - if (length_modifier == '2') - length_modifier = '\0'; -# endif -#else - length_modifier = '\0'; -#endif - ptr_arg = va_arg(ap, void *); - if (ptr_arg != NULL) - arg_sign = 1; - } else if (fmt_spec == 'd') { /* signed */ - switch (length_modifier) { - case '\0': - case 'h': - /* It is non-portable to specify a second argument of char or short - * to va_arg, because arguments seen by the called function - * are not char or short. C converts char and short arguments - * to int before passing them to a function. - */ - int_arg = va_arg(ap, int); - if (int_arg > 0) - arg_sign = 1; - else if (int_arg < 0) - arg_sign = -1; - break; - case 'l': - long_arg = va_arg(ap, long int); - if (long_arg > 0) - arg_sign = 1; - else if (long_arg < 0) - arg_sign = -1; - break; -#ifdef SNPRINTF_LONGLONG_SUPPORT - case '2': - long_long_arg = va_arg(ap, long long int); - if (long_long_arg > 0) - arg_sign = 1; - else if (long_long_arg < 0) - arg_sign = -1; - break; -#endif - } - } else { /* unsigned */ - switch (length_modifier) { - case '\0': - case 'h': - uint_arg = va_arg(ap, unsigned int); - if (uint_arg) - arg_sign = 1; - break; - case 'l': - ulong_arg = va_arg(ap, unsigned long int); - if (ulong_arg) - arg_sign = 1; - break; -#ifdef SNPRINTF_LONGLONG_SUPPORT - case '2': - ulong_long_arg = va_arg(ap, unsigned long long int); - if (ulong_long_arg) - arg_sign = 1; - break; -#endif - } - } - str_arg = tmp; - str_arg_l = 0; - /* NOTE: - * For d, i, u, o, x, and X conversions, if precision is specified, - * the '0' flag should be ignored. This is so with Solaris 2.6, - * Digital UNIX 4.0, HPUX 10, Linux, FreeBSD, NetBSD; but not with Perl. - */ -#ifndef PERL_COMPATIBLE - if (precision_specified) - zero_padding = 0; -#endif - if (fmt_spec == 'd') { - if (force_sign && arg_sign >= 0) - tmp[str_arg_l++] = space_for_positive ? ' ' : '+'; - /* leave negative numbers for sprintf to handle, - to avoid handling tricky cases like (short int)(-32768) */ -#ifdef LINUX_COMPATIBLE - } else if (fmt_spec == 'p' && force_sign && arg_sign > 0) { - tmp[str_arg_l++] = space_for_positive ? ' ' : '+'; -#endif - } else if (alternate_form) { - if (arg_sign != 0 && (fmt_spec == 'x' || fmt_spec == 'X')) { - tmp[str_arg_l++] = '0'; - tmp[str_arg_l++] = fmt_spec; - } - /* alternate form should have no effect for p conversion, but ... */ -#ifdef HPUX_COMPATIBLE - else if (fmt_spec == 'p' - /* HPUX 10: for an alternate form of p conversion, - * a nonzero result is prefixed by 0x. */ -#ifndef HPUX_BUG_COMPATIBLE - /* Actually it uses 0x prefix even for a zero value. */ - && arg_sign != 0 -#endif - ) { - tmp[str_arg_l++] = '0'; - tmp[str_arg_l++] = 'x'; - } -#endif - } - zero_padding_insertion_ind = str_arg_l; - if (!precision_specified) - precision = 1; /* default precision is 1 */ - if (precision == 0 && arg_sign == 0 -#if defined(HPUX_BUG_COMPATIBLE) || defined(LINUX_COMPATIBLE) - && fmt_spec != 'p' - /* HPUX 10 man page claims: With conversion character p the result of - * converting a zero value with a precision of zero is a null string. - * Actually HP returns all zeroes, and Linux returns "(nil)". */ -#endif - ) { - /* converted to null string */ - /* When zero value is formatted with an explicit precision 0, - the resulting formatted string is empty (d, i, u, o, x, X, p). */ - } else { - char f[5]; - int f_l = 0; - f[f_l++] = '%'; /* construct a simple format string for sprintf */ - if (!length_modifier) { - } else if (length_modifier == '2') { - f[f_l++] = 'l'; - f[f_l++] = 'l'; - } else - f[f_l++] = length_modifier; - f[f_l++] = fmt_spec; - f[f_l++] = '\0'; - if (fmt_spec == 'p') - str_arg_l += sprintf(tmp + str_arg_l, f, ptr_arg); - else if (fmt_spec == 'd') { /* signed */ - switch (length_modifier) { - case '\0': - case 'h': - str_arg_l += sprintf(tmp + str_arg_l, f, int_arg); - break; - case 'l': - str_arg_l += sprintf(tmp + str_arg_l, f, long_arg); - break; -#ifdef SNPRINTF_LONGLONG_SUPPORT - case '2': - str_arg_l += sprintf(tmp + str_arg_l, f, long_long_arg); - break; -#endif - } - } else { /* unsigned */ - switch (length_modifier) { - case '\0': - case 'h': - str_arg_l += sprintf(tmp + str_arg_l, f, uint_arg); - break; - case 'l': - str_arg_l += sprintf(tmp + str_arg_l, f, ulong_arg); - break; -#ifdef SNPRINTF_LONGLONG_SUPPORT - case '2': - str_arg_l += sprintf(tmp + str_arg_l, f, ulong_long_arg); - break; -#endif - } - } - /* include the optional minus sign and possible "0x" - in the region before the zero padding insertion point */ - if (zero_padding_insertion_ind < str_arg_l && - tmp[zero_padding_insertion_ind] == '-') { - zero_padding_insertion_ind++; - } - if (zero_padding_insertion_ind + 1 < str_arg_l && - tmp[zero_padding_insertion_ind] == '0' && - (tmp[zero_padding_insertion_ind + 1] == 'x' || - tmp[zero_padding_insertion_ind + 1] == 'X')) { - zero_padding_insertion_ind += 2; - } - } - { - size_t num_of_digits = str_arg_l - zero_padding_insertion_ind; - if (alternate_form && fmt_spec == 'o' -#ifdef HPUX_COMPATIBLE /* ("%#.o",0) -> "" */ - && (str_arg_l > 0) -#endif -#ifdef DIGITAL_UNIX_BUG_COMPATIBLE /* ("%#o",0) -> "00" */ -#else - /* unless zero is already the first character */ - && !(zero_padding_insertion_ind < str_arg_l - && tmp[zero_padding_insertion_ind] == '0') -#endif - ) { /* assure leading zero for alternate-form octal numbers */ - if (!precision_specified || precision < num_of_digits + 1) { - /* precision is increased to force the first character to be zero, - except if a zero value is formatted with an explicit precision - of zero */ - precision = num_of_digits + 1; - precision_specified = 1; - } - } - /* zero padding to specified precision? */ - if (num_of_digits < precision) - number_of_zeros_to_pad = precision - num_of_digits; - } - /* zero padding to specified minimal field width? */ - if (!justify_left && zero_padding) { - int n = min_field_width - (str_arg_l + number_of_zeros_to_pad); - if (n > 0) - number_of_zeros_to_pad += n; - } - break; - } - default: /* unrecognized conversion specifier, keep format string as-is */ - zero_padding = 0; /* turn zero padding off for non-numeric convers. */ -#ifndef DIGITAL_UNIX_COMPATIBLE - justify_left = 1; - min_field_width = 0; /* reset flags */ -#endif -#if defined(PERL_COMPATIBLE) || defined(LINUX_COMPATIBLE) - /* keep the entire format string unchanged */ - str_arg = starting_p; - str_arg_l = p - starting_p; - /* well, not exactly so for Linux, which does something inbetween, - * and I don't feel an urge to imitate it: "%+++++hy" -> "%+y" */ -#else - /* discard the unrecognized conversion, just keep * - * the unrecognized conversion character */ - str_arg = p; - str_arg_l = 0; -#endif - if (*p) - str_arg_l++; /* include invalid conversion specifier unchanged - if not at end-of-string */ - break; - } - if (*p) - p++; /* step over the just processed conversion specifier */ - /* insert padding to the left as requested by min_field_width; - this does not include the zero padding in case of numerical conversions */ - if (!justify_left) { /* left padding with blank or zero */ - int n = min_field_width - (str_arg_l + number_of_zeros_to_pad); - if (n > 0) { - if (str_l < str_m) { - int avail = str_m - str_l; - fast_memset(str + str_l, (zero_padding ? '0' : ' '), - (n > avail ? avail : n)); - } - str_l += n; - } - } - /* zero padding as requested by the precision or by the minimal field width - * for numeric conversions required? */ - if (number_of_zeros_to_pad <= 0) { - /* will not copy first part of numeric right now, * - * force it to be copied later in its entirety */ - zero_padding_insertion_ind = 0; - } else { - /* insert first part of numerics (sign or '0x') before zero padding */ - int n = zero_padding_insertion_ind; - if (n > 0) { - if (str_l < str_m) { - int avail = str_m - str_l; - fast_memcpy(str + str_l, str_arg, (n > avail ? avail : n)); - } - str_l += n; - } - /* insert zero padding as requested by the precision or min field width */ - n = number_of_zeros_to_pad; - if (n > 0) { - if (str_l < str_m) { - int avail = str_m - str_l; - fast_memset(str + str_l, '0', (n > avail ? avail : n)); - } - str_l += n; - } - } - /* insert formatted string - * (or as-is conversion specifier for unknown conversions) */ - { - int n = str_arg_l - zero_padding_insertion_ind; - if (n > 0) { - if (str_l < str_m) { - int avail = str_m - str_l; - fast_memcpy(str + str_l, str_arg + zero_padding_insertion_ind, - (n > avail ? avail : n)); - } - str_l += n; - } - } - /* insert right padding */ - if (justify_left) { /* right blank padding to the field width */ - int n = min_field_width - (str_arg_l + number_of_zeros_to_pad); - if (n > 0) { - if (str_l < str_m) { - int avail = str_m - str_l; - fast_memset(str + str_l, ' ', (n > avail ? avail : n)); - } - str_l += n; - } - } - } - } -#if defined(NEED_SNPRINTF_ONLY) - va_end(ap); -#endif - if (str_m > 0) { /* make sure the string is null-terminated - even at the expense of overwriting the last character - (shouldn't happen, but just in case) */ - str[str_l <= str_m - 1 ? str_l : str_m - 1] = '\0'; - } - /* Return the number of characters formatted (excluding trailing null - * character), that is, the number of characters that would have been - * written to the buffer if it were large enough. - * - * The value of str_l should be returned, but str_l is of unsigned type - * size_t, and snprintf is int, possibly leading to an undetected - * integer overflow, resulting in a negative return value, which is illegal. - * Both XSH5 and ISO C99 (at least the draft) are silent on this issue. - * Should errno be set to EOVERFLOW and EOF returned in this case??? - */ - return (int) str_l; -} -#endif char *bvprintf(const char *fmt, va_list ap) diff --git a/tools/cmake/PrintArgs.cmake b/tools/cmake/PrintArgs.cmake index b80d7a0250..1727555e40 100644 --- a/tools/cmake/PrintArgs.cmake +++ b/tools/cmake/PrintArgs.cmake @@ -7,7 +7,6 @@ if(enable_print_message) message("PTH_STACKGROWTH .............: ${PTH_STACKGROWTH}") message("need_asprintf ...............: ${simgrid_need_asprintf}") message("need_vasprintf ..............: ${simgrid_need_vasprintf}") - message("PREFER_PORTABLE_SNPRINTF ....: ${PREFER_PORTABLE_SNPRINTF}") message("HAVE_VA_COPY ................: ${HAVE_VA_COPY}") message("") message("\#define pth_skaddr_makecontext(skaddr,sksize) (${makecontext_addr})") @@ -40,8 +39,6 @@ if(enable_print_message) message("HAVE_SYSCONF ................: ${HAVE_SYSCONF}") message("HAVE_POPEN ..................: ${HAVE_POPEN}") message("HAVE_MAKECONTEXT ............: ${HAVE_MAKECONTEXT}") - message("HAVE_SNPRINTF ...............: ${HAVE_SNPRINTF}") - message("HAVE_VSNPRINTF ..............: ${HAVE_VSNPRINTF}") message("HAVE_ASPRINTF ...............: ${HAVE_ASPRINTF}") message("HAVE_VASPRINTF ..............: ${HAVE_VASPRINTF}") message("HAVE_MMAP ...................: ${HAVE_MMAP}") diff --git a/tools/cmake/src/internal_config.h.in b/tools/cmake/src/internal_config.h.in index de3a7d5d42..4cff92476e 100644 --- a/tools/cmake/src/internal_config.h.in +++ b/tools/cmake/src/internal_config.h.in @@ -130,9 +130,6 @@ /* Define to 1 if you have the header file. */ #cmakedefine HAVE_SIGNAL_H @HAVE_SIGNAL_H@ -/* Define to 1 if you have the `snprintf' function. */ -#cmakedefine HAVE_SNPRINTF @HAVE_SNPRINTF@ - /* Define to 1 if you have the header file. */ #cmakedefine HAVE_STDINT_H @HAVE_STDINT_H@ @@ -160,9 +157,6 @@ /* Define to 1 if you have the header file. */ #cmakedefine HAVE_VALGRIND_VALGRIND_H @HAVE_VALGRIND_VALGRIND_H@ -/* Define to 1 if you have the `vsnprintf' function. */ -#cmakedefine HAVE_VSNPRINTF @HAVE_VSNPRINTF@ - /* Define to 1 if you have the header file. */ #cmakedefine HAVE_WINDOWS_H @HAVE_WINDOWS_H@ @@ -193,9 +187,6 @@ /* Define to the version of this package. */ #cmakedefine PACKAGE_VERSION @PACKAGE_VERSION@ -/* "enable replacement (v)snprintf if system (v)snprintf is broken" */ -#cmakedefine PREFER_PORTABLE_SNPRINTF @PREFER_PORTABLE_SNPRINTF@ - /* define for stack growth */ #cmakedefine PTH_STACKGROWTH @PTH_STACKGROWTH@