summaryrefslogtreecommitdiff
path: root/tests/include/test/memory.h
diff options
context:
space:
mode:
Diffstat (limited to 'tests/include/test/memory.h')
-rw-r--r--tests/include/test/memory.h108
1 files changed, 108 insertions, 0 deletions
diff --git a/tests/include/test/memory.h b/tests/include/test/memory.h
new file mode 100644
index 00000000000..940d9e6baa0
--- /dev/null
+++ b/tests/include/test/memory.h
@@ -0,0 +1,108 @@
+/**
+ * \file memory.h
+ *
+ * \brief Helper macros and functions related to testing memory management.
+ */
+
+/*
+ * Copyright The Mbed TLS Contributors
+ * SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
+ */
+
+#ifndef TEST_MEMORY_H
+#define TEST_MEMORY_H
+
+#include "mbedtls/build_info.h"
+#include "mbedtls/platform.h"
+#include "test/helpers.h"
+
+/** \def MBEDTLS_TEST_MEMORY_CAN_POISON
+ *
+ * This macro is defined if the tests are compiled with a method to mark
+ * memory as poisoned, which can be used to enforce some memory access
+ * policies.
+ *
+ * Support for the C11 thread_local keyword is also required.
+ *
+ * Currently, only Asan (Address Sanitizer) is supported.
+ */
+#if defined(MBEDTLS_TEST_HAVE_ASAN) && \
+ (__STDC_VERSION__ >= 201112L) && \
+ !defined(PSA_CRYPTO_DRIVER_TEST)
+# define MBEDTLS_TEST_MEMORY_CAN_POISON
+#endif
+
+/** \def MBEDTLS_TEST_MEMORY_POISON(buf, size)
+ *
+ * Poison a memory area so that any attempt to read or write from it will
+ * cause a runtime failure.
+ *
+ * Depending on the implementation, this may poison a few bytes beyond the
+ * indicated region, but will never poison a separate object on the heap
+ * or a separate object with more than the alignment of a long long.
+ *
+ * The behavior is undefined if any part of the memory area is invalid.
+ *
+ * This is a no-op in builds without a poisoning method.
+ * See #MBEDTLS_TEST_MEMORY_CAN_POISON.
+ *
+ * \param buf Pointer to the beginning of the memory area to poison.
+ * \param size Size of the memory area in bytes.
+ */
+
+/** \def MBEDTLS_TEST_MEMORY_UNPOISON(buf, size)
+ *
+ * Undo the effect of #MBEDTLS_TEST_MEMORY_POISON.
+ *
+ * The behavior is undefined if any part of the memory area is invalid,
+ * or if the memory area contains a mixture of poisoned and unpoisoned parts.
+ *
+ * This is a no-op in builds without a poisoning method.
+ * See #MBEDTLS_TEST_MEMORY_CAN_POISON.
+ *
+ * \param buf Pointer to the beginning of the memory area to unpoison.
+ * \param size Size of the memory area in bytes.
+ */
+
+#if defined(MBEDTLS_TEST_MEMORY_CAN_POISON)
+
+/** Thread-local variable used to enable memory poisoning. This is set and
+ * unset in the test wrappers so that calls to PSA functions from the library
+ * do not poison memory.
+ */
+extern _Thread_local unsigned int mbedtls_test_memory_poisoning_count;
+
+/** Poison a memory area so that any attempt to read or write from it will
+ * cause a runtime failure.
+ *
+ * The behavior is undefined if any part of the memory area is invalid.
+ */
+void mbedtls_test_memory_poison(const unsigned char *ptr, size_t size);
+#define MBEDTLS_TEST_MEMORY_POISON(ptr, size) \
+ do { \
+ mbedtls_test_memory_poisoning_count++; \
+ mbedtls_test_memory_poison(ptr, size); \
+ } while (0)
+
+/** Undo the effect of mbedtls_test_memory_poison().
+ *
+ * This is a no-op if the given area is entirely valid, unpoisoned memory.
+ *
+ * The behavior is undefined if any part of the memory area is invalid,
+ * or if the memory area contains a mixture of poisoned and unpoisoned parts.
+ */
+void mbedtls_test_memory_unpoison(const unsigned char *ptr, size_t size);
+#define MBEDTLS_TEST_MEMORY_UNPOISON(ptr, size) \
+ do { \
+ mbedtls_test_memory_unpoison(ptr, size); \
+ if (mbedtls_test_memory_poisoning_count != 0) { \
+ mbedtls_test_memory_poisoning_count--; \
+ } \
+ } while (0)
+
+#else /* MBEDTLS_TEST_MEMORY_CAN_POISON */
+#define MBEDTLS_TEST_MEMORY_POISON(ptr, size) ((void) (ptr), (void) (size))
+#define MBEDTLS_TEST_MEMORY_UNPOISON(ptr, size) ((void) (ptr), (void) (size))
+#endif /* MBEDTLS_TEST_MEMORY_CAN_POISON */
+
+#endif /* TEST_MEMORY_H */