diff options
author | João Valverde <joao.valverde@tecnico.ulisboa.pt> | 2017-10-23 19:00:27 +0100 |
---|---|---|
committer | João Valverde <j@v6e.pt> | 2017-10-24 22:00:46 +0000 |
commit | e1ef8e5f7555a1608d0cddde6c824c5a897f6e58 (patch) | |
tree | 9da653772c2ba7d97ac17385597811bd86aa3f06 | |
parent | 08a490328387eafb7f9d20293a2a5e97e6cf4268 (diff) |
Test g_printf() thousands grouping flag at runtime
This tests the runtime environment so avoid hard-coding it during the build.
For now we avoid messing with locales for the test, unless it turns out to
be necessary (ISO C printf behaviour with invalid conversion specifier is
undefined).
Change-Id: I341c2ab5e716973689cf9002f13435404a41369f
Reviewed-on: https://code.wireshark.org/review/24038
Petri-Dish: João Valverde <j@v6e.pt>
Tested-by: Petri Dish Buildbot
Reviewed-by: João Valverde <j@v6e.pt>
-rw-r--r-- | ConfigureChecks.cmake | 35 | ||||
-rw-r--r-- | configure.ac | 35 | ||||
-rw-r--r-- | wsutil/str_util.c | 42 |
3 files changed, 29 insertions, 83 deletions
diff --git a/ConfigureChecks.cmake b/ConfigureChecks.cmake index c4bd431a1a..99732f9e7d 100644 --- a/ConfigureChecks.cmake +++ b/ConfigureChecks.cmake @@ -185,41 +185,6 @@ if (NL_FOUND) endif() # -# Check whether GLib's printf supports thousands grouping. (This might -# be different from the system's printf since GLib can optionally use -# its own printf implementation.) -# -if (CMAKE_CROSSCOMPILING OR WIN32) - # - # Play it safe when cross-compiling. - # - # XXX - compiling and trying to run the test below appears - # to loop infinitely on Windows, and the locale is wrong in - # any case, so we don't do this on Window for now. - # - set(HAVE_GLIB_PRINTF_GROUPING FALSE) -else() - cmake_push_check_state() - set(CMAKE_REQUIRED_INCLUDES ${GLIB2_INCLUDE_DIRS}) - set(CMAKE_REQUIRED_LIBRARIES ${GLIB2_LIBRARIES}) - check_c_source_runs( - "#include <glib.h> - #include <locale.h> - #include <stdio.h> - #include <string.h> - - int - main () - { - gchar *str; - setlocale(LC_ALL, \"en_US.UTF-8\"); - str = g_strdup_printf(\"%'u\", 123456); - return (strcmp (str, \"123,456\") != 0); - }" HAVE_GLIB_PRINTF_GROUPING) - cmake_pop_check_state() -endif() - -# # Editor modelines - http://www.wireshark.org/tools/modelines.html # # Local variables: diff --git a/configure.ac b/configure.ac index b504b5520c..cfbfb88c5a 100644 --- a/configure.ac +++ b/configure.ac @@ -1515,41 +1515,6 @@ then LIBS="$ac_save_LIBS" fi -# -# Check whether GLib's printf supports thousands grouping. (This might -# be different from the system's printf since GLib can optionally use -# its own printf implementation.) -# -AC_CACHE_CHECK([whether GLib supports POSIX/XSI thousands grouping], - [ac_cv_glib_supports_printf_grouping], [ -ac_save_CFLAGS="$CFLAGS" -ac_save_LIBS="$LIBS" -CFLAGS="$WS_CFLAGS $GLIB_CFLAGS $CFLAGS" -LIBS="$LIBS $GLIB_LIBS" -AC_TRY_RUN([ -#include <glib.h> -#include <locale.h> -#include <stdio.h> -#include <string.h> - -int -main () -{ - gchar *str; - setlocale(LC_ALL, "en_US.UTF-8"); - str = g_strdup_printf("%'u", 123456); - return (strcmp (str, "123,456") != 0); -} -], ac_cv_glib_supports_printf_grouping=yes, ac_cv_glib_supports_printf_grouping=no, - [echo $ac_n "cross compiling; playing it safe... $ac_c" - ac_cv_glib_supports_printf_grouping=no]) -CFLAGS="$ac_save_CFLAGS" -LIBS="$ac_save_LIBS" -]) -if test "$ac_cv_glib_supports_printf_grouping" = yes ; then - AC_DEFINE(HAVE_GLIB_PRINTF_GROUPING, 1, [Define if GLib's printf functions support thousands grouping.]) -fi - AC_SUBST(wireshark_bin) AC_SUBST(wireshark_man) AC_SUBST(wireshark_SUBDIRS) diff --git a/wsutil/str_util.c b/wsutil/str_util.c index 8763666f9a..e0e8531d9d 100644 --- a/wsutil/str_util.c +++ b/wsutil/str_util.c @@ -113,11 +113,21 @@ isdigit_string(guchar *str) #define FORMAT_SIZE_UNIT_MASK 0x00ff #define FORMAT_SIZE_PFX_MASK 0xff00 -#ifdef HAVE_GLIB_PRINTF_GROUPING -#define GROUP_FLAG "'" -#else -#define GROUP_FLAG "" -#endif +static const char *thousands_grouping_fmt = NULL; + +DIAG_OFF(format) +static void test_printf_thousands_grouping(void) { + /* test whether g_printf works with "'" flag character */ + gchar *str = g_strdup_printf("%'d", 22); + if (g_strcmp0(str, "22") == 0) { + thousands_grouping_fmt = "%'"G_GINT64_MODIFIER"d"; + } else { + /* Don't use */ + thousands_grouping_fmt = "%"G_GINT64_MODIFIER"d"; + } + g_free(str); +} +DIAG_ON(format) /* Given a size, return its value in a human-readable format */ /* This doesn't handle fractional values. We might want to make size a double. */ @@ -128,28 +138,34 @@ format_size(gint64 size, format_size_flags_e flags) int power = 1000; int pfx_off = 0; gboolean is_small = FALSE; - static const gchar *prefix[] = {"T", "G", "M", "k", "Ti", "Gi", "Mi", "Ki"}; + static const gchar *prefix[] = {" T", " G", " M", " k", " Ti", " Gi", " Mi", " Ki"}; gchar *ret_val; + if (thousands_grouping_fmt == NULL) + test_printf_thousands_grouping(); + if ((flags & FORMAT_SIZE_PFX_MASK) == format_size_prefix_iec) { pfx_off = 4; power = 1024; } -DIAG_OFF(format) if (size / power / power / power / power >= 10) { - g_string_printf(human_str, "%" GROUP_FLAG G_GINT64_MODIFIER "d %s", size / power / power / power / power, prefix[pfx_off]); + g_string_printf(human_str, thousands_grouping_fmt, size / power / power / power / power); + g_string_append(human_str, prefix[pfx_off]); } else if (size / power / power / power >= 10) { - g_string_printf(human_str, "%" GROUP_FLAG G_GINT64_MODIFIER "d %s", size / power / power / power, prefix[pfx_off+1]); + g_string_printf(human_str, thousands_grouping_fmt, size / power / power / power); + g_string_append(human_str, prefix[pfx_off+1]); } else if (size / power / power >= 10) { - g_string_printf(human_str, "%" GROUP_FLAG G_GINT64_MODIFIER "d %s", size / power / power, prefix[pfx_off+2]); + g_string_printf(human_str, thousands_grouping_fmt, size / power / power); + g_string_append(human_str, prefix[pfx_off+2]); } else if (size / power >= 10) { - g_string_printf(human_str, "%" GROUP_FLAG G_GINT64_MODIFIER "d %s", size / power, prefix[pfx_off+3]); + g_string_printf(human_str, thousands_grouping_fmt, size / power); + g_string_append(human_str, prefix[pfx_off+3]); } else { - g_string_printf(human_str, "%" GROUP_FLAG G_GINT64_MODIFIER "d", size); + g_string_printf(human_str, thousands_grouping_fmt, size); is_small = TRUE; } -DIAG_ON(format) + switch (flags & FORMAT_SIZE_UNIT_MASK) { case format_size_unit_none: |