1 /*
2  * Copyright (c) 2012-2014 Wind River Systems, Inc.
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 #include <zephyr/kernel.h>
8 #include <zephyr/sys/printk.h>
9 #include <zephyr/debug/coredump.h>
10 
11 #ifdef CONFIG_COVERAGE_DUMP
12 #include <zephyr/debug/gcov.h>
13 #endif
14 
15 
k_sys_fatal_error_handler(unsigned int reason,const struct arch_esf * pEsf)16 void k_sys_fatal_error_handler(unsigned int reason, const struct arch_esf *pEsf)
17 {
18 	ARG_UNUSED(pEsf);
19 
20 	printk("%s is expected; reason = %u; halting ...\n", __func__, reason);
21 
22 #ifdef CONFIG_COVERAGE_DUMP
23 	gcov_coverage_dump();  /* LCOV_EXCL_LINE */
24 #endif
25 	k_fatal_halt(reason);
26 }
27 
28 /* Turn off optimizations to prevent the compiler from optimizing this away
29  * due to the null pointer dereference.
30  */
func_3(uint32_t * addr)31 __no_optimization void func_3(uint32_t *addr)
32 {
33 #if defined(CONFIG_BOARD_M2GL025_MIV) || \
34 	defined(CONFIG_BOARD_HIFIVE1) || \
35 	defined(CONFIG_BOARD_HIFIVE_UNLEASHED) || \
36 	defined(CONFIG_BOARD_HIFIVE_UNMATCHED) || \
37 	defined(CONFIG_BOARD_LONGAN_NANO) || \
38 	defined(CONFIG_BOARD_QEMU_XTENSA) || \
39 	defined(CONFIG_BOARD_RISCV32_VIRTUAL) || \
40 	defined(CONFIG_SOC_FAMILY_INTEL_ADSP)
41 	ARG_UNUSED(addr);
42 	/* Call k_panic() directly so Renode doesn't pause execution.
43 	 * Needed on ADSP as well, since null pointer derefence doesn't
44 	 * fault as the lowest memory region is writable. SOF uses k_panic
45 	 * a lot, so it's good to check that it causes a coredump.
46 	 */
47 	k_panic();
48 #elif !defined(CONFIG_CPU_CORTEX_M)
49 	/* For null pointer reference */
50 	*addr = 0;
51 #else
52 	ARG_UNUSED(addr);
53 	/* Dereferencing null-pointer in TrustZone-enabled
54 	 * builds may crash the system, so use, instead an
55 	 * undefined instruction to trigger a CPU fault.
56 	 */
57 	__asm__ volatile("udf #0" : : : );
58 #endif
59 }
60 
func_2(uint32_t * addr)61 void func_2(uint32_t *addr)
62 {
63 	func_3(addr);
64 }
65 
func_1(uint32_t * addr)66 void func_1(uint32_t *addr)
67 {
68 	func_2(addr);
69 }
70 
main(void)71 int main(void)
72 {
73 	printk("Coredump: %s\n", CONFIG_BOARD);
74 
75 	func_1(0);
76 	return 0;
77 }
78