OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [rtos/] [freertos-6.1.1/] [Source/] [portable/] [GCC/] [ARM_CM3_MPU/] [port.c] - Blame information for rev 572

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 572 jeremybenn
/*
2
    FreeRTOS V6.1.1 - Copyright (C) 2011 Real Time Engineers Ltd.
3
 
4
    ***************************************************************************
5
    *                                                                         *
6
    * If you are:                                                             *
7
    *                                                                         *
8
    *    + New to FreeRTOS,                                                   *
9
    *    + Wanting to learn FreeRTOS or multitasking in general quickly       *
10
    *    + Looking for basic training,                                        *
11
    *    + Wanting to improve your FreeRTOS skills and productivity           *
12
    *                                                                         *
13
    * then take a look at the FreeRTOS books - available as PDF or paperback  *
14
    *                                                                         *
15
    *        "Using the FreeRTOS Real Time Kernel - a Practical Guide"        *
16
    *                  http://www.FreeRTOS.org/Documentation                  *
17
    *                                                                         *
18
    * A pdf reference manual is also available.  Both are usually delivered   *
19
    * to your inbox within 20 minutes to two hours when purchased between 8am *
20
    * and 8pm GMT (although please allow up to 24 hours in case of            *
21
    * exceptional circumstances).  Thank you for your support!                *
22
    *                                                                         *
23
    ***************************************************************************
24
 
25
    This file is part of the FreeRTOS distribution.
26
 
27
    FreeRTOS is free software; you can redistribute it and/or modify it under
28
    the terms of the GNU General Public License (version 2) as published by the
29
    Free Software Foundation AND MODIFIED BY the FreeRTOS exception.
30
    ***NOTE*** The exception to the GPL is included to allow you to distribute
31
    a combined work that includes FreeRTOS without being obliged to provide the
32
    source code for proprietary components outside of the FreeRTOS kernel.
33
    FreeRTOS is distributed in the hope that it will be useful, but WITHOUT
34
    ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
35
    FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
36
    more details. You should have received a copy of the GNU General Public
37
    License and the FreeRTOS license exception along with FreeRTOS; if not it
38
    can be viewed here: http://www.freertos.org/a00114.html and also obtained
39
    by writing to Richard Barry, contact details for whom are available on the
40
    FreeRTOS WEB site.
41
 
42
    1 tab == 4 spaces!
43
 
44
    http://www.FreeRTOS.org - Documentation, latest information, license and
45
    contact details.
46
 
47
    http://www.SafeRTOS.com - A version that is certified for use in safety
48
    critical systems.
49
 
50
    http://www.OpenRTOS.com - Commercial support, development, porting,
51
    licensing and training services.
52
*/
53
 
54
/*-----------------------------------------------------------
55
 * Implementation of functions defined in portable.h for the ARM CM3 port.
56
 *----------------------------------------------------------*/
57
 
58
/* Defining MPU_WRAPPERS_INCLUDED_FROM_API_FILE prevents task.h from redefining
59
all the API functions to use the MPU wrappers.  That should only be done when
60
task.h is included from an application file. */
61
#define MPU_WRAPPERS_INCLUDED_FROM_API_FILE
62
 
63
/* Scheduler includes. */
64
#include "FreeRTOS.h"
65
#include "task.h"
66
#include "queue.h"
67
 
68
#undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE
69
 
70
/* Constants required to access and manipulate the NVIC. */
71
#define portNVIC_SYSTICK_CTRL                                   ( ( volatile unsigned long * ) 0xe000e010 )
72
#define portNVIC_SYSTICK_LOAD                                   ( ( volatile unsigned long * ) 0xe000e014 )
73
#define portNVIC_SYSPRI2                                                ( ( volatile unsigned long * ) 0xe000ed20 )
74
#define portNVIC_SYSPRI1                                                ( ( volatile unsigned long * ) 0xe000ed1c )
75
#define portNVIC_SYS_CTRL_STATE                                 ( ( volatile unsigned long * ) 0xe000ed24 )
76
#define portNVIC_MEM_FAULT_ENABLE                               ( 1UL << 16UL )
77
 
78
/* Constants required to access and manipulate the MPU. */
79
#define portMPU_TYPE                                                    ( ( volatile unsigned long * ) 0xe000ed90 )
80
#define portMPU_REGION_BASE_ADDRESS                             ( ( volatile unsigned long * ) 0xe000ed9C )
81
#define portMPU_REGION_ATTRIBUTE                                ( ( volatile unsigned long * ) 0xe000edA0 )
82
#define portMPU_CTRL                                                    ( ( volatile unsigned long * ) 0xe000ed94 )
83
#define portEXPECTED_MPU_TYPE_VALUE                             ( 8UL << 8UL ) /* 8 regions, unified. */
84
#define portMPU_ENABLE                                                  ( 0x01UL )
85
#define portMPU_BACKGROUND_ENABLE                               ( 1UL << 2UL )
86
#define portPRIVILEGED_EXECUTION_START_ADDRESS  ( 0UL )
87
#define portMPU_REGION_VALID                                    ( 0x10UL )
88
#define portMPU_REGION_ENABLE                                   ( 0x01UL )
89
#define portPERIPHERALS_START_ADDRESS                   0x40000000UL
90
#define portPERIPHERALS_END_ADDRESS                             0x5FFFFFFFUL
91
 
92
/* Constants required to access and manipulate the SysTick. */
93
#define portNVIC_SYSTICK_CLK                                    ( 0x00000004UL )
94
#define portNVIC_SYSTICK_INT                                    ( 0x00000002UL )
95
#define portNVIC_SYSTICK_ENABLE                                 ( 0x00000001UL )
96
#define portNVIC_PENDSV_PRI                                             ( ( ( unsigned long ) configKERNEL_INTERRUPT_PRIORITY ) << 16UL )
97
#define portNVIC_SYSTICK_PRI                                    ( ( ( unsigned long ) configKERNEL_INTERRUPT_PRIORITY ) << 24UL )
98
#define portNVIC_SVC_PRI                                                ( ( ( unsigned long ) configKERNEL_INTERRUPT_PRIORITY ) << 24UL )
99
 
100
/* Constants required to set up the initial stack. */
101
#define portINITIAL_XPSR                                                ( 0x01000000 )
102
#define portINITIAL_CONTROL_IF_UNPRIVILEGED             ( 0x03 )
103
#define portINITIAL_CONTROL_IF_PRIVILEGED               ( 0x02 )
104
 
105
/* Offsets in the stack to the parameters when inside the SVC handler. */
106
#define portOFFSET_TO_PC                                                ( 6 )
107
 
108
/* Set the privilege level to user mode if xRunningPrivileged is false. */
109
#define portRESET_PRIVILEGE( xRunningPrivileged ) if( xRunningPrivileged != pdTRUE ) __asm volatile ( " mrs r0, control \n orr r0, #1 \n msr control, r0" :::"r0" )
110
 
111
/* Each task maintains its own interrupt status in the critical nesting
112
variable.  Note this is not saved as part of the task context as context
113
switches can only occur when uxCriticalNesting is zero. */
114
static unsigned portBASE_TYPE uxCriticalNesting = 0xaaaaaaaa;
115
 
116
/*
117
 * Setup the timer to generate the tick interrupts.
118
 */
119
static void prvSetupTimerInterrupt( void ) PRIVILEGED_FUNCTION;
120
 
121
/*
122
 * Configure a number of standard MPU regions that are used by all tasks.
123
 */
124
static void prvSetupMPU( void ) PRIVILEGED_FUNCTION;
125
 
126
/*
127
 * Return the smallest MPU region size that a given number of bytes will fit
128
 * into.  The region size is returned as the value that should be programmed
129
 * into the region attribute register for that region.
130
 */
131
static unsigned long prvGetMPURegionSizeSetting( unsigned long ulActualSizeInBytes ) PRIVILEGED_FUNCTION;
132
 
133
/*
134
 * Checks to see if being called from the context of an unprivileged task, and
135
 * if so raises the privilege level and returns false - otherwise does nothing
136
 * other than return true.
137
 */
138
static portBASE_TYPE prvRaisePrivilege( void ) __attribute__(( naked ));
139
 
140
/*
141
 * Standard FreeRTOS exception handlers.
142
 */
143
void xPortPendSVHandler( void ) __attribute__ (( naked )) PRIVILEGED_FUNCTION;
144
void xPortSysTickHandler( void )  __attribute__ ((optimize("3"))) PRIVILEGED_FUNCTION;
145
void vPortSVCHandler( void ) __attribute__ (( naked )) PRIVILEGED_FUNCTION;
146
 
147
/*
148
 * Starts the scheduler by restoring the context of the first task to run.
149
 */
150
static void prvRestoreContextOfFirstTask( void ) __attribute__(( naked )) PRIVILEGED_FUNCTION;
151
 
152
/*
153
 * C portion of the SVC handler.  The SVC handler is split between an asm entry
154
 * and a C wrapper for simplicity of coding and maintenance.
155
 */
156
static void prvSVCHandler( unsigned long *pulRegisters ) __attribute__(( noinline )) PRIVILEGED_FUNCTION;
157
 
158
/*
159
 * Prototypes for all the MPU wrappers.
160
 */
161
signed portBASE_TYPE MPU_xTaskGenericCreate( pdTASK_CODE pvTaskCode, const signed char * const pcName, unsigned short usStackDepth, void *pvParameters, unsigned portBASE_TYPE uxPriority, xTaskHandle *pxCreatedTask, portSTACK_TYPE *puxStackBuffer, const xMemoryRegion * const xRegions );
162
void MPU_vTaskAllocateMPURegions( xTaskHandle xTask, const xMemoryRegion * const xRegions );
163
void MPU_vTaskDelete( xTaskHandle pxTaskToDelete );
164
void MPU_vTaskDelayUntil( portTickType * const pxPreviousWakeTime, portTickType xTimeIncrement );
165
void MPU_vTaskDelay( portTickType xTicksToDelay );
166
unsigned portBASE_TYPE MPU_uxTaskPriorityGet( xTaskHandle pxTask );
167
void MPU_vTaskPrioritySet( xTaskHandle pxTask, unsigned portBASE_TYPE uxNewPriority );
168
void MPU_vTaskSuspend( xTaskHandle pxTaskToSuspend );
169
signed portBASE_TYPE MPU_xTaskIsTaskSuspended( xTaskHandle xTask );
170
void MPU_vTaskResume( xTaskHandle pxTaskToResume );
171
void MPU_vTaskSuspendAll( void );
172
signed portBASE_TYPE MPU_xTaskResumeAll( void );
173
portTickType MPU_xTaskGetTickCount( void );
174
unsigned portBASE_TYPE MPU_uxTaskGetNumberOfTasks( void );
175
void MPU_vTaskList( signed char *pcWriteBuffer );
176
void MPU_vTaskGetRunTimeStats( signed char *pcWriteBuffer );
177
void MPU_vTaskStartTrace( signed char * pcBuffer, unsigned long ulBufferSize );
178
unsigned long MPU_ulTaskEndTrace( void );
179
void MPU_vTaskSetApplicationTaskTag( xTaskHandle xTask, pdTASK_HOOK_CODE pxTagValue );
180
pdTASK_HOOK_CODE MPU_xTaskGetApplicationTaskTag( xTaskHandle xTask );
181
portBASE_TYPE MPU_xTaskCallApplicationTaskHook( xTaskHandle xTask, void *pvParameter );
182
unsigned portBASE_TYPE MPU_uxTaskGetStackHighWaterMark( xTaskHandle xTask );
183
xTaskHandle MPU_xTaskGetCurrentTaskHandle( void );
184
portBASE_TYPE MPU_xTaskGetSchedulerState( void );
185
xQueueHandle MPU_xQueueCreate( unsigned portBASE_TYPE uxQueueLength, unsigned portBASE_TYPE uxItemSize );
186
signed portBASE_TYPE MPU_xQueueGenericSend( xQueueHandle xQueue, const void * const pvItemToQueue, portTickType xTicksToWait, portBASE_TYPE xCopyPosition );
187
unsigned portBASE_TYPE MPU_uxQueueMessagesWaiting( const xQueueHandle pxQueue );
188
signed portBASE_TYPE MPU_xQueueGenericReceive( xQueueHandle pxQueue, void * const pvBuffer, portTickType xTicksToWait, portBASE_TYPE xJustPeeking );
189
xQueueHandle MPU_xQueueCreateMutex( void );
190
xQueueHandle MPU_xQueueCreateCountingSemaphore( unsigned portBASE_TYPE uxCountValue, unsigned portBASE_TYPE uxInitialCount );
191
portBASE_TYPE MPU_xQueueTakeMutexRecursive( xQueueHandle xMutex, portTickType xBlockTime );
192
portBASE_TYPE MPU_xQueueGiveMutexRecursive( xQueueHandle xMutex );
193
signed portBASE_TYPE MPU_xQueueAltGenericSend( xQueueHandle pxQueue, const void * const pvItemToQueue, portTickType xTicksToWait, portBASE_TYPE xCopyPosition );
194
signed portBASE_TYPE MPU_xQueueAltGenericReceive( xQueueHandle pxQueue, void * const pvBuffer, portTickType xTicksToWait, portBASE_TYPE xJustPeeking );
195
void MPU_vQueueAddToRegistry( xQueueHandle xQueue, signed char *pcName );
196
void *MPU_pvPortMalloc( size_t xSize );
197
void MPU_vPortFree( void *pv );
198
void MPU_vPortInitialiseBlocks( void );
199
size_t MPU_xPortGetFreeHeapSize( void );
200
 
201
/*-----------------------------------------------------------*/
202
 
203
/*
204
 * See header file for description.
205
 */
206
portSTACK_TYPE *pxPortInitialiseStack( portSTACK_TYPE *pxTopOfStack, pdTASK_CODE pxCode, void *pvParameters, portBASE_TYPE xRunPrivileged )
207
{
208
        /* Simulate the stack frame as it would be created by a context switch
209
        interrupt. */
210
        pxTopOfStack--; /* Offset added to account for the way the MCU uses the stack on entry/exit of interrupts. */
211
        *pxTopOfStack = portINITIAL_XPSR;       /* xPSR */
212
        pxTopOfStack--;
213
        *pxTopOfStack = ( portSTACK_TYPE ) pxCode;      /* PC */
214
        pxTopOfStack--;
215
        *pxTopOfStack = 0;       /* LR */
216
        pxTopOfStack -= 5;      /* R12, R3, R2 and R1. */
217
        *pxTopOfStack = ( portSTACK_TYPE ) pvParameters;        /* R0 */
218
        pxTopOfStack -= 9;      /* R11, R10, R9, R8, R7, R6, R5 and R4. */
219
 
220
        if( xRunPrivileged == pdTRUE )
221
        {
222
                *pxTopOfStack = portINITIAL_CONTROL_IF_PRIVILEGED;
223
        }
224
        else
225
        {
226
                *pxTopOfStack = portINITIAL_CONTROL_IF_UNPRIVILEGED;
227
        }
228
 
229
        return pxTopOfStack;
230
}
231
/*-----------------------------------------------------------*/
232
 
233
void vPortSVCHandler( void )
234
{
235
        /* Assumes psp was in use. */
236
        __asm volatile
237
        (
238
                #ifndef USE_PROCESS_STACK       /* Code should not be required if a main() is using the process stack. */
239
                        "       tst lr, #4                                              \n"
240
                        "       ite eq                                                  \n"
241
                        "       mrseq r0, msp                                   \n"
242
                        "       mrsne r0, psp                                   \n"
243
                #else
244
                        "       mrs r0, psp                                             \n"
245
                #endif
246
                        "       b prvSVCHandler                                 \n"
247
                        :::"r0"
248
        );
249
 
250
        /* This will never get executed, but is required to prevent prvSVCHandler
251
        being removed by the optimiser. */
252
        prvSVCHandler( NULL );
253
}
254
/*-----------------------------------------------------------*/
255
 
256
static void prvSVCHandler(      unsigned long *pulParam )
257
{
258
unsigned char ucSVCNumber;
259
 
260
        /* The stack contains: r0, r1, r2, r3, r12, r14, the return address and
261
        xPSR.  The first argument (r0) is pulParam[ 0 ]. */
262
        ucSVCNumber = ( ( unsigned char * ) pulParam[ portOFFSET_TO_PC ] )[ -2 ];
263
        switch( ucSVCNumber )
264
        {
265
                case portSVC_START_SCHEDULER    :       *(portNVIC_SYSPRI1) |= portNVIC_SVC_PRI;
266
                                                                                        prvRestoreContextOfFirstTask();
267
                                                                                        break;
268
 
269
                case portSVC_YIELD                              :       *(portNVIC_INT_CTRL) = portNVIC_PENDSVSET;
270
                                                                                        break;
271
 
272
                case portSVC_RAISE_PRIVILEGE    :       __asm volatile
273
                                                                                        (
274
                                                                                                "       mrs r1, control         \n" /* Obtain current control value. */
275
                                                                                                "       bic r1, #1                      \n" /* Set privilege bit. */
276
                                                                                                "       msr control, r1         \n" /* Write back new control value. */
277
                                                                                                :::"r1"
278
                                                                                        );
279
                                                                                        break;
280
 
281
                default                                                 :       /* Unknown SVC call. */
282
                                                                                        break;
283
        }
284
}
285
/*-----------------------------------------------------------*/
286
 
287
static void prvRestoreContextOfFirstTask( void )
288
{
289
        __asm volatile
290
        (
291
                "       ldr r0, =0xE000ED08                             \n" /* Use the NVIC offset register to locate the stack. */
292
                "       ldr r0, [r0]                                    \n"
293
                "       ldr r0, [r0]                                    \n"
294
                "       msr msp, r0                                             \n" /* Set the msp back to the start of the stack. */
295
                "       ldr     r3, pxCurrentTCBConst2          \n" /* Restore the context. */
296
                "       ldr r1, [r3]                                    \n"
297
                "       ldr r0, [r1]                                    \n" /* The first item in the TCB is the task top of stack. */
298
                "       add r1, r1, #4                                  \n" /* Move onto the second item in the TCB... */
299
                "       ldr r2, =0xe000ed9c                             \n" /* Region Base Address register. */
300
                "       ldmia r1!, {r4-r11}                             \n" /* Read 4 sets of MPU registers. */
301
                "       stmia r2!, {r4-r11}                             \n" /* Write 4 sets of MPU registers. */
302
                "       ldmia r0!, {r3, r4-r11}                 \n" /* Pop the registers that are not automatically saved on exception entry. */
303
                "       msr control, r3                                 \n"
304
                "       msr psp, r0                                             \n" /* Restore the task stack pointer. */
305
                "       mov r0, #0                                              \n"
306
                "       msr     basepri, r0                                     \n"
307
                "       ldr r14, =0xfffffffd                    \n" /* Load exec return code. */
308
                "       bx r14                                                  \n"
309
                "                                                                       \n"
310
                "       .align 2                                                \n"
311
                "pxCurrentTCBConst2: .word pxCurrentTCB \n"
312
        );
313
}
314
/*-----------------------------------------------------------*/
315
 
316
/*
317
 * See header file for description.
318
 */
319
portBASE_TYPE xPortStartScheduler( void )
320
{
321
        /* Make PendSV and SysTick the same priroity as the kernel. */
322
        *(portNVIC_SYSPRI2) |= portNVIC_PENDSV_PRI;
323
        *(portNVIC_SYSPRI2) |= portNVIC_SYSTICK_PRI;
324
 
325
        /* Configure the regions in the MPU that are common to all tasks. */
326
        prvSetupMPU();
327
 
328
        /* Start the timer that generates the tick ISR.  Interrupts are disabled
329
        here already. */
330
        prvSetupTimerInterrupt();
331
 
332
        /* Initialise the critical nesting count ready for the first task. */
333
        uxCriticalNesting = 0;
334
 
335
        /* Start the first task. */
336
        __asm volatile( "       svc %0                  \n"
337
                                        :: "i" (portSVC_START_SCHEDULER) );
338
 
339
        /* Should not get here! */
340
        return 0;
341
}
342
/*-----------------------------------------------------------*/
343
 
344
void vPortEndScheduler( void )
345
{
346
        /* It is unlikely that the CM3 port will require this function as there
347
        is nothing to return to.  */
348
}
349
/*-----------------------------------------------------------*/
350
 
351
void vPortEnterCritical( void )
352
{
353
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
354
 
355
        portDISABLE_INTERRUPTS();
356
        uxCriticalNesting++;
357
 
358
        portRESET_PRIVILEGE( xRunningPrivileged );
359
}
360
/*-----------------------------------------------------------*/
361
 
362
void vPortExitCritical( void )
363
{
364
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
365
 
366
        uxCriticalNesting--;
367
        if( uxCriticalNesting == 0 )
368
        {
369
                portENABLE_INTERRUPTS();
370
        }
371
        portRESET_PRIVILEGE( xRunningPrivileged );
372
}
373
/*-----------------------------------------------------------*/
374
 
375
void xPortPendSVHandler( void )
376
{
377
        /* This is a naked function. */
378
 
379
        __asm volatile
380
        (
381
                "       mrs r0, psp                                                     \n"
382
                "                                                                               \n"
383
                "       ldr     r3, pxCurrentTCBConst                   \n" /* Get the location of the current TCB. */
384
                "       ldr     r2, [r3]                                                \n"
385
                "                                                                               \n"
386
                "       mrs r1, control                                         \n"
387
                "       stmdb r0!, {r1, r4-r11}                         \n" /* Save the remaining registers. */
388
                "       str r0, [r2]                                            \n" /* Save the new top of stack into the first member of the TCB. */
389
                "                                                                               \n"
390
                "       stmdb sp!, {r3, r14}                            \n"
391
                "       mov r0, %0                                                      \n"
392
                "       msr basepri, r0                                         \n"
393
                "       bl vTaskSwitchContext                           \n"
394
                "       mov r0, #0                                                      \n"
395
                "       msr basepri, r0                                         \n"
396
                "       ldmia sp!, {r3, r14}                            \n"
397
                "                                                                               \n"     /* Restore the context. */
398
                "       ldr r1, [r3]                                            \n"
399
                "       ldr r0, [r1]                                            \n" /* The first item in the TCB is the task top of stack. */
400
                "       add r1, r1, #4                                          \n" /* Move onto the second item in the TCB... */
401
                "       ldr r2, =0xe000ed9c                                     \n" /* Region Base Address register. */
402
                "       ldmia r1!, {r4-r11}                                     \n" /* Read 4 sets of MPU registers. */
403
                "       stmia r2!, {r4-r11}                                     \n" /* Write 4 sets of MPU registers. */
404
                "       ldmia r0!, {r3, r4-r11}                         \n" /* Pop the registers that are not automatically saved on exception entry. */
405
                "       msr control, r3                                         \n"
406
                "                                                                               \n"
407
                "       msr psp, r0                                                     \n"
408
                "       bx r14                                                          \n"
409
                "                                                                               \n"
410
                "       .align 2                                                        \n"
411
                "pxCurrentTCBConst: .word pxCurrentTCB  \n"
412
                ::"i"(configMAX_SYSCALL_INTERRUPT_PRIORITY)
413
        );
414
}
415
/*-----------------------------------------------------------*/
416
 
417
void xPortSysTickHandler( void )
418
{
419
unsigned long ulDummy;
420
 
421
        /* If using preemption, also force a context switch. */
422
        #if configUSE_PREEMPTION == 1
423
                *(portNVIC_INT_CTRL) = portNVIC_PENDSVSET;
424
        #endif
425
 
426
        ulDummy = portSET_INTERRUPT_MASK_FROM_ISR();
427
        {
428
                vTaskIncrementTick();
429
        }
430
        portCLEAR_INTERRUPT_MASK_FROM_ISR( ulDummy );
431
}
432
/*-----------------------------------------------------------*/
433
 
434
/*
435
 * Setup the systick timer to generate the tick interrupts at the required
436
 * frequency.
437
 */
438
static void prvSetupTimerInterrupt( void )
439
{
440
        /* Configure SysTick to interrupt at the requested rate. */
441
        *(portNVIC_SYSTICK_LOAD) = ( configCPU_CLOCK_HZ / configTICK_RATE_HZ ) - 1UL;
442
        *(portNVIC_SYSTICK_CTRL) = portNVIC_SYSTICK_CLK | portNVIC_SYSTICK_INT | portNVIC_SYSTICK_ENABLE;
443
}
444
/*-----------------------------------------------------------*/
445
 
446
static void prvSetupMPU( void )
447
{
448
extern unsigned long __privileged_functions_end__[];
449
extern unsigned long __FLASH_segment_start__[];
450
extern unsigned long __FLASH_segment_end__[];
451
extern unsigned long __privileged_data_start__[];
452
extern unsigned long __privileged_data_end__[];
453
 
454
        /* Check the expected MPU is present. */
455
        if( *portMPU_TYPE == portEXPECTED_MPU_TYPE_VALUE )
456
        {
457
                /* First setup the entire flash for unprivileged read only access. */
458
        *portMPU_REGION_BASE_ADDRESS =  ( ( unsigned long ) __FLASH_segment_start__ ) | /* Base address. */
459
                                                                                ( portMPU_REGION_VALID ) |
460
                                                                                ( portUNPRIVILEGED_FLASH_REGION );
461
 
462
                *portMPU_REGION_ATTRIBUTE =             ( portMPU_REGION_READ_ONLY ) |
463
                                                                                ( portMPU_REGION_CACHEABLE_BUFFERABLE ) |
464
                                                                                ( prvGetMPURegionSizeSetting( ( unsigned long ) __FLASH_segment_end__ - ( unsigned long ) __FLASH_segment_start__ ) ) |
465
                                                                                ( portMPU_REGION_ENABLE );
466
 
467
                /* Setup the first 16K for privileged only access (even though less
468
                than 10K is actually being used).  This is where the kernel code is
469
                placed. */
470
        *portMPU_REGION_BASE_ADDRESS =  ( ( unsigned long ) __FLASH_segment_start__ ) | /* Base address. */
471
                                                                                ( portMPU_REGION_VALID ) |
472
                                                                                ( portPRIVILEGED_FLASH_REGION );
473
 
474
                *portMPU_REGION_ATTRIBUTE =             ( portMPU_REGION_PRIVILEGED_READ_ONLY ) |
475
                                                                                ( portMPU_REGION_CACHEABLE_BUFFERABLE ) |
476
                                                                                ( prvGetMPURegionSizeSetting( ( unsigned long ) __privileged_functions_end__ - ( unsigned long ) __FLASH_segment_start__ ) ) |
477
                                                                                ( portMPU_REGION_ENABLE );
478
 
479
                /* Setup the privileged data RAM region.  This is where the kernel data
480
                is placed. */
481
                *portMPU_REGION_BASE_ADDRESS =  ( ( unsigned long ) __privileged_data_start__ ) | /* Base address. */
482
                                                                                ( portMPU_REGION_VALID ) |
483
                                                                                ( portPRIVILEGED_RAM_REGION );
484
 
485
                *portMPU_REGION_ATTRIBUTE =             ( portMPU_REGION_PRIVILEGED_READ_WRITE ) |
486
                                                                                ( portMPU_REGION_CACHEABLE_BUFFERABLE ) |
487
                                                                                prvGetMPURegionSizeSetting( ( unsigned long ) __privileged_data_end__ - ( unsigned long ) __privileged_data_start__ ) |
488
                                                                                ( portMPU_REGION_ENABLE );
489
 
490
                /* By default allow everything to access the general peripherals.  The
491
                system peripherals and registers are protected. */
492
                *portMPU_REGION_BASE_ADDRESS =  ( portPERIPHERALS_START_ADDRESS ) |
493
                                                                                ( portMPU_REGION_VALID ) |
494
                                                                                ( portGENERAL_PERIPHERALS_REGION );
495
 
496
                *portMPU_REGION_ATTRIBUTE =             ( portMPU_REGION_READ_WRITE | portMPU_REGION_EXECUTE_NEVER ) |
497
                                                                                ( prvGetMPURegionSizeSetting( portPERIPHERALS_END_ADDRESS - portPERIPHERALS_START_ADDRESS ) ) |
498
                                                                                ( portMPU_REGION_ENABLE );
499
 
500
                /* Enable the memory fault exception. */
501
                *portNVIC_SYS_CTRL_STATE |= portNVIC_MEM_FAULT_ENABLE;
502
 
503
                /* Enable the MPU with the background region configured. */
504
                *portMPU_CTRL |= ( portMPU_ENABLE | portMPU_BACKGROUND_ENABLE );
505
        }
506
}
507
/*-----------------------------------------------------------*/
508
 
509
static unsigned long prvGetMPURegionSizeSetting( unsigned long ulActualSizeInBytes )
510
{
511
unsigned long ulRegionSize, ulReturnValue = 4;
512
 
513
        /* 32 is the smallest region size, 31 is the largest valid value for
514
        ulReturnValue. */
515
        for( ulRegionSize = 32UL; ulReturnValue < 31UL; ( ulRegionSize <<= 1UL ) )
516
        {
517
                if( ulActualSizeInBytes <= ulRegionSize )
518
                {
519
                        break;
520
                }
521
                else
522
                {
523
                        ulReturnValue++;
524
                }
525
        }
526
 
527
        /* Shift the code by one before returning so it can be written directly
528
        into the the correct bit position of the attribute register. */
529
        return ( ulReturnValue << 1UL );
530
}
531
/*-----------------------------------------------------------*/
532
 
533
static portBASE_TYPE prvRaisePrivilege( void )
534
{
535
        __asm volatile
536
        (
537
                "       mrs r0, control                                         \n"
538
                "       tst r0, #1                                                      \n" /* Is the task running privileged? */
539
                "       itte ne                                                         \n"
540
                "       movne r0, #0                                            \n" /* CONTROL[0]!=0, return false. */
541
                "       svcne %0                                                        \n" /* Switch to privileged. */
542
                "       moveq r0, #1                                            \n" /* CONTROL[0]==0, return true. */
543
                "       bx lr                                                           \n"
544
                :: "i" (portSVC_RAISE_PRIVILEGE) : "r0"
545
        );
546
 
547
        return 0;
548
}
549
/*-----------------------------------------------------------*/
550
 
551
void vPortStoreTaskMPUSettings( xMPU_SETTINGS *xMPUSettings, const struct xMEMORY_REGION * const xRegions, portSTACK_TYPE *pxBottomOfStack, unsigned short usStackDepth )
552
{
553
extern unsigned long __SRAM_segment_start__[];
554
extern unsigned long __SRAM_segment_end__[];
555
extern unsigned long __privileged_data_start__[];
556
extern unsigned long __privileged_data_end__[];
557
long lIndex;
558
unsigned long ul;
559
 
560
        if( xRegions == NULL )
561
        {
562
                /* No MPU regions are specified so allow access to all RAM. */
563
        xMPUSettings->xRegion[ 0 ].ulRegionBaseAddress =
564
                                ( ( unsigned long ) __SRAM_segment_start__ ) | /* Base address. */
565
                                ( portMPU_REGION_VALID ) |
566
                                ( portSTACK_REGION );
567
 
568
                xMPUSettings->xRegion[ 0 ].ulRegionAttribute =
569
                                ( portMPU_REGION_READ_WRITE ) |
570
                                ( portMPU_REGION_CACHEABLE_BUFFERABLE ) |
571
                                ( prvGetMPURegionSizeSetting( ( unsigned long ) __SRAM_segment_end__ - ( unsigned long ) __SRAM_segment_start__ ) ) |
572
                                ( portMPU_REGION_ENABLE );
573
 
574
                /* Re-instate the privileged only RAM region as xRegion[ 0 ] will have
575
                just removed the privileged only parameters. */
576
                xMPUSettings->xRegion[ 1 ].ulRegionBaseAddress =
577
                                ( ( unsigned long ) __privileged_data_start__ ) | /* Base address. */
578
                                ( portMPU_REGION_VALID ) |
579
                                ( portSTACK_REGION + 1 );
580
 
581
                xMPUSettings->xRegion[ 1 ].ulRegionAttribute =
582
                                ( portMPU_REGION_PRIVILEGED_READ_WRITE ) |
583
                                ( portMPU_REGION_CACHEABLE_BUFFERABLE ) |
584
                                prvGetMPURegionSizeSetting( ( unsigned long ) __privileged_data_end__ - ( unsigned long ) __privileged_data_start__ ) |
585
                                ( portMPU_REGION_ENABLE );
586
 
587
                /* Invalidate all other regions. */
588
                for( ul = 2; ul <= portNUM_CONFIGURABLE_REGIONS; ul++ )
589
                {
590
                        xMPUSettings->xRegion[ ul ].ulRegionBaseAddress = ( portSTACK_REGION + ul ) | portMPU_REGION_VALID;
591
                        xMPUSettings->xRegion[ ul ].ulRegionAttribute = 0UL;
592
                }
593
        }
594
        else
595
        {
596
                /* This function is called automatically when the task is created - in
597
                which case the stack region parameters will be valid.  At all other
598
                times the stack parameters will not be valid and it is assumed that the
599
                stack region has already been configured. */
600
                if( usStackDepth > 0 )
601
                {
602
                        /* Define the region that allows access to the stack. */
603
                        xMPUSettings->xRegion[ 0 ].ulRegionBaseAddress =
604
                                        ( ( unsigned long ) pxBottomOfStack ) |
605
                                        ( portMPU_REGION_VALID ) |
606
                                        ( portSTACK_REGION ); /* Region number. */
607
 
608
                        xMPUSettings->xRegion[ 0 ].ulRegionAttribute =
609
                                        ( portMPU_REGION_READ_WRITE ) | /* Read and write. */
610
                                        ( prvGetMPURegionSizeSetting( ( unsigned long ) usStackDepth * ( unsigned long ) sizeof( portSTACK_TYPE ) ) ) |
611
                                        ( portMPU_REGION_CACHEABLE_BUFFERABLE ) |
612
                                        ( portMPU_REGION_ENABLE );
613
                }
614
 
615
                lIndex = 0;
616
 
617
                for( ul = 1; ul <= portNUM_CONFIGURABLE_REGIONS; ul++ )
618
                {
619
                        if( ( xRegions[ lIndex ] ).ulLengthInBytes > 0UL )
620
                        {
621
                                /* Translate the generic region definition contained in
622
                                xRegions into the CM3 specific MPU settings that are then
623
                                stored in xMPUSettings. */
624
                                xMPUSettings->xRegion[ ul ].ulRegionBaseAddress =
625
                                                ( ( unsigned long ) xRegions[ lIndex ].pvBaseAddress ) |
626
                                                ( portMPU_REGION_VALID ) |
627
                                                ( portSTACK_REGION + ul ); /* Region number. */
628
 
629
                                xMPUSettings->xRegion[ ul ].ulRegionAttribute =
630
                                                ( prvGetMPURegionSizeSetting( xRegions[ lIndex ].ulLengthInBytes ) ) |
631
                                                ( xRegions[ lIndex ].ulParameters ) |
632
                                                ( portMPU_REGION_ENABLE );
633
                        }
634
                        else
635
                        {
636
                                /* Invalidate the region. */
637
                                xMPUSettings->xRegion[ ul ].ulRegionBaseAddress = ( portSTACK_REGION + ul ) | portMPU_REGION_VALID;
638
                                xMPUSettings->xRegion[ ul ].ulRegionAttribute = 0UL;
639
                        }
640
 
641
                        lIndex++;
642
                }
643
        }
644
}
645
/*-----------------------------------------------------------*/
646
 
647
signed portBASE_TYPE MPU_xTaskGenericCreate( pdTASK_CODE pvTaskCode, const signed char * const pcName, unsigned short usStackDepth, void *pvParameters, unsigned portBASE_TYPE uxPriority, xTaskHandle *pxCreatedTask, portSTACK_TYPE *puxStackBuffer, const xMemoryRegion * const xRegions )
648
{
649
signed portBASE_TYPE xReturn;
650
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
651
 
652
        xReturn = xTaskGenericCreate( pvTaskCode, pcName, usStackDepth, pvParameters, uxPriority, pxCreatedTask, puxStackBuffer, xRegions );
653
        portRESET_PRIVILEGE( xRunningPrivileged );
654
        return xReturn;
655
}
656
/*-----------------------------------------------------------*/
657
 
658
void MPU_vTaskAllocateMPURegions( xTaskHandle xTask, const xMemoryRegion * const xRegions )
659
{
660
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
661
 
662
        vTaskAllocateMPURegions( xTask, xRegions );
663
        portRESET_PRIVILEGE( xRunningPrivileged );
664
}
665
/*-----------------------------------------------------------*/
666
 
667
#if ( INCLUDE_vTaskDelete == 1 )
668
        void MPU_vTaskDelete( xTaskHandle pxTaskToDelete )
669
        {
670
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
671
 
672
                vTaskDelete( pxTaskToDelete );
673
        portRESET_PRIVILEGE( xRunningPrivileged );
674
        }
675
#endif
676
/*-----------------------------------------------------------*/
677
 
678
#if ( INCLUDE_vTaskDelayUntil == 1 )
679
        void MPU_vTaskDelayUntil( portTickType * const pxPreviousWakeTime, portTickType xTimeIncrement )
680
        {
681
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
682
 
683
                vTaskDelayUntil( pxPreviousWakeTime, xTimeIncrement );
684
        portRESET_PRIVILEGE( xRunningPrivileged );
685
        }
686
#endif
687
/*-----------------------------------------------------------*/
688
 
689
#if ( INCLUDE_vTaskDelay == 1 )
690
        void MPU_vTaskDelay( portTickType xTicksToDelay )
691
        {
692
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
693
 
694
                vTaskDelay( xTicksToDelay );
695
        portRESET_PRIVILEGE( xRunningPrivileged );
696
        }
697
#endif
698
/*-----------------------------------------------------------*/
699
 
700
#if ( INCLUDE_uxTaskPriorityGet == 1 )
701
        unsigned portBASE_TYPE MPU_uxTaskPriorityGet( xTaskHandle pxTask )
702
        {
703
        unsigned portBASE_TYPE uxReturn;
704
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
705
 
706
                uxReturn = uxTaskPriorityGet( pxTask );
707
        portRESET_PRIVILEGE( xRunningPrivileged );
708
                return uxReturn;
709
        }
710
#endif
711
/*-----------------------------------------------------------*/
712
 
713
#if ( INCLUDE_vTaskPrioritySet == 1 )
714
        void MPU_vTaskPrioritySet( xTaskHandle pxTask, unsigned portBASE_TYPE uxNewPriority )
715
        {
716
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
717
 
718
                vTaskPrioritySet( pxTask, uxNewPriority );
719
        portRESET_PRIVILEGE( xRunningPrivileged );
720
        }
721
#endif
722
/*-----------------------------------------------------------*/
723
 
724
#if ( INCLUDE_vTaskSuspend == 1 )
725
        void MPU_vTaskSuspend( xTaskHandle pxTaskToSuspend )
726
        {
727
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
728
 
729
                vTaskSuspend( pxTaskToSuspend );
730
        portRESET_PRIVILEGE( xRunningPrivileged );
731
        }
732
#endif
733
/*-----------------------------------------------------------*/
734
 
735
#if ( INCLUDE_vTaskSuspend == 1 )
736
        signed portBASE_TYPE MPU_xTaskIsTaskSuspended( xTaskHandle xTask )
737
        {
738
        signed portBASE_TYPE xReturn;
739
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
740
 
741
                xReturn = xTaskIsTaskSuspended( xTask );
742
        portRESET_PRIVILEGE( xRunningPrivileged );
743
                return xReturn;
744
        }
745
#endif
746
/*-----------------------------------------------------------*/
747
 
748
#if ( INCLUDE_vTaskSuspend == 1 )
749
        void MPU_vTaskResume( xTaskHandle pxTaskToResume )
750
        {
751
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
752
 
753
                vTaskResume( pxTaskToResume );
754
        portRESET_PRIVILEGE( xRunningPrivileged );
755
        }
756
#endif
757
/*-----------------------------------------------------------*/
758
 
759
void MPU_vTaskSuspendAll( void )
760
{
761
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
762
 
763
        vTaskSuspendAll();
764
    portRESET_PRIVILEGE( xRunningPrivileged );
765
}
766
/*-----------------------------------------------------------*/
767
 
768
signed portBASE_TYPE MPU_xTaskResumeAll( void )
769
{
770
signed portBASE_TYPE xReturn;
771
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
772
 
773
        xReturn = xTaskResumeAll();
774
    portRESET_PRIVILEGE( xRunningPrivileged );
775
    return xReturn;
776
}
777
/*-----------------------------------------------------------*/
778
 
779
portTickType MPU_xTaskGetTickCount( void )
780
{
781
portTickType xReturn;
782
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
783
 
784
        xReturn = xTaskGetTickCount();
785
    portRESET_PRIVILEGE( xRunningPrivileged );
786
        return xReturn;
787
}
788
/*-----------------------------------------------------------*/
789
 
790
unsigned portBASE_TYPE MPU_uxTaskGetNumberOfTasks( void )
791
{
792
unsigned portBASE_TYPE uxReturn;
793
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
794
 
795
        uxReturn = uxTaskGetNumberOfTasks();
796
    portRESET_PRIVILEGE( xRunningPrivileged );
797
        return uxReturn;
798
}
799
/*-----------------------------------------------------------*/
800
 
801
#if ( configUSE_TRACE_FACILITY == 1 )
802
        void MPU_vTaskList( signed char *pcWriteBuffer )
803
        {
804
        portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
805
 
806
                vTaskList( pcWriteBuffer );
807
                portRESET_PRIVILEGE( xRunningPrivileged );
808
        }
809
#endif
810
/*-----------------------------------------------------------*/
811
 
812
#if ( configGENERATE_RUN_TIME_STATS == 1 )
813
        void MPU_vTaskGetRunTimeStats( signed char *pcWriteBuffer )
814
        {
815
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
816
 
817
                vTaskGetRunTimeStats( pcWriteBuffer );
818
        portRESET_PRIVILEGE( xRunningPrivileged );
819
        }
820
#endif
821
/*-----------------------------------------------------------*/
822
 
823
#if ( configUSE_TRACE_FACILITY == 1 )
824
        void MPU_vTaskStartTrace( signed char * pcBuffer, unsigned long ulBufferSize )
825
        {
826
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
827
 
828
                vTaskStartTrace( pcBuffer, ulBufferSize );
829
        portRESET_PRIVILEGE( xRunningPrivileged );
830
        }
831
#endif
832
/*-----------------------------------------------------------*/
833
 
834
#if ( configUSE_TRACE_FACILITY == 1 )
835
        unsigned long MPU_ulTaskEndTrace( void )
836
        {
837
        unsigned long ulReturn;
838
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
839
 
840
                ulReturn = ulTaskEndTrace();
841
        portRESET_PRIVILEGE( xRunningPrivileged );
842
                return ulReturn;
843
        }
844
#endif
845
/*-----------------------------------------------------------*/
846
 
847
#if ( configUSE_APPLICATION_TASK_TAG == 1 )
848
        void MPU_vTaskSetApplicationTaskTag( xTaskHandle xTask, pdTASK_HOOK_CODE pxTagValue )
849
        {
850
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
851
 
852
                vTaskSetApplicationTaskTag( xTask, pxTagValue );
853
        portRESET_PRIVILEGE( xRunningPrivileged );
854
        }
855
#endif
856
/*-----------------------------------------------------------*/
857
 
858
#if ( configUSE_APPLICATION_TASK_TAG == 1 )
859
        pdTASK_HOOK_CODE MPU_xTaskGetApplicationTaskTag( xTaskHandle xTask )
860
        {
861
        pdTASK_HOOK_CODE xReturn;
862
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
863
 
864
                xReturn = xTaskGetApplicationTaskTag( xTask );
865
        portRESET_PRIVILEGE( xRunningPrivileged );
866
                return xReturn;
867
        }
868
#endif
869
/*-----------------------------------------------------------*/
870
 
871
#if ( configUSE_APPLICATION_TASK_TAG == 1 )
872
        portBASE_TYPE MPU_xTaskCallApplicationTaskHook( xTaskHandle xTask, void *pvParameter )
873
        {
874
        portBASE_TYPE xReturn;
875
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
876
 
877
                xReturn = xTaskCallApplicationTaskHook( xTask, pvParameter );
878
        portRESET_PRIVILEGE( xRunningPrivileged );
879
                return xReturn;
880
        }
881
#endif
882
/*-----------------------------------------------------------*/
883
 
884
#if ( INCLUDE_uxTaskGetStackHighWaterMark == 1 )
885
        unsigned portBASE_TYPE MPU_uxTaskGetStackHighWaterMark( xTaskHandle xTask )
886
        {
887
        unsigned portBASE_TYPE uxReturn;
888
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
889
 
890
                uxReturn = uxTaskGetStackHighWaterMark( xTask );
891
        portRESET_PRIVILEGE( xRunningPrivileged );
892
                return uxReturn;
893
        }
894
#endif
895
/*-----------------------------------------------------------*/
896
 
897
#if ( INCLUDE_xTaskGetCurrentTaskHandle == 1 )
898
        xTaskHandle MPU_xTaskGetCurrentTaskHandle( void )
899
        {
900
        xTaskHandle xReturn;
901
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
902
 
903
                xReturn = xTaskGetCurrentTaskHandle();
904
        portRESET_PRIVILEGE( xRunningPrivileged );
905
                return xReturn;
906
        }
907
#endif
908
/*-----------------------------------------------------------*/
909
 
910
#if ( INCLUDE_xTaskGetSchedulerState == 1 )
911
        portBASE_TYPE MPU_xTaskGetSchedulerState( void )
912
        {
913
        portBASE_TYPE xReturn;
914
    portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
915
 
916
                xReturn = xTaskGetSchedulerState();
917
        portRESET_PRIVILEGE( xRunningPrivileged );
918
                return xReturn;
919
        }
920
#endif
921
/*-----------------------------------------------------------*/
922
 
923
xQueueHandle MPU_xQueueCreate( unsigned portBASE_TYPE uxQueueLength, unsigned portBASE_TYPE uxItemSize )
924
{
925
xQueueHandle xReturn;
926
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
927
 
928
        xReturn = xQueueCreate( uxQueueLength, uxItemSize );
929
        portRESET_PRIVILEGE( xRunningPrivileged );
930
        return xReturn;
931
}
932
/*-----------------------------------------------------------*/
933
 
934
signed portBASE_TYPE MPU_xQueueGenericSend( xQueueHandle xQueue, const void * const pvItemToQueue, portTickType xTicksToWait, portBASE_TYPE xCopyPosition )
935
{
936
signed portBASE_TYPE xReturn;
937
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
938
 
939
        xReturn = xQueueGenericSend( xQueue, pvItemToQueue, xTicksToWait, xCopyPosition );
940
        portRESET_PRIVILEGE( xRunningPrivileged );
941
        return xReturn;
942
}
943
/*-----------------------------------------------------------*/
944
 
945
unsigned portBASE_TYPE MPU_uxQueueMessagesWaiting( const xQueueHandle pxQueue )
946
{
947
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
948
unsigned portBASE_TYPE uxReturn;
949
 
950
        uxReturn = uxQueueMessagesWaiting( pxQueue );
951
        portRESET_PRIVILEGE( xRunningPrivileged );
952
        return uxReturn;
953
}
954
/*-----------------------------------------------------------*/
955
 
956
signed portBASE_TYPE MPU_xQueueGenericReceive( xQueueHandle pxQueue, void * const pvBuffer, portTickType xTicksToWait, portBASE_TYPE xJustPeeking )
957
{
958
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
959
signed portBASE_TYPE xReturn;
960
 
961
        xReturn = xQueueGenericReceive( pxQueue, pvBuffer, xTicksToWait, xJustPeeking );
962
        portRESET_PRIVILEGE( xRunningPrivileged );
963
        return xReturn;
964
}
965
/*-----------------------------------------------------------*/
966
 
967
#if ( configUSE_MUTEXES == 1 )
968
        xQueueHandle MPU_xQueueCreateMutex( void )
969
        {
970
    xQueueHandle xReturn;
971
        portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
972
 
973
                xReturn = xQueueCreateMutex();
974
                portRESET_PRIVILEGE( xRunningPrivileged );
975
                return xReturn;
976
        }
977
#endif
978
/*-----------------------------------------------------------*/
979
 
980
#if configUSE_COUNTING_SEMAPHORES == 1
981
        xQueueHandle MPU_xQueueCreateCountingSemaphore( unsigned portBASE_TYPE uxCountValue, unsigned portBASE_TYPE uxInitialCount )
982
        {
983
    xQueueHandle xReturn;
984
        portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
985
 
986
                xReturn = xQueueHandle xQueueCreateCountingSemaphore( uxCountValue, uxInitialCount );
987
                portRESET_PRIVILEGE( xRunningPrivileged );
988
                return xReturn;
989
        }
990
#endif
991
/*-----------------------------------------------------------*/
992
 
993
#if ( configUSE_MUTEXES == 1 )
994
        portBASE_TYPE MPU_xQueueTakeMutexRecursive( xQueueHandle xMutex, portTickType xBlockTime )
995
        {
996
        portBASE_TYPE xReturn;
997
        portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
998
 
999
                xReturn = xQueueTakeMutexRecursive( xMutex, xBlockTime );
1000
                portRESET_PRIVILEGE( xRunningPrivileged );
1001
                return xReturn;
1002
        }
1003
#endif
1004
/*-----------------------------------------------------------*/
1005
 
1006
#if ( configUSE_MUTEXES == 1 )
1007
        portBASE_TYPE MPU_xQueueGiveMutexRecursive( xQueueHandle xMutex )
1008
        {
1009
        portBASE_TYPE xReturn;
1010
        portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
1011
 
1012
                xReturn = xQueueGiveMutexRecursive( xMutex );
1013
                portRESET_PRIVILEGE( xRunningPrivileged );
1014
                return xReturn;
1015
        }
1016
#endif
1017
/*-----------------------------------------------------------*/
1018
 
1019
#if configUSE_ALTERNATIVE_API == 1
1020
        signed portBASE_TYPE MPU_xQueueAltGenericSend( xQueueHandle pxQueue, const void * const pvItemToQueue, portTickType xTicksToWait, portBASE_TYPE xCopyPosition )
1021
        {
1022
        signed portBASE_TYPE xReturn;
1023
        portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
1024
 
1025
                xReturn =       signed portBASE_TYPE xQueueAltGenericSend( pxQueue, pvItemToQueue, xTicksToWait, xCopyPosition );
1026
                portRESET_PRIVILEGE( xRunningPrivileged );
1027
                return xReturn;
1028
        }
1029
#endif
1030
/*-----------------------------------------------------------*/
1031
 
1032
#if configUSE_ALTERNATIVE_API == 1
1033
        signed portBASE_TYPE MPU_xQueueAltGenericReceive( xQueueHandle pxQueue, void * const pvBuffer, portTickType xTicksToWait, portBASE_TYPE xJustPeeking )
1034
        {
1035
    signed portBASE_TYPE xReturn;
1036
        portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
1037
 
1038
                xReturn = xQueueAltGenericReceive( pxQueue, pvBuffer, xTicksToWait, xJustPeeking );
1039
                portRESET_PRIVILEGE( xRunningPrivileged );
1040
                return xReturn;
1041
        }
1042
#endif
1043
/*-----------------------------------------------------------*/
1044
 
1045
#if configQUEUE_REGISTRY_SIZE > 0
1046
        void MPU_vQueueAddToRegistry( xQueueHandle xQueue, signed char *pcName )
1047
        {
1048
        portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
1049
 
1050
                vQueueAddToRegistry( xQueue, pcName );
1051
 
1052
                portRESET_PRIVILEGE( xRunningPrivileged );
1053
        }
1054
#endif
1055
/*-----------------------------------------------------------*/
1056
 
1057
void *MPU_pvPortMalloc( size_t xSize )
1058
{
1059
void *pvReturn;
1060
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
1061
 
1062
        pvReturn = pvPortMalloc( xSize );
1063
 
1064
        portRESET_PRIVILEGE( xRunningPrivileged );
1065
 
1066
        return pvReturn;
1067
}
1068
/*-----------------------------------------------------------*/
1069
 
1070
void MPU_vPortFree( void *pv )
1071
{
1072
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
1073
 
1074
        vPortFree( pv );
1075
 
1076
        portRESET_PRIVILEGE( xRunningPrivileged );
1077
}
1078
/*-----------------------------------------------------------*/
1079
 
1080
void MPU_vPortInitialiseBlocks( void )
1081
{
1082
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
1083
 
1084
        vPortInitialiseBlocks();
1085
 
1086
        portRESET_PRIVILEGE( xRunningPrivileged );
1087
}
1088
/*-----------------------------------------------------------*/
1089
 
1090
size_t MPU_xPortGetFreeHeapSize( void )
1091
{
1092
size_t xReturn;
1093
portBASE_TYPE xRunningPrivileged = prvRaisePrivilege();
1094
 
1095
        xReturn = xPortGetFreeHeapSize();
1096
 
1097
        portRESET_PRIVILEGE( xRunningPrivileged );
1098
 
1099
        return xReturn;
1100
}
1101
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.