diff --git a/lib/cppmyth/CMakeLists.txt b/lib/cppmyth/CMakeLists.txt index 9e3a5bd8..d09006bd 100644 --- a/lib/cppmyth/CMakeLists.txt +++ b/lib/cppmyth/CMakeLists.txt @@ -15,7 +15,7 @@ endif () # set lib version here set (PACKAGE_VERSION_MAJOR 2) set (PACKAGE_VERSION_MINOR 17) -set (PACKAGE_VERSION_PATCH 3) +set (PACKAGE_VERSION_PATCH 4) set (PACKAGE_VERSION ${PACKAGE_VERSION_MAJOR}.${PACKAGE_VERSION_MINOR}.${PACKAGE_VERSION_PATCH}) set (PACKAGE_LIB_SOVERSION ${PACKAGE_VERSION_MAJOR}) diff --git a/lib/cppmyth/src/private/builtin.c b/lib/cppmyth/src/private/builtin.c index 55f77e4d..86a3ed27 100644 --- a/lib/cppmyth/src/private/builtin.c +++ b/lib/cppmyth/src/private/builtin.c @@ -1,5 +1,5 @@ /* - * Copyright (C) 2014-2023 Jean-Luc Barriere + * Copyright (C) 2014-2024 Jean-Luc Barriere * * This Program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -215,6 +215,42 @@ int hex_to_num(const char *str, int *num) return 0; } +unsigned uint_to_strdec(unsigned u, char *str, unsigned len, int pad) +{ + static const char g[10] = { + '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', + }; + if (len) + { + char *ptr = str, *end = str + len; + unsigned n = u, n10 = u / 10; + do + { + *ptr++ = g[n - n10 * 10]; + n = n10; + } while ((n10 = n / 10) > 0 && ptr < end); + if (ptr < end) + { + /* push last digit */ + if (n > 0) + *ptr++ = g[n]; + /* padding */ + if (pad) + while (ptr < end) *ptr++ = '0'; + } + len = ptr - str; + /* reorder digits */ + while (--ptr > str) + { + char c = *str; + *str = *ptr; + *ptr = c; + ++str; + } + } + return len; +} + time_t __timegm(struct tm *utctime_tm) { time_t time; @@ -384,13 +420,20 @@ void time_to_iso8601utc(time_t time, BUILTIN_BUFFER *str) str->data[0] = '\0'; return; } - snprintf(str->data, sizeof(BUILTIN_BUFFER), "%4.4d-%2.2d-%2.2dT%2.2d:%2.2d:%2.2dZ", - time_tm.tm_year + 1900, - time_tm.tm_mon + 1, - time_tm.tm_mday, - time_tm.tm_hour, - time_tm.tm_min, - time_tm.tm_sec); + /* yyyy-MM-ddTHH:mm:ssZ */ + uint_to_strdec(time_tm.tm_year + 1900, str->data, 4, 1); + str->data[4] = '-'; + uint_to_strdec(time_tm.tm_mon + 1, str->data + 5, 2, 1); + str->data[7] = '-'; + uint_to_strdec(time_tm.tm_mday, str->data + 8, 2, 1); + str->data[10] = 'T'; + uint_to_strdec(time_tm.tm_hour, str->data + 11, 2, 1); + str->data[13] = ':'; + uint_to_strdec(time_tm.tm_min, str->data + 14, 2, 1); + str->data[16] = ':'; + uint_to_strdec(time_tm.tm_sec, str->data + 17, 2, 1); + str->data[19] = 'Z'; + str->data[20] = '\0'; } void time_to_iso8601(time_t time, BUILTIN_BUFFER *str) @@ -402,13 +445,19 @@ void time_to_iso8601(time_t time, BUILTIN_BUFFER *str) str->data[0] = '\0'; return; } - snprintf(str->data, sizeof(BUILTIN_BUFFER), "%4.4d-%2.2d-%2.2dT%2.2d:%2.2d:%2.2d", - time_tm.tm_year + 1900, - time_tm.tm_mon + 1, - time_tm.tm_mday, - time_tm.tm_hour, - time_tm.tm_min, - time_tm.tm_sec); + /* yyyy-MM-ddTHH:mm:ss */ + uint_to_strdec(time_tm.tm_year + 1900, str->data, 4, 1); + str->data[4] = '-'; + uint_to_strdec(time_tm.tm_mon + 1, str->data + 5, 2, 1); + str->data[7] = '-'; + uint_to_strdec(time_tm.tm_mday, str->data + 8, 2, 1); + str->data[10] = 'T'; + uint_to_strdec(time_tm.tm_hour, str->data + 11, 2, 1); + str->data[13] = ':'; + uint_to_strdec(time_tm.tm_min, str->data + 14, 2, 1); + str->data[16] = ':'; + uint_to_strdec(time_tm.tm_sec, str->data + 17, 2, 1); + str->data[19] = '\0'; } void time_to_isodate(time_t time, BUILTIN_BUFFER *str) @@ -420,10 +469,12 @@ void time_to_isodate(time_t time, BUILTIN_BUFFER *str) str->data[0] = '\0'; return; } - snprintf(str->data, sizeof(BUILTIN_BUFFER), "%4.4d-%2.2d-%2.2d", - time_tm.tm_year + 1900, - time_tm.tm_mon + 1, - time_tm.tm_mday); + uint_to_strdec(time_tm.tm_year + 1900, str->data, 4, 1); + str->data[4] = '-'; + uint_to_strdec(time_tm.tm_mon + 1, str->data + 5, 2, 1); + str->data[7] = '-'; + uint_to_strdec(time_tm.tm_mday, str->data + 8, 2, 1); + str->data[10] = '\0'; } tz_t *time_tz(time_t time, tz_t* tz) { diff --git a/lib/cppmyth/src/private/builtin.h b/lib/cppmyth/src/private/builtin.h index 6286451b..846ded05 100644 --- a/lib/cppmyth/src/private/builtin.h +++ b/lib/cppmyth/src/private/builtin.h @@ -100,22 +100,28 @@ static CC_INLINE void int8_to_string(int8_t num, BUILTIN_BUFFER *str) snprintf(str->data, sizeof(BUILTIN_BUFFER), "%d", num); } +#define uint_to_strdec __uintstrdec +extern unsigned uint_to_strdec(unsigned u, char *str, unsigned len, int pad); + #define uint32_to_string __uint32str static CC_INLINE void uint32_to_string(uint32_t num, BUILTIN_BUFFER *str) { - snprintf(str->data, sizeof(BUILTIN_BUFFER), "%lu", (unsigned long)num); + unsigned len = uint_to_strdec(num, str->data, 10, 0); + str->data[len] = '\0'; } #define uint16_to_string __uint16str static CC_INLINE void uint16_to_string(uint16_t num, BUILTIN_BUFFER *str) { - snprintf(str->data, sizeof(BUILTIN_BUFFER), "%u", num); + unsigned len = uint_to_strdec(num, str->data, 5, 0); + str->data[len] = '\0'; } #define uint8_to_string __uint8str static CC_INLINE void uint8_to_string(uint8_t num, BUILTIN_BUFFER *str) { - snprintf(str->data, sizeof(BUILTIN_BUFFER), "%u", num); + unsigned len = uint_to_strdec(num, str->data, 3, 0); + str->data[len] = '\0'; } #define double_to_string __doublestr