]> begriffs open source - freertos/blob - portable/GCC/IA32_flat/portmacro.h
Style: uncrusitfy
[freertos] / portable / GCC / IA32_flat / portmacro.h
1 /*\r
2  * FreeRTOS Kernel V10.3.1\r
3  * Copyright (C) 2020 Amazon.com, Inc. or its affiliates.  All Rights Reserved.\r
4  *\r
5  * Permission is hereby granted, free of charge, to any person obtaining a copy of\r
6  * this software and associated documentation files (the "Software"), to deal in\r
7  * the Software without restriction, including without limitation the rights to\r
8  * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of\r
9  * the Software, and to permit persons to whom the Software is furnished to do so,\r
10  * subject to the following conditions:\r
11  *\r
12  * The above copyright notice and this permission notice shall be included in all\r
13  * copies or substantial portions of the Software.\r
14  *\r
15  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\r
16  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS\r
17  * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR\r
18  * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER\r
19  * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN\r
20  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\r
21  *\r
22  * http://www.FreeRTOS.org\r
23  * http://aws.amazon.com/freertos\r
24  *\r
25  */\r
26 \r
27 #ifndef PORTMACRO_H\r
28     #define PORTMACRO_H\r
29 \r
30     #ifdef __cplusplus\r
31         extern "C" {\r
32     #endif\r
33 \r
34 /*-----------------------------------------------------------\r
35  * Port specific definitions.\r
36  *\r
37  * The settings in this file configure FreeRTOS correctly for the given hardware\r
38  * and compiler.\r
39  *\r
40  * These settings should not be altered.\r
41  *-----------------------------------------------------------\r
42  */\r
43 \r
44 /* Type definitions. */\r
45     #define portCHAR          char\r
46     #define portFLOAT         float\r
47     #define portDOUBLE        double\r
48     #define portLONG          long\r
49     #define portSHORT         short\r
50     #define portSTACK_TYPE    uint32_t\r
51     #define portBASE_TYPE     long\r
52 \r
53     typedef portSTACK_TYPE   StackType_t;\r
54     typedef long             BaseType_t;\r
55     typedef unsigned long    UBaseType_t;\r
56 \r
57     typedef uint32_t         TickType_t;\r
58     #define portMAX_DELAY    ( ( TickType_t ) 0xffffffffUL )\r
59 \r
60 /*-----------------------------------------------------------*/\r
61 \r
62 /* Hardware specifics. */\r
63     #define portSTACK_GROWTH      ( -1 )\r
64     #define portTICK_PERIOD_MS    ( ( TickType_t ) 1000 / configTICK_RATE_HZ )\r
65     #define portBYTE_ALIGNMENT    32\r
66 \r
67 /*-----------------------------------------------------------*/\r
68 \r
69 /* Task utilities. */\r
70 \r
71 /* The interrupt priority (for vectors 16 to 255) is determined using vector/16.\r
72  * The quotient is rounded to the nearest integer with 1 being the lowest priority\r
73  * and 15 is the highest.  Therefore the following two interrupts are at the lowest\r
74  * priority.  *NOTE 1* If the yield vector is changed then it must also be changed\r
75  * in the portYIELD_INTERRUPT definition immediately below. */\r
76     #define portAPIC_TIMER_INT_VECTOR       ( 0x21 )\r
77     #define portAPIC_YIELD_INT_VECTOR       ( 0x20 )\r
78 \r
79 /* Build yield interrupt instruction. */\r
80     #define portYIELD_INTERRUPT             "int $0x20"\r
81 \r
82 /* APIC register addresses. */\r
83     #define portAPIC_EOI                    ( *( ( volatile uint32_t * ) 0xFEE000B0UL ) )\r
84 \r
85 /* APIC bit definitions. */\r
86     #define portAPIC_ENABLE_BIT             ( 1UL << 8UL )\r
87     #define portAPIC_TIMER_PERIODIC         ( 1UL << 17UL )\r
88     #define portAPIC_DISABLE                ( 1UL << 16UL )\r
89     #define portAPIC_NMI                    ( 4 << 8 )\r
90     #define portAPIC_DIV_16                 ( 0x03 )\r
91 \r
92 /* Define local API register addresses. */\r
93     #define portAPIC_ID_REGISTER            ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x20UL ) ) )\r
94     #define portAPIC_SPURIOUS_INT           ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0xF0UL ) ) )\r
95     #define portAPIC_LVT_TIMER              ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x320UL ) ) )\r
96     #define portAPIC_TIMER_INITIAL_COUNT    ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x380UL ) ) )\r
97     #define portAPIC_TIMER_CURRENT_COUNT    ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x390UL ) ) )\r
98     #define portAPIC_TASK_PRIORITY          ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x80UL ) ) )\r
99     #define portAPIC_LVT_ERROR              ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x370UL ) ) )\r
100     #define portAPIC_ERROR_STATUS           ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x280UL ) ) )\r
101     #define portAPIC_LDR                    ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0xD0UL ) ) )\r
102     #define portAPIC_TMRDIV                 ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x3E0UL ) ) )\r
103     #define portAPIC_LVT_PERF               ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x340UL ) ) )\r
104     #define portAPIC_LVT_LINT0              ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x350UL ) ) )\r
105     #define portAPIC_LVT_LINT1              ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0x360UL ) ) )\r
106 \r
107 /* Don't yield if inside a critical section - instead hold the yield pending\r
108  * so it is performed when the critical section is exited. */\r
109     #define portYIELD()                              \\r
110     {                                                \\r
111         extern volatile uint32_t ulCriticalNesting;  \\r
112         extern volatile uint32_t ulPortYieldPending; \\r
113         if( ulCriticalNesting != 0 )                 \\r
114         {                                            \\r
115             ulPortYieldPending = pdTRUE;             \\r
116         }                                            \\r
117         else                                         \\r
118         {                                            \\r
119             __asm volatile ( portYIELD_INTERRUPT );  \\r
120         }                                            \\r
121     }\r
122 \r
123 /* Called at the end of an ISR that can cause a context switch - pend a yield if\r
124  * xSwithcRequired is not false. */\r
125     #define portEND_SWITCHING_ISR( xSwitchRequired ) \\r
126     {                                                \\r
127         extern volatile uint32_t ulPortYieldPending; \\r
128         if( xSwitchRequired != pdFALSE )             \\r
129         {                                            \\r
130             ulPortYieldPending = 1;                  \\r
131         }                                            \\r
132     }\r
133 \r
134 /* Same as portEND_SWITCHING_ISR() - take your pick which name to use. */\r
135     #define portYIELD_FROM_ISR( x )    portEND_SWITCHING_ISR( x )\r
136 \r
137 /*-----------------------------------------------------------\r
138 * Critical section control\r
139 *----------------------------------------------------------*/\r
140 \r
141 /* Critical sections for use in interrupts. */\r
142     #define portSET_INTERRUPT_MASK_FROM_ISR()         ulPortSetInterruptMask()\r
143     #define portCLEAR_INTERRUPT_MASK_FROM_ISR( x )    vPortClearInterruptMask( x )\r
144 \r
145     extern void vPortEnterCritical( void );\r
146     extern void vPortExitCritical( void );\r
147     extern uint32_t ulPortSetInterruptMask( void );\r
148     extern void vPortClearInterruptMask( uint32_t ulNewMaskValue );\r
149 \r
150 /* These macros do not globally disable/enable interrupts.  They do mask off\r
151  * interrupts that have a priority below configMAX_API_CALL_INTERRUPT_PRIORITY. */\r
152     #define portENTER_CRITICAL()        vPortEnterCritical()\r
153     #define portEXIT_CRITICAL()         vPortExitCritical()\r
154     #define portDISABLE_INTERRUPTS()    __asm volatile ( "cli" )\r
155     #define portENABLE_INTERRUPTS()     __asm volatile ( "sti" )\r
156 \r
157 /*-----------------------------------------------------------*/\r
158 \r
159 /* Task function macros as described on the FreeRTOS.org WEB site.  These are\r
160  * not required for this port but included in case common demo code that uses these\r
161  * macros is used. */\r
162     #define portTASK_FUNCTION_PROTO( vFunction, pvParameters )    void vFunction( void * pvParameters )\r
163     #define portTASK_FUNCTION( vFunction, pvParameters )          void vFunction( void * pvParameters )\r
164 \r
165 /* Architecture specific optimisations. */\r
166     #if configUSE_PORT_OPTIMISED_TASK_SELECTION == 1\r
167 \r
168 /* Store/clear the ready priorities in a bit map. */\r
169         #define portGET_HIGHEST_PRIORITY( uxTopPriority, uxReadyPriorities ) \\r
170     __asm volatile ( "bsr %1, %0\n\t"                                        \\r
171                      : "=r" ( uxTopPriority ) : "rm" ( uxReadyPriorities ) : "cc" )\r
172 \r
173         #define portRECORD_READY_PRIORITY( uxPriority, uxReadyPriorities )    ( uxReadyPriorities ) |= ( 1UL << ( uxPriority ) )\r
174         #define portRESET_READY_PRIORITY( uxPriority, uxReadyPriorities )     ( uxReadyPriorities ) &= ~( 1UL << ( uxPriority ) )\r
175 \r
176     #endif /* configUSE_PORT_OPTIMISED_TASK_SELECTION */\r
177 \r
178     #define portNOP()    __asm volatile ( "NOP" )\r
179 \r
180 /*-----------------------------------------------------------\r
181 * Misc\r
182 *----------------------------------------------------------*/\r
183 \r
184     #define portNUM_VECTORS     256\r
185     #define portMAX_PRIORITY    15\r
186     typedef void ( * ISR_Handler_t ) ( void );\r
187 \r
188 /* Any task that uses the floating point unit MUST call vPortTaskUsesFPU()\r
189  * before any floating point instructions are executed. */\r
190     #ifndef configSUPPORT_FPU\r
191         #define configSUPPORT_FPU    0\r
192     #endif\r
193 \r
194     #if configSUPPORT_FPU == 1\r
195         void vPortTaskUsesFPU( void );\r
196         #define portTASK_USES_FLOATING_POINT()    vPortTaskUsesFPU()\r
197     #endif\r
198 \r
199 /* See the comments under the configUSE_COMMON_INTERRUPT_ENTRY_POINT definition\r
200  * below. */\r
201     BaseType_t xPortRegisterCInterruptHandler( ISR_Handler_t pxHandler,\r
202                                                uint32_t ulVectorNumber );\r
203     BaseType_t xPortInstallInterruptHandler( ISR_Handler_t pxHandler,\r
204                                              uint32_t ulVectorNumber );\r
205 \r
206     #ifndef configAPIC_BASE\r
207 \r
208 /* configAPIC_BASE_ADDRESS sets the base address of the local APIC.  It can\r
209  * be overridden in FreeRTOSConfig.h should it not be constant. */\r
210         #define configAPIC_BASE    0xFEE00000UL\r
211     #endif\r
212 \r
213     #ifndef configUSE_PORT_OPTIMISED_TASK_SELECTION\r
214 \r
215 /* The FreeRTOS scheduling algorithm selects the task that will enter the\r
216  * Running state.  configUSE_PORT_OPTIMISED_TASK_SELECTION is used to set how\r
217  * that is done.\r
218  *\r
219  * If configUSE_PORT_OPTIMISED_TASK_SELECTION is set to 0 then the task to\r
220  * enter the Running state is selected using a portable algorithm written in\r
221  * C.  This is the slowest method, but the algorithm does not restrict the\r
222  * maximum number of unique RTOS task priorities that are available.\r
223  *\r
224  * If configUSE_PORT_OPTIMISED_TASK_SELECTION is set to 1 then the task to\r
225  * enter the Running state is selected using a single assembly instruction.\r
226  * This is the fastest method, but restricts the maximum number of unique RTOS\r
227  * task priorities to 32 (the same task priority can be assigned to any number\r
228  * of RTOS      tasks). */\r
229         #warning configUSE_PORT_OPTIMISED_TASK_SELECTION was not defined in FreeRTOSConfig.h and has been defaulted to 1\r
230         #define configUSE_PORT_OPTIMISED_TASK_SELECTION    1\r
231     #endif\r
232 \r
233     #ifndef configUSE_COMMON_INTERRUPT_ENTRY_POINT\r
234 \r
235 /* There are two ways of implementing interrupt handlers:\r
236  *\r
237  *  1) As standard C functions -\r
238  *\r
239  *  This method can only be used if configUSE_COMMON_INTERRUPT_ENTRY_POINT\r
240  *  is set to 1.  The C function is installed using\r
241  *  xPortRegisterCInterruptHandler().\r
242  *\r
243  *  This is the simplest of the two methods but incurs a slightly longer\r
244  *  interrupt entry time.\r
245  *\r
246  *  2) By using an assembly stub that wraps the handler in the FreeRTOS\r
247  *     portFREERTOS_INTERRUPT_ENTRY and portFREERTOS_INTERRUPT_EXIT macros.\r
248  *\r
249  *  This method can always be used.  It is slightly more complex than\r
250  *  method 1 but benefits from a faster interrupt entry time. */\r
251         #warning configUSE_COMMON_INTERRUPT_ENTRY_POINT was not defined in FreeRTOSConfig.h and has been defaulted to 1.\r
252         #define configUSE_COMMON_INTERRUPT_ENTRY_POINT    1\r
253     #endif\r
254 \r
255     #ifndef configISR_STACK_SIZE\r
256 \r
257 /* Interrupt entry code will switch the stack in use to a dedicated system\r
258  * stack.\r
259  *\r
260  * configISR_STACK_SIZE defines the number of 32-bit values that can be stored\r
261  * on the system stack, and must be large enough to hold a potentially nested\r
262  * interrupt stack frame. */\r
263 \r
264         #error configISR_STACK_SIZE was not defined in FreeRTOSConfig.h.\r
265     #endif\r
266 \r
267     #ifndef configMAX_API_CALL_INTERRUPT_PRIORITY\r
268 \r
269 /* Interrupt safe FreeRTOS functions (those that end in "FromISR" must not\r
270  * be called from an interrupt that has a priority above that set by\r
271  * configMAX_API_CALL_INTERRUPT_PRIORITY.  */\r
272         #warning configMAX_API_CALL_INTERRUPT_PRIORITY was not defined in FreeRTOSConfig.h and has been defaulted to 10\r
273         #define configMAX_API_CALL_INTERRUPT_PRIORITY    10\r
274     #endif\r
275 \r
276     #ifndef configSUPPORT_FPU\r
277         #warning configSUPPORT_FPU was not defined in FreeRTOSConfig.h and has been defaulted to 0\r
278         #define configSUPPORT_FPU    0\r
279     #endif\r
280 \r
281 /* The value written to the task priority register to raise the interrupt mask\r
282  * to the maximum from which FreeRTOS API calls can be made. */\r
283     #define portAPIC_PRIORITY_SHIFT        ( 4UL )\r
284     #define portAPIC_MAX_SUB_PRIORITY      ( 0x0fUL )\r
285     #define portMAX_API_CALL_PRIORITY      ( ( configMAX_API_CALL_INTERRUPT_PRIORITY << portAPIC_PRIORITY_SHIFT ) | portAPIC_MAX_SUB_PRIORITY )\r
286 \r
287 /* Asserts if interrupt safe FreeRTOS functions are called from a priority\r
288  * above the max system call interrupt priority. */\r
289     #define portAPIC_PROCESSOR_PRIORITY    ( *( ( volatile uint32_t * ) ( configAPIC_BASE + 0xA0UL ) ) )\r
290     #define portASSERT_IF_INTERRUPT_PRIORITY_INVALID()    configASSERT( ( portAPIC_PROCESSOR_PRIORITY ) <= ( portMAX_API_CALL_PRIORITY ) )\r
291 \r
292     #ifdef __cplusplus\r
293         } /* extern C */\r
294     #endif\r
295 \r
296 #endif /* PORTMACRO_H */\r