]> git.sur5r.net Git - freertos/blob - FreeRTOS/Demo/CORTEX_M0+_LPC51U68_LPCXpresso/GCC_specific/semihost_hardfault.c
7ce5fadb9544e45a87e2427dbf475ad992d5228d
[freertos] / FreeRTOS / Demo / CORTEX_M0+_LPC51U68_LPCXpresso / GCC_specific / semihost_hardfault.c
1 // ****************************************************************************\r
2 // semihost_hardfault.c\r
3 //                - Provides hard fault handler to allow semihosting code not\r
4 //                  to hang application when debugger not connected.\r
5 //\r
6 // ****************************************************************************\r
7 // Copyright 2017-2019 NXP\r
8 // All rights reserved.\r
9 //\r
10 // Software that is described herein is for illustrative purposes only\r
11 // which provides customers with programming information regarding the\r
12 // NXP Cortex-M based MCUs. This software is supplied "AS IS" without any\r
13 // warranties of any kind, and NXP Semiconductors and its licensor disclaim any\r
14 // and all warranties, express or implied, including all implied warranties of\r
15 // merchantability, fitness for a particular purpose and non-infringement of\r
16 // intellectual property rights.  NXP Semiconductors assumes no responsibility\r
17 // or liability for the use of the software, conveys no license or rights under\r
18 // any patent, copyright, mask work right, or any other intellectual property\r
19 // rights in or to any products. NXP Semiconductors reserves the right to make\r
20 // changes in the software without notification. NXP Semiconductors also makes\r
21 // no representation or warranty that such application will be suitable for the\r
22 // specified use without further testing or modification.\r
23 //\r
24 // Permission to use, copy, modify, and distribute this software and its\r
25 // documentation is hereby granted, under NXP Semiconductors' and its\r
26 // licensor's relevant copyrights in the software, without fee, provided that it\r
27 // is used in conjunction with NXP Semiconductors microcontrollers.  This\r
28 // copyright, permission, and disclaimer notice must appear in all copies of\r
29 // this code.\r
30 // ****************************************************************************\r
31 //\r
32 //                       ===== DESCRIPTION =====\r
33 //\r
34 // One of the issues with applications that make use of semihosting operations\r
35 // (such as printf calls) is that the code will not execute correctly when the\r
36 // debugger is not connected. Generally this will show up with the application\r
37 // appearing to just hang. This may include the application running from reset\r
38 // or powering up the board (with the application already in FLASH), and also\r
39 // as the application failing to continue to execute after a debug session is\r
40 // terminated.\r
41 //\r
42 // The problem here is that the "bottom layer" of the semihosted variants of\r
43 // the C library, semihosting is implemented by a "BKPT 0xAB" instruction.\r
44 // When the debug tools are not connected, this instruction triggers a hard\r
45 // fault - and the default hard fault handler within an application will\r
46 // typically just contains an infinite loop - causing the application to\r
47 // appear to have hang when no debugger is connected.\r
48 //\r
49 // The below code provides an example hard fault handler which instead looks\r
50 // to see what the instruction that caused the hard fault was - and if it\r
51 // was a "BKPT 0xAB", then it instead returns back to the user application.\r
52 //\r
53 // In most cases this will allow applications containing semihosting\r
54 // operations to execute (to some degree) when the debugger is not connected.\r
55 //\r
56 // == NOTE ==\r
57 //\r
58 // Correct execution of the application containing semihosted operations\r
59 // which are vectored onto this hard fault handler cannot be guaranteed. This\r
60 // is because the handler may not return data or return codes that the higher\r
61 // level C library code or application code expects. This hard fault handler\r
62 // is meant as a development aid, and it is not recommended to leave\r
63 // semihosted code in a production build of your application!\r
64 //\r
65 // ****************************************************************************\r
66 \r
67 // Allow handler to be removed by setting a define (via command line)\r
68 #if !defined (__SEMIHOST_HARDFAULT_DISABLE)\r
69 \r
70 __attribute__((naked))\r
71 void HardFault_Handler(void){\r
72     __asm(  ".syntax unified\n"\r
73         // Check which stack is in use\r
74             "MOVS   R0, #4  \n"\r
75             "MOV    R1, LR  \n"\r
76             "TST    R0, R1  \n"\r
77             "BEQ    _MSP    \n"\r
78             "MRS    R0, PSP \n"\r
79             "B  _process      \n"\r
80             "_MSP:  \n"\r
81             "MRS    R0, MSP \n"\r
82         // Load the instruction that triggered hard fault\r
83         "_process:     \n"\r
84             "LDR    R1,[R0,#24] \n"\r
85             "LDRH    R2,[r1] \n"\r
86         // Semihosting instruction is "BKPT 0xAB" (0xBEAB)\r
87             "LDR    R3,=0xBEAB \n"\r
88             "CMP     R2,R3 \n"\r
89             "BEQ    _semihost_return \n"\r
90         // Wasn't semihosting instruction so enter infinite loop\r
91             "B . \n"\r
92         // Was semihosting instruction, so adjust location to\r
93         // return to by 1 instruction (2 bytes), then exit function\r
94         "_semihost_return: \n"\r
95             "ADDS    R1,#2 \n"\r
96             "STR    R1,[R0,#24] \n"\r
97         // Set a return value from semihosting operation.\r
98         // 32 is slightly arbitrary, but appears to allow most\r
99         // C Library IO functions sitting on top of semihosting to\r
100         // continue to operate to some degree\r
101                     "MOVS   R1,#32 \n"\r
102                     "STR R1,[ R0,#0 ] \n" // R0 is at location 0 on stack\r
103         // Return from hard fault handler to application\r
104             "BX LR \n"\r
105         ".syntax divided\n") ;\r
106 }\r
107 \r
108 #endif\r
109 \r