1a8e1175bSopenharmony_ci/** 2a8e1175bSopenharmony_ci * \file memory.h 3a8e1175bSopenharmony_ci * 4a8e1175bSopenharmony_ci * \brief Helper macros and functions related to testing memory management. 5a8e1175bSopenharmony_ci */ 6a8e1175bSopenharmony_ci 7a8e1175bSopenharmony_ci/* 8a8e1175bSopenharmony_ci * Copyright The Mbed TLS Contributors 9a8e1175bSopenharmony_ci * SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later 10a8e1175bSopenharmony_ci */ 11a8e1175bSopenharmony_ci 12a8e1175bSopenharmony_ci#ifndef TEST_MEMORY_H 13a8e1175bSopenharmony_ci#define TEST_MEMORY_H 14a8e1175bSopenharmony_ci 15a8e1175bSopenharmony_ci#include "mbedtls/build_info.h" 16a8e1175bSopenharmony_ci#include "mbedtls/platform.h" 17a8e1175bSopenharmony_ci#include "test/helpers.h" 18a8e1175bSopenharmony_ci 19a8e1175bSopenharmony_ci/** \def MBEDTLS_TEST_MEMORY_CAN_POISON 20a8e1175bSopenharmony_ci * 21a8e1175bSopenharmony_ci * This macro is defined if the tests are compiled with a method to mark 22a8e1175bSopenharmony_ci * memory as poisoned, which can be used to enforce some memory access 23a8e1175bSopenharmony_ci * policies. 24a8e1175bSopenharmony_ci * 25a8e1175bSopenharmony_ci * Support for the C11 thread_local keyword is also required. 26a8e1175bSopenharmony_ci * 27a8e1175bSopenharmony_ci * Currently, only Asan (Address Sanitizer) is supported. 28a8e1175bSopenharmony_ci */ 29a8e1175bSopenharmony_ci#if defined(MBEDTLS_TEST_HAVE_ASAN) && \ 30a8e1175bSopenharmony_ci (__STDC_VERSION__ >= 201112L) && \ 31a8e1175bSopenharmony_ci !defined(PSA_CRYPTO_DRIVER_TEST) 32a8e1175bSopenharmony_ci# define MBEDTLS_TEST_MEMORY_CAN_POISON 33a8e1175bSopenharmony_ci#endif 34a8e1175bSopenharmony_ci 35a8e1175bSopenharmony_ci/** \def MBEDTLS_TEST_MEMORY_POISON(buf, size) 36a8e1175bSopenharmony_ci * 37a8e1175bSopenharmony_ci * Poison a memory area so that any attempt to read or write from it will 38a8e1175bSopenharmony_ci * cause a runtime failure. 39a8e1175bSopenharmony_ci * 40a8e1175bSopenharmony_ci * Depending on the implementation, this may poison a few bytes beyond the 41a8e1175bSopenharmony_ci * indicated region, but will never poison a separate object on the heap 42a8e1175bSopenharmony_ci * or a separate object with more than the alignment of a long long. 43a8e1175bSopenharmony_ci * 44a8e1175bSopenharmony_ci * The behavior is undefined if any part of the memory area is invalid. 45a8e1175bSopenharmony_ci * 46a8e1175bSopenharmony_ci * This is a no-op in builds without a poisoning method. 47a8e1175bSopenharmony_ci * See #MBEDTLS_TEST_MEMORY_CAN_POISON. 48a8e1175bSopenharmony_ci * 49a8e1175bSopenharmony_ci * \param buf Pointer to the beginning of the memory area to poison. 50a8e1175bSopenharmony_ci * \param size Size of the memory area in bytes. 51a8e1175bSopenharmony_ci */ 52a8e1175bSopenharmony_ci 53a8e1175bSopenharmony_ci/** \def MBEDTLS_TEST_MEMORY_UNPOISON(buf, size) 54a8e1175bSopenharmony_ci * 55a8e1175bSopenharmony_ci * Undo the effect of #MBEDTLS_TEST_MEMORY_POISON. 56a8e1175bSopenharmony_ci * 57a8e1175bSopenharmony_ci * The behavior is undefined if any part of the memory area is invalid, 58a8e1175bSopenharmony_ci * or if the memory area contains a mixture of poisoned and unpoisoned parts. 59a8e1175bSopenharmony_ci * 60a8e1175bSopenharmony_ci * This is a no-op in builds without a poisoning method. 61a8e1175bSopenharmony_ci * See #MBEDTLS_TEST_MEMORY_CAN_POISON. 62a8e1175bSopenharmony_ci * 63a8e1175bSopenharmony_ci * \param buf Pointer to the beginning of the memory area to unpoison. 64a8e1175bSopenharmony_ci * \param size Size of the memory area in bytes. 65a8e1175bSopenharmony_ci */ 66a8e1175bSopenharmony_ci 67a8e1175bSopenharmony_ci#if defined(MBEDTLS_TEST_MEMORY_CAN_POISON) 68a8e1175bSopenharmony_ci 69a8e1175bSopenharmony_ci/** Thread-local variable used to enable memory poisoning. This is set and 70a8e1175bSopenharmony_ci * unset in the test wrappers so that calls to PSA functions from the library 71a8e1175bSopenharmony_ci * do not poison memory. 72a8e1175bSopenharmony_ci */ 73a8e1175bSopenharmony_ciextern _Thread_local unsigned int mbedtls_test_memory_poisoning_count; 74a8e1175bSopenharmony_ci 75a8e1175bSopenharmony_ci/** Poison a memory area so that any attempt to read or write from it will 76a8e1175bSopenharmony_ci * cause a runtime failure. 77a8e1175bSopenharmony_ci * 78a8e1175bSopenharmony_ci * The behavior is undefined if any part of the memory area is invalid. 79a8e1175bSopenharmony_ci */ 80a8e1175bSopenharmony_civoid mbedtls_test_memory_poison(const unsigned char *ptr, size_t size); 81a8e1175bSopenharmony_ci#define MBEDTLS_TEST_MEMORY_POISON(ptr, size) \ 82a8e1175bSopenharmony_ci do { \ 83a8e1175bSopenharmony_ci mbedtls_test_memory_poisoning_count++; \ 84a8e1175bSopenharmony_ci mbedtls_test_memory_poison(ptr, size); \ 85a8e1175bSopenharmony_ci } while (0) 86a8e1175bSopenharmony_ci 87a8e1175bSopenharmony_ci/** Undo the effect of mbedtls_test_memory_poison(). 88a8e1175bSopenharmony_ci * 89a8e1175bSopenharmony_ci * This is a no-op if the given area is entirely valid, unpoisoned memory. 90a8e1175bSopenharmony_ci * 91a8e1175bSopenharmony_ci * The behavior is undefined if any part of the memory area is invalid, 92a8e1175bSopenharmony_ci * or if the memory area contains a mixture of poisoned and unpoisoned parts. 93a8e1175bSopenharmony_ci */ 94a8e1175bSopenharmony_civoid mbedtls_test_memory_unpoison(const unsigned char *ptr, size_t size); 95a8e1175bSopenharmony_ci#define MBEDTLS_TEST_MEMORY_UNPOISON(ptr, size) \ 96a8e1175bSopenharmony_ci do { \ 97a8e1175bSopenharmony_ci mbedtls_test_memory_unpoison(ptr, size); \ 98a8e1175bSopenharmony_ci if (mbedtls_test_memory_poisoning_count != 0) { \ 99a8e1175bSopenharmony_ci mbedtls_test_memory_poisoning_count--; \ 100a8e1175bSopenharmony_ci } \ 101a8e1175bSopenharmony_ci } while (0) 102a8e1175bSopenharmony_ci 103a8e1175bSopenharmony_ci#else /* MBEDTLS_TEST_MEMORY_CAN_POISON */ 104a8e1175bSopenharmony_ci#define MBEDTLS_TEST_MEMORY_POISON(ptr, size) ((void) (ptr), (void) (size)) 105a8e1175bSopenharmony_ci#define MBEDTLS_TEST_MEMORY_UNPOISON(ptr, size) ((void) (ptr), (void) (size)) 106a8e1175bSopenharmony_ci#endif /* MBEDTLS_TEST_MEMORY_CAN_POISON */ 107a8e1175bSopenharmony_ci 108a8e1175bSopenharmony_ci#endif /* TEST_MEMORY_H */ 109