1 /* 2 * Copyright 2018 The Hafnium Authors. 3 * 4 * Use of this source code is governed by a BSD-style 5 * license that can be found in the LICENSE file or at 6 * https://opensource.org/licenses/BSD-3-Clause. 7 */ 8 9 #pragma once 10 11 #include <stdbool.h> 12 #include <stddef.h> 13 #include <stdint.h> 14 #include <stdnoreturn.h> 15 16 #include "hf/dlog.h" 17 #include "hf/fdt.h" 18 #include "hf/memiter.h" 19 20 /* 21 * Define a set up function to be run before every test in a test suite. 22 */ 23 #define SET_UP(suite) HFTEST_SET_UP(suite) 24 25 /* 26 * Define a tear down function to be run after every test in a test suite. 27 */ 28 #define TEAR_DOWN(suite) HFTEST_TEAR_DOWN(suite) 29 30 /* 31 * Define a test as part of a test suite. 32 */ 33 #define TEST(suite, test) HFTEST_TEST(suite, test, false) 34 35 /* 36 * Define a test as part of a test suite and mark it long-running. 37 */ 38 #define TEST_LONG_RUNNING(suite, test) HFTEST_TEST(suite, test, true) 39 40 /* 41 * Define a test service. 42 */ 43 #define TEST_SERVICE(service) HFTEST_TEST_SERVICE(service) 44 45 /* Assertions. */ 46 #define ASSERT_EQ(x, y) HFTEST_ASSERT_OP(x, y, ==, true) 47 #define ASSERT_NE(x, y) HFTEST_ASSERT_OP(x, y, !=, true) 48 #define ASSERT_LE(x, y) HFTEST_ASSERT_OP(x, y, <=, true) 49 #define ASSERT_LT(x, y) HFTEST_ASSERT_OP(x, y, <, true) 50 #define ASSERT_GE(x, y) HFTEST_ASSERT_OP(x, y, >=, true) 51 #define ASSERT_GT(x, y) HFTEST_ASSERT_OP(x, y, >, true) 52 53 #define ASSERT_TRUE(x) ASSERT_EQ(x, true) 54 #define ASSERT_FALSE(x) ASSERT_EQ(x, false) 55 56 #define EXPECT_EQ(x, y) HFTEST_ASSERT_OP(x, y, ==, false) 57 #define EXPECT_NE(x, y) HFTEST_ASSERT_OP(x, y, !=, false) 58 #define EXPECT_LE(x, y) HFTEST_ASSERT_OP(x, y, <=, false) 59 #define EXPECT_LT(x, y) HFTEST_ASSERT_OP(x, y, <, false) 60 #define EXPECT_GE(x, y) HFTEST_ASSERT_OP(x, y, >=, false) 61 #define EXPECT_GT(x, y) HFTEST_ASSERT_OP(x, y, >, false) 62 63 #define EXPECT_TRUE(x) EXPECT_EQ(x, true) 64 #define EXPECT_FALSE(x) EXPECT_EQ(x, false) 65 66 #define FAIL(...) HFTEST_FAIL(true, __VA_ARGS__) 67 68 /* Service utilities. */ 69 #define SERVICE_NAME_MAX_LENGTH 64 70 #define SERVICE_SELECT(vm_id, service, send_buffer) \ 71 HFTEST_SERVICE_SELECT(vm_id, service, send_buffer) 72 73 #define SERVICE_SEND_BUFFER() HFTEST_SERVICE_SEND_BUFFER() 74 #define SERVICE_RECV_BUFFER() HFTEST_SERVICE_RECV_BUFFER() 75 #define SERVICE_MEMORY_SIZE() HFTEST_SERVICE_MEMORY_SIZE() 76 77 /* 78 * This must be used exactly once in a test image to signal to the linker that 79 * the .hftest section is allowed to be included in the generated image. 80 */ 81 #define HFTEST_ENABLE() __attribute__((used)) int hftest_enable 82 83 /* 84 * Prefixed to log lines from tests for easy filtering in the console. 85 */ 86 #define HFTEST_LOG_PREFIX "[hftest] " 87 88 /* 89 * Indentation used e.g. to give the reason for an assertion failure. 90 */ 91 #define HFTEST_LOG_INDENT " " 92 93 /** Initializes stage-1 MMU for tests running in a VM. */ 94 bool hftest_mm_init(void); 95 96 /** Adds stage-1 identity mapping for pages covering bytes [base, base+size). */ 97 void hftest_mm_identity_map(const void *base, size_t size, uint32_t mode); 98 99 void hftest_mm_vcpu_init(void); 100 101 /** 102 * Returns a pointer to stage-1 mappings. 103 * Note: There is no locking as all existing users are on the same vCPU. 104 */ 105 struct mm_stage1_locked hftest_mm_get_stage1(void); 106 107 /** Returns a pointer to the page-table pool. */ 108 struct mpool *hftest_mm_get_ppool(void); 109 110 /** 111 * Inform a host that this is the start of a test run and obtain the command 112 * line arguments for it. 113 */ 114 bool hftest_ctrl_start(const struct fdt *fdt, struct memiter *cmd); 115 116 /** Inform a host that this test run has finished and clean up. */ 117 void hftest_ctrl_finish(void); 118 void hftest_ctrl_reboot(void); 119 120 /** Parses and run test command */ 121 void hftest_command(struct fdt *fdt); 122 123 /** Reboot the device. */ 124 noreturn void hftest_device_reboot(void); 125 126 /** 127 * Device-specific operation to escape from the test environment. 128 * For example, an Android device with UART test controller will reboot after 129 * every test run back into hftest. So as to flash the device with a different 130 * system image, the device must escape this loop and boot into the Android 131 * bootloader. 132 * If successful, this function will not return. 133 * It may not be supported on all devices. 134 */ 135 void hftest_device_exit_test_environment(void); 136 137 /** 138 * Starts the CPU with the given ID. It will start at the provided entry point 139 * with the provided argument. It is a wrapper around the generic cpu_start() 140 * and takes care of MMU initialization. 141 */ 142 bool hftest_cpu_start(uintptr_t id, void *stack, size_t stack_size, 143 void (*entry)(uintptr_t arg), uintptr_t arg); 144 145 uintptr_t hftest_get_cpu_id(size_t index); 146 147 noreturn void hftest_service_main(const void *fdt_ptr); 148 /* Above this point is the public API. Now include the implementation. */ 149 #include "hftest_impl.h" 150