Merge pull request #7385 from daverodgman/timing_alignment
Fix cast alignment warning in timing.c
diff --git a/ChangeLog.d/add-milliseconds-time-api.txt b/ChangeLog.d/add-milliseconds-time-api.txt
new file mode 100644
index 0000000..d9e939f
--- /dev/null
+++ b/ChangeLog.d/add-milliseconds-time-api.txt
@@ -0,0 +1,5 @@
+API changes
+ * Add new millisecond time type `mbedtls_ms_time_t` and `mbedtls_ms_time()`
+ function, needed for TLS 1.3 ticket lifetimes. Alternative implementations
+ can be created using an ALT interface.
+
diff --git a/include/mbedtls/check_config.h b/include/mbedtls/check_config.h
index ec0e23a..f5a1bcb 100644
--- a/include/mbedtls/check_config.h
+++ b/include/mbedtls/check_config.h
@@ -495,6 +495,16 @@
#error "MBEDTLS_PLATFORM_TIME_MACRO defined, but not all prerequisites"
#endif
+#if defined(MBEDTLS_PLATFORM_MS_TIME_TYPE_MACRO) &&\
+ ( !defined(MBEDTLS_PLATFORM_C) || !defined(MBEDTLS_HAVE_TIME) )
+#error "MBEDTLS_PLATFORM_MS_TIME_TYPE_MACRO defined, but not all prerequisites"
+#endif
+
+#if defined(MBEDTLS_PLATFORM_MS_TIME_ALT) && \
+ ( !defined(MBEDTLS_PLATFORM_C) || !defined(MBEDTLS_HAVE_TIME) )
+#error "MBEDTLS_PLATFORM_MS_TIME_ALT defined, but not all prerequisites"
+#endif
+
#if defined(MBEDTLS_PLATFORM_TIME_TYPE_MACRO) &&\
( !defined(MBEDTLS_PLATFORM_C) ||\
!defined(MBEDTLS_HAVE_TIME) )
diff --git a/include/mbedtls/debug.h b/include/mbedtls/debug.h
index 2b0d00e..74f5d55 100644
--- a/include/mbedtls/debug.h
+++ b/include/mbedtls/debug.h
@@ -131,6 +131,10 @@
#endif \
/* (defined(__MINGW32__) && __USE_MINGW_ANSI_STDIO == 0) || (defined(_MSC_VER) && _MSC_VER < 1800) */
+#if !defined(MBEDTLS_PRINTF_MS_TIME)
+#define MBEDTLS_PRINTF_MS_TIME PRId64
+#endif /* MBEDTLS_PRINTF_MS_TIME */
+
#ifdef __cplusplus
extern "C" {
#endif
diff --git a/include/mbedtls/mbedtls_config.h b/include/mbedtls/mbedtls_config.h
index 0ad6dcc..8923137 100644
--- a/include/mbedtls/mbedtls_config.h
+++ b/include/mbedtls/mbedtls_config.h
@@ -238,6 +238,7 @@
//#define MBEDTLS_PLATFORM_VSNPRINTF_ALT
//#define MBEDTLS_PLATFORM_NV_SEED_ALT
//#define MBEDTLS_PLATFORM_SETUP_TEARDOWN_ALT
+//#define MBEDTLS_PLATFORM_MS_TIME_ALT
/**
* \def MBEDTLS_DEPRECATED_WARNING
@@ -3675,6 +3676,8 @@
//#define MBEDTLS_PLATFORM_VSNPRINTF_MACRO vsnprintf /**< Default vsnprintf macro to use, can be undefined */
//#define MBEDTLS_PLATFORM_NV_SEED_READ_MACRO mbedtls_platform_std_nv_seed_read /**< Default nv_seed_read function to use, can be undefined */
//#define MBEDTLS_PLATFORM_NV_SEED_WRITE_MACRO mbedtls_platform_std_nv_seed_write /**< Default nv_seed_write function to use, can be undefined */
+//#define MBEDTLS_PLATFORM_MS_TIME_TYPE_MACRO int64_t //#define MBEDTLS_PLATFORM_MS_TIME_TYPE_MACRO int64_t /**< Default milliseconds time macro to use, can be undefined. MBEDTLS_HAVE_TIME must be enabled. It must be signed, and at least 64 bits. If it is changed from the default, MBEDTLS_PRINTF_MS_TIME must be updated to match.*/
+//#define MBEDTLS_PRINTF_MS_TIME PRId64 /**< Default fmt for printf. That's avoid compiler warning if mbedtls_ms_time_t is redefined */
/** \def MBEDTLS_CHECK_RETURN
*
diff --git a/include/mbedtls/platform_time.h b/include/mbedtls/platform_time.h
index eae6f5f..c7973d9 100644
--- a/include/mbedtls/platform_time.h
+++ b/include/mbedtls/platform_time.h
@@ -39,6 +39,29 @@
typedef time_t mbedtls_time_t;
#endif /* MBEDTLS_PLATFORM_TIME_TYPE_MACRO */
+#if defined(MBEDTLS_PLATFORM_MS_TIME_TYPE_MACRO)
+typedef MBEDTLS_PLATFORM_MS_TIME_TYPE_MACRO mbedtls_ms_time_t;
+#else
+#include <stdint.h>
+#include <inttypes.h>
+typedef int64_t mbedtls_ms_time_t;
+#endif /* MBEDTLS_PLATFORM_MS_TIME_TYPE_MACRO */
+
+/**
+ * \brief Get time in milliseconds.
+ *
+ * \return Monotonically-increasing current time in milliseconds.
+ *
+ * \note Define MBEDTLS_PLATFORM_MS_TIME_ALT to be able to provide an
+ * alternative implementation
+ *
+ * \warning This function returns a monotonically-increasing time value from a
+ * start time that will differ from platform to platform, and possibly
+ * from run to run of the process.
+ *
+ */
+mbedtls_ms_time_t mbedtls_ms_time(void);
+
/*
* The function pointers for time
*/
diff --git a/library/platform_util.c b/library/platform_util.c
index f891cd4..e903f8e 100644
--- a/library/platform_util.c
+++ b/library/platform_util.c
@@ -219,3 +219,45 @@
extern inline uint64_t mbedtls_get_unaligned_uint64(const void *p);
extern inline void mbedtls_put_unaligned_uint64(void *p, uint64_t x);
+
+#if defined(MBEDTLS_HAVE_TIME) && !defined(MBEDTLS_PLATFORM_MS_TIME_ALT)
+
+#include <time.h>
+#if !defined(_WIN32) && \
+ (defined(unix) || defined(__unix) || defined(__unix__) || \
+ (defined(__APPLE__) && defined(__MACH__)))
+#include <unistd.h>
+#endif /* !_WIN32 && (unix || __unix || __unix__ || (__APPLE__ && __MACH__)) */
+#if (defined(_POSIX_VERSION) && _POSIX_VERSION >= 199309L)
+mbedtls_ms_time_t mbedtls_ms_time(void)
+{
+ int ret;
+ struct timespec tv;
+ mbedtls_ms_time_t current_ms;
+
+ ret = clock_gettime(CLOCK_MONOTONIC, &tv);
+ if (ret) {
+ return time(NULL) * 1000;
+ }
+
+ current_ms = tv.tv_sec;
+
+ return current_ms*1000 + tv.tv_nsec / 1000000;
+}
+#elif defined(_WIN32) || defined(WIN32) || defined(__CYGWIN__) || \
+ defined(__MINGW32__) || defined(_WIN64)
+#include <windows.h>
+mbedtls_ms_time_t mbedtls_ms_time(void)
+{
+ FILETIME ct;
+ mbedtls_ms_time_t current_ms;
+
+ GetSystemTimeAsFileTime(&ct);
+ current_ms = ((mbedtls_ms_time_t) ct.dwLowDateTime +
+ ((mbedtls_ms_time_t) (ct.dwHighDateTime) << 32LL))/10000;
+ return current_ms;
+}
+#else
+#error "No mbedtls_ms_time available"
+#endif
+#endif /* MBEDTLS_HAVE_TIME && !MBEDTLS_PLATFORM_MS_TIME_ALT */
diff --git a/scripts/config.py b/scripts/config.py
index 404a5ef..ac5f77c 100755
--- a/scripts/config.py
+++ b/scripts/config.py
@@ -230,7 +230,7 @@
Exclude alternative implementations of library functions since they require
an implementation of the relevant functions and an xxx_alt.h header.
"""
- if name == 'MBEDTLS_PLATFORM_SETUP_TEARDOWN_ALT':
+ if name in ('MBEDTLS_PLATFORM_SETUP_TEARDOWN_ALT', 'MBEDTLS_PLATFORM_MS_TIME_ALT'):
# Similar to non-platform xxx_ALT, requires platform_alt.h
return False
return name.startswith('MBEDTLS_PLATFORM_')
diff --git a/tests/suites/test_suite_platform.data b/tests/suites/test_suite_platform.data
new file mode 100644
index 0000000..557b586
--- /dev/null
+++ b/tests/suites/test_suite_platform.data
@@ -0,0 +1,12 @@
+
+Time: get milliseconds
+time_get_milliseconds:
+
+Time: get seconds
+time_get_seconds:
+
+Time: delay milliseconds
+time_delay_milliseconds:1000
+
+Time: delay seconds
+time_delay_seconds:1
diff --git a/tests/suites/test_suite_platform.function b/tests/suites/test_suite_platform.function
new file mode 100644
index 0000000..54ddd42
--- /dev/null
+++ b/tests/suites/test_suite_platform.function
@@ -0,0 +1,91 @@
+/* BEGIN_HEADER */
+
+/* This test module exercises the platform_* module. Since, depending on the
+ * underlying operating system, the time routines are not always reliable,
+ * this suite only performs very basic sanity checks of the timing API.
+ */
+
+#include <limits.h>
+
+#if defined(MBEDTLS_HAVE_TIME)
+#include "mbedtls/platform_time.h"
+
+#ifdef WIN32
+#include <windows.h>
+#elif _POSIX_C_SOURCE >= 199309L
+#include <time.h>
+#else
+#include <unistd.h>
+#endif
+void sleep_ms(int milliseconds)
+{
+#ifdef WIN32
+ Sleep(milliseconds);
+#elif _POSIX_C_SOURCE >= 199309L
+ struct timespec ts;
+ ts.tv_sec = milliseconds / 1000;
+ ts.tv_nsec = (milliseconds % 1000) * 1000000;
+ nanosleep(&ts, NULL);
+#else
+ usleep(milliseconds * 1000);
+#endif
+}
+#endif
+
+/* END_HEADER */
+
+/* BEGIN_DEPENDENCIES */
+
+/* END_DEPENDENCIES */
+
+
+
+/* BEGIN_CASE depends_on:MBEDTLS_HAVE_TIME */
+void time_get_milliseconds()
+{
+ mbedtls_ms_time_t current = mbedtls_ms_time();
+ (void) current;
+ /* This goto is added to avoid warnings from the generated code. */
+ goto exit;
+}
+/* END_CASE */
+
+/* BEGIN_CASE depends_on:MBEDTLS_HAVE_TIME */
+void time_get_seconds()
+{
+ mbedtls_time_t current = mbedtls_time(NULL);
+ (void) current;
+ /* This goto is added to avoid warnings from the generated code. */
+ goto exit;
+}
+/* END_CASE */
+
+/* BEGIN_CASE depends_on:MBEDTLS_HAVE_TIME */
+void time_delay_milliseconds(int delay_ms)
+{
+ mbedtls_ms_time_t current = mbedtls_ms_time();
+ mbedtls_ms_time_t elapsed_ms;
+
+ sleep_ms(delay_ms);
+
+ elapsed_ms = mbedtls_ms_time() - current;
+ TEST_ASSERT(elapsed_ms >= delay_ms && elapsed_ms < 4000 + delay_ms);
+ /* This goto is added to avoid warnings from the generated code. */
+ goto exit;
+}
+/* END_CASE */
+
+/* BEGIN_CASE depends_on:MBEDTLS_HAVE_TIME */
+void time_delay_seconds(int delay_secs)
+{
+ mbedtls_time_t current = mbedtls_time(NULL);
+ mbedtls_time_t elapsed_secs;
+
+ sleep_ms(delay_secs * 1000);
+
+ elapsed_secs = mbedtls_time(NULL) - current;
+ TEST_ASSERT(elapsed_secs >= delay_secs && elapsed_secs < 4 + delay_secs);
+ /* This goto is added to avoid warnings from the generated code. */
+ goto exit;
+}
+/* END_CASE */