Update system call entry mechanism (#898)

Earlier the System Call entry from an unprivileged task
looked like:

1. SVC for entering system call.
2. System call implementation.
3. SVC for exiting system call.

Now, the system call entry needs to make only one SVC
call and everything else is handled internally.

This PR also makes the following changes:

1. Update the Access Control List (ACL) mechanism to
    grant access to all the kernel objects before the
    scheduler is started.
2. Add one struct param for system calls with 5 parameters.
    This removes the need for special handling for system
    calls with 5 parameters.
3. Remove raise privilege SVC when MPU wrapper v2 is used.
4. Add additional run time parameter checks to MPU wrappers
    for xTaskGenericNotify and xQueueTakeMutexRecursive APIs.
This commit is contained in:
Gaurav-Aggarwal-AWS 2023-11-23 10:47:47 +05:30 committed by GitHub
parent 4ff01a7a4a
commit 76be28cdc6
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
114 changed files with 7521 additions and 16320 deletions

View file

@ -38,6 +38,8 @@
#include "timers.h"
#include "event_groups.h"
#include "stream_buffer.h"
#include "mpu_prototypes.h"
#include "mpu_syscall_numbers.h"
#undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE
/*-----------------------------------------------------------*/
@ -67,11 +69,8 @@
" MPU_xTaskDelayUntil_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskDelayUntilImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskDelayUntil ) : "memory"
);
}
@ -99,11 +98,8 @@
" MPU_xTaskAbortDelay_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskAbortDelayImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskAbortDelay ) : "memory"
);
}
@ -131,11 +127,8 @@
" MPU_vTaskDelay_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vTaskDelayImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vTaskDelay ) : "memory"
);
}
@ -163,11 +156,8 @@
" MPU_uxTaskPriorityGet_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_uxTaskPriorityGetImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_uxTaskPriorityGet ) : "memory"
);
}
@ -195,11 +185,8 @@
" MPU_eTaskGetState_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_eTaskGetStateImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_eTaskGetState ) : "memory"
);
}
@ -233,11 +220,8 @@
" MPU_vTaskGetInfo_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vTaskGetInfoImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vTaskGetInfo ) : "memory"
);
}
@ -265,11 +249,8 @@
" MPU_xTaskGetIdleTaskHandle_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskGetIdleTaskHandleImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskGetIdleTaskHandle ) : "memory"
);
}
@ -297,11 +278,8 @@
" MPU_vTaskSuspend_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vTaskSuspendImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vTaskSuspend ) : "memory"
);
}
@ -329,11 +307,8 @@
" MPU_vTaskResume_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vTaskResumeImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vTaskResume ) : "memory"
);
}
@ -359,11 +334,8 @@
" MPU_xTaskGetTickCount_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskGetTickCountImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskGetTickCount ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -387,11 +359,8 @@
" MPU_uxTaskGetNumberOfTasks_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_uxTaskGetNumberOfTasksImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_uxTaskGetNumberOfTasks ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -417,11 +386,8 @@
" MPU_ulTaskGetRunTimeCounter_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_ulTaskGetRunTimeCounterImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_ulTaskGetRunTimeCounter ) : "memory"
);
}
@ -449,11 +415,8 @@
" MPU_ulTaskGetRunTimePercent_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_ulTaskGetRunTimePercentImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_ulTaskGetRunTimePercent ) : "memory"
);
}
@ -481,11 +444,8 @@
" MPU_ulTaskGetIdleRunTimePercent_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_ulTaskGetIdleRunTimePercentImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_ulTaskGetIdleRunTimePercent ) : "memory"
);
}
@ -513,11 +473,8 @@
" MPU_ulTaskGetIdleRunTimeCounter_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_ulTaskGetIdleRunTimeCounterImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_ulTaskGetIdleRunTimeCounter ) : "memory"
);
}
@ -547,11 +504,8 @@
" MPU_vTaskSetApplicationTaskTag_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vTaskSetApplicationTaskTagImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vTaskSetApplicationTaskTag ) : "memory"
);
}
@ -579,11 +533,8 @@
" MPU_xTaskGetApplicationTaskTag_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskGetApplicationTaskTagImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskGetApplicationTaskTag ) : "memory"
);
}
@ -615,11 +566,8 @@
" MPU_vTaskSetThreadLocalStoragePointer_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vTaskSetThreadLocalStoragePointerImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vTaskSetThreadLocalStoragePointer ) : "memory"
);
}
@ -649,11 +597,8 @@
" MPU_pvTaskGetThreadLocalStoragePointer_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_pvTaskGetThreadLocalStoragePointerImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_pvTaskGetThreadLocalStoragePointer ) : "memory"
);
}
@ -685,11 +630,8 @@
" MPU_uxTaskGetSystemState_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_uxTaskGetSystemStateImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_uxTaskGetSystemState ) : "memory"
);
}
@ -717,11 +659,8 @@
" MPU_uxTaskGetStackHighWaterMark_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_uxTaskGetStackHighWaterMarkImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_uxTaskGetStackHighWaterMark ) : "memory"
);
}
@ -749,11 +688,8 @@
" MPU_uxTaskGetStackHighWaterMark2_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_uxTaskGetStackHighWaterMark2Impl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_uxTaskGetStackHighWaterMark2 ) : "memory"
);
}
@ -781,11 +717,8 @@
" MPU_xTaskGetCurrentTaskHandle_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskGetCurrentTaskHandleImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskGetCurrentTaskHandle ) : "memory"
);
}
@ -813,11 +746,8 @@
" MPU_xTaskGetSchedulerState_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskGetSchedulerStateImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskGetSchedulerState ) : "memory"
);
}
@ -843,11 +773,8 @@
" MPU_vTaskSetTimeOutState_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vTaskSetTimeOutStateImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vTaskSetTimeOutState ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -873,28 +800,17 @@
" MPU_xTaskCheckForTimeOut_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskCheckForTimeOutImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskCheckForTimeOut ) : "memory"
);
}
/*-----------------------------------------------------------*/
#if ( configUSE_TASK_NOTIFICATIONS == 1 )
BaseType_t MPU_xTaskGenericNotify( TaskHandle_t xTaskToNotify,
UBaseType_t uxIndexToNotify,
uint32_t ulValue,
eNotifyAction eAction,
uint32_t * pulPreviousNotificationValue ) __attribute__( ( naked ) ) FREERTOS_SYSTEM_CALL;
BaseType_t MPU_xTaskGenericNotifyEntry( const xTaskGenericNotifyParams_t * pxParams ) __attribute__( ( naked ) ) FREERTOS_SYSTEM_CALL;
BaseType_t MPU_xTaskGenericNotify( TaskHandle_t xTaskToNotify,
UBaseType_t uxIndexToNotify,
uint32_t ulValue,
eNotifyAction eAction,
uint32_t * pulPreviousNotificationValue ) /* __attribute__ (( naked )) FREERTOS_SYSTEM_CALL */
BaseType_t MPU_xTaskGenericNotifyEntry( const xTaskGenericNotifyParams_t * pxParams ) /* __attribute__ (( naked )) FREERTOS_SYSTEM_CALL */
{
__asm volatile
(
@ -911,11 +827,8 @@
" MPU_xTaskGenericNotify_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskGenericNotifyImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER_1 ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskGenericNotify ) : "memory"
);
}
@ -924,17 +837,9 @@
#if ( configUSE_TASK_NOTIFICATIONS == 1 )
BaseType_t MPU_xTaskGenericNotifyWait( UBaseType_t uxIndexToWaitOn,
uint32_t ulBitsToClearOnEntry,
uint32_t ulBitsToClearOnExit,
uint32_t * pulNotificationValue,
TickType_t xTicksToWait ) __attribute__( ( naked ) ) FREERTOS_SYSTEM_CALL;
BaseType_t MPU_xTaskGenericNotifyWaitEntry( const xTaskGenericNotifyWaitParams_t * pxParams ) __attribute__( ( naked ) ) FREERTOS_SYSTEM_CALL;
BaseType_t MPU_xTaskGenericNotifyWait( UBaseType_t uxIndexToWaitOn,
uint32_t ulBitsToClearOnEntry,
uint32_t ulBitsToClearOnExit,
uint32_t * pulNotificationValue,
TickType_t xTicksToWait ) /* __attribute__ (( naked )) FREERTOS_SYSTEM_CALL */
BaseType_t MPU_xTaskGenericNotifyWaitEntry( const xTaskGenericNotifyWaitParams_t * pxParams ) /* __attribute__ (( naked )) FREERTOS_SYSTEM_CALL */
{
__asm volatile
(
@ -951,11 +856,8 @@
" MPU_xTaskGenericNotifyWait_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskGenericNotifyWaitImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER_1 ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskGenericNotifyWait ) : "memory"
);
}
@ -987,11 +889,8 @@
" MPU_ulTaskGenericNotifyTake_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_ulTaskGenericNotifyTakeImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_ulTaskGenericNotifyTake ) : "memory"
);
}
@ -1021,11 +920,8 @@
" MPU_xTaskGenericNotifyStateClear_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTaskGenericNotifyStateClearImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTaskGenericNotifyStateClear ) : "memory"
);
}
@ -1057,11 +953,8 @@
" MPU_ulTaskGenericNotifyValueClear_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_ulTaskGenericNotifyValueClearImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_ulTaskGenericNotifyValueClear ) : "memory"
);
}
@ -1093,11 +986,8 @@
" MPU_xQueueGenericSend_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xQueueGenericSendImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xQueueGenericSend ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -1121,11 +1011,8 @@
" MPU_uxQueueMessagesWaiting_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_uxQueueMessagesWaitingImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_uxQueueMessagesWaiting ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -1149,11 +1036,8 @@
" MPU_uxQueueSpacesAvailable_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_uxQueueSpacesAvailableImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_uxQueueSpacesAvailable ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -1181,11 +1065,8 @@
" MPU_xQueueReceive_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xQueueReceiveImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xQueueReceive ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -1213,11 +1094,8 @@
" MPU_xQueuePeek_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xQueuePeekImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xQueuePeek ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -1243,11 +1121,8 @@
" MPU_xQueueSemaphoreTake_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xQueueSemaphoreTakeImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xQueueSemaphoreTake ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -1273,11 +1148,8 @@
" MPU_xQueueGetMutexHolder_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xQueueGetMutexHolderImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xQueueGetMutexHolder ) : "memory"
);
}
@ -1307,11 +1179,8 @@
" MPU_xQueueTakeMutexRecursive_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xQueueTakeMutexRecursiveImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xQueueTakeMutexRecursive ) : "memory"
);
}
@ -1339,11 +1208,8 @@
" MPU_xQueueGiveMutexRecursive_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xQueueGiveMutexRecursiveImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xQueueGiveMutexRecursive ) : "memory"
);
}
@ -1373,11 +1239,8 @@
" MPU_xQueueSelectFromSet_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xQueueSelectFromSetImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xQueueSelectFromSet ) : "memory"
);
}
@ -1407,11 +1270,8 @@
" MPU_xQueueAddToSet_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xQueueAddToSetImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xQueueAddToSet ) : "memory"
);
}
@ -1441,11 +1301,8 @@
" MPU_vQueueAddToRegistry_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vQueueAddToRegistryImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vQueueAddToRegistry ) : "memory"
);
}
@ -1473,11 +1330,8 @@
" MPU_vQueueUnregisterQueue_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vQueueUnregisterQueueImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vQueueUnregisterQueue ) : "memory"
);
}
@ -1505,11 +1359,8 @@
" MPU_pcQueueGetName_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_pcQueueGetNameImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_pcQueueGetName ) : "memory"
);
}
@ -1537,11 +1388,8 @@
" MPU_pvTimerGetTimerID_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_pvTimerGetTimerIDImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_pvTimerGetTimerID ) : "memory"
);
}
@ -1571,11 +1419,8 @@
" MPU_vTimerSetTimerID_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vTimerSetTimerIDImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vTimerSetTimerID ) : "memory"
);
}
@ -1603,11 +1448,8 @@
" MPU_xTimerIsTimerActive_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTimerIsTimerActiveImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTimerIsTimerActive ) : "memory"
);
}
@ -1635,11 +1477,8 @@
" MPU_xTimerGetTimerDaemonTaskHandle_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTimerGetTimerDaemonTaskHandleImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTimerGetTimerDaemonTaskHandle ) : "memory"
);
}
@ -1648,17 +1487,9 @@
#if ( configUSE_TIMERS == 1 )
BaseType_t MPU_xTimerGenericCommandFromTask( TimerHandle_t xTimer,
const BaseType_t xCommandID,
const TickType_t xOptionalValue,
BaseType_t * const pxHigherPriorityTaskWoken,
const TickType_t xTicksToWait ) __attribute__( ( naked ) ) FREERTOS_SYSTEM_CALL;
BaseType_t MPU_xTimerGenericCommandFromTaskEntry( const xTimerGenericCommandFromTaskParams_t * pxParams ) __attribute__( ( naked ) ) FREERTOS_SYSTEM_CALL;
BaseType_t MPU_xTimerGenericCommandFromTask( TimerHandle_t xTimer,
const BaseType_t xCommandID,
const TickType_t xOptionalValue,
BaseType_t * const pxHigherPriorityTaskWoken,
const TickType_t xTicksToWait ) /* __attribute__ (( naked )) FREERTOS_SYSTEM_CALL */
BaseType_t MPU_xTimerGenericCommandFromTaskEntry( const xTimerGenericCommandFromTaskParams_t * pxParams ) /* __attribute__ (( naked )) FREERTOS_SYSTEM_CALL */
{
__asm volatile
(
@ -1675,11 +1506,8 @@
" MPU_xTimerGenericCommandFromTask_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTimerGenericCommandFromTaskImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER_1 ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTimerGenericCommandFromTask ) : "memory"
);
}
@ -1707,11 +1535,8 @@
" MPU_pcTimerGetName_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_pcTimerGetNameImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_pcTimerGetName ) : "memory"
);
}
@ -1741,11 +1566,8 @@
" MPU_vTimerSetReloadMode_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vTimerSetReloadModeImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vTimerSetReloadMode ) : "memory"
);
}
@ -1773,11 +1595,8 @@
" MPU_xTimerGetReloadMode_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTimerGetReloadModeImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTimerGetReloadMode ) : "memory"
);
}
@ -1805,11 +1624,8 @@
" MPU_uxTimerGetReloadMode_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_uxTimerGetReloadModeImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_uxTimerGetReloadMode ) : "memory"
);
}
@ -1837,11 +1653,8 @@
" MPU_xTimerGetPeriod_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTimerGetPeriodImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTimerGetPeriod ) : "memory"
);
}
@ -1869,28 +1682,17 @@
" MPU_xTimerGetExpiryTime_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xTimerGetExpiryTimeImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xTimerGetExpiryTime ) : "memory"
);
}
#endif /* if ( configUSE_TIMERS == 1 ) */
/*-----------------------------------------------------------*/
EventBits_t MPU_xEventGroupWaitBits( EventGroupHandle_t xEventGroup,
const EventBits_t uxBitsToWaitFor,
const BaseType_t xClearOnExit,
const BaseType_t xWaitForAllBits,
TickType_t xTicksToWait ) __attribute__( ( naked ) ) FREERTOS_SYSTEM_CALL;
EventBits_t MPU_xEventGroupWaitBitsEntry( const xEventGroupWaitBitsParams_t * pxParams ) __attribute__( ( naked ) ) FREERTOS_SYSTEM_CALL;
EventBits_t MPU_xEventGroupWaitBits( EventGroupHandle_t xEventGroup,
const EventBits_t uxBitsToWaitFor,
const BaseType_t xClearOnExit,
const BaseType_t xWaitForAllBits,
TickType_t xTicksToWait ) /* __attribute__ (( naked )) FREERTOS_SYSTEM_CALL */
EventBits_t MPU_xEventGroupWaitBitsEntry( const xEventGroupWaitBitsParams_t * pxParams ) /* __attribute__ (( naked )) FREERTOS_SYSTEM_CALL */
{
__asm volatile
(
@ -1907,11 +1709,8 @@
" MPU_xEventGroupWaitBits_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xEventGroupWaitBitsImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER_1 ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xEventGroupWaitBits ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -1937,11 +1736,8 @@
" MPU_xEventGroupClearBits_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xEventGroupClearBitsImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xEventGroupClearBits ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -1967,11 +1763,8 @@
" MPU_xEventGroupSetBits_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xEventGroupSetBitsImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xEventGroupSetBits ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -2001,11 +1794,8 @@
" MPU_xEventGroupSync_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xEventGroupSyncImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xEventGroupSync ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -2031,11 +1821,8 @@
" MPU_uxEventGroupGetNumber_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_uxEventGroupGetNumberImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_uxEventGroupGetNumber ) : "memory"
);
}
@ -2065,11 +1852,8 @@
" MPU_vEventGroupSetNumber_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_vEventGroupSetNumberImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_vEventGroupSetNumber ) : "memory"
);
}
@ -2101,11 +1885,8 @@
" MPU_xStreamBufferSend_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xStreamBufferSendImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xStreamBufferSend ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -2135,11 +1916,8 @@
" MPU_xStreamBufferReceive_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xStreamBufferReceiveImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xStreamBufferReceive ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -2163,11 +1941,8 @@
" MPU_xStreamBufferIsFull_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xStreamBufferIsFullImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xStreamBufferIsFull ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -2191,11 +1966,8 @@
" MPU_xStreamBufferIsEmpty_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xStreamBufferIsEmptyImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xStreamBufferIsEmpty ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -2219,11 +1991,8 @@
" MPU_xStreamBufferSpacesAvailable_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xStreamBufferSpacesAvailableImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xStreamBufferSpacesAvailable ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -2247,11 +2016,8 @@
" MPU_xStreamBufferBytesAvailable_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xStreamBufferBytesAvailableImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xStreamBufferBytesAvailable ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -2277,11 +2043,8 @@
" MPU_xStreamBufferSetTriggerLevel_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xStreamBufferSetTriggerLevelImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xStreamBufferSetTriggerLevel ) : "memory"
);
}
/*-----------------------------------------------------------*/
@ -2305,11 +2068,8 @@
" MPU_xStreamBufferNextMessageLengthBytes_Unpriv: \n"
" pop {r0} \n"
" svc %0 \n"
" bl MPU_xStreamBufferNextMessageLengthBytesImpl \n"
" svc %1 \n"
" bx lr \n"
" \n"
: : "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory"
: : "i" ( SYSTEM_CALL_xStreamBufferNextMessageLengthBytes ) : "memory"
);
}
/*-----------------------------------------------------------*/

View file

@ -35,8 +35,9 @@
#include "FreeRTOS.h"
#include "task.h"
/* MPU wrappers includes. */
/* MPU includes. */
#include "mpu_wrappers.h"
#include "mpu_syscall_numbers.h"
/* Portasm includes. */
#include "portasm.h"
@ -436,29 +437,22 @@ portDONT_DISCARD void vPortSVCHandler_C( uint32_t * pulCallerStackAddress ) PRIV
* @brief Sets up the system call stack so that upon returning from
* SVC, the system call stack is used.
*
* It is used for the system calls with up to 4 parameters.
*
* @param pulTaskStack The current SP when the SVC was raised.
* @param ulLR The value of Link Register (EXC_RETURN) in the SVC handler.
* @param ucSystemCallNumber The system call number of the system call.
*/
void vSystemCallEnter( uint32_t * pulTaskStack,
uint32_t ulLR ) PRIVILEGED_FUNCTION;
uint32_t ulLR,
uint8_t ucSystemCallNumber ) PRIVILEGED_FUNCTION;
#endif /* ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) */
#if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) )
/**
* @brief Sets up the system call stack so that upon returning from
* SVC, the system call stack is used.
*
* It is used for the system calls with 5 parameters.
*
* @param pulTaskStack The current SP when the SVC was raised.
* @param ulLR The value of Link Register (EXC_RETURN) in the SVC handler.
* @brief Raise SVC for exiting from a system call.
*/
void vSystemCallEnter_1( uint32_t * pulTaskStack,
uint32_t ulLR ) PRIVILEGED_FUNCTION;
void vRequestSystemCallExit( void ) __attribute__( ( naked ) ) PRIVILEGED_FUNCTION;
#endif /* ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) */
@ -488,6 +482,15 @@ portDONT_DISCARD void vPortSVCHandler_C( uint32_t * pulCallerStackAddress ) PRIV
#endif /* configENABLE_MPU == 1 */
/*-----------------------------------------------------------*/
#if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) )
/**
* @brief This variable is set to pdTRUE when the scheduler is started.
*/
PRIVILEGED_DATA static BaseType_t xSchedulerRunning = pdFALSE;
#endif
/**
* @brief Each task maintains its own interrupt status in the critical nesting
* variable.
@ -1134,15 +1137,16 @@ void vPortSVCHandler_C( uint32_t * pulCallerStackAddress ) /* PRIVILEGED_FUNCTIO
#if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) )
void vSystemCallEnter( uint32_t * pulTaskStack,
uint32_t ulLR ) /* PRIVILEGED_FUNCTION */
uint32_t ulLR,
uint8_t ucSystemCallNumber ) /* PRIVILEGED_FUNCTION */
{
extern TaskHandle_t pxCurrentTCB;
extern UBaseType_t uxSystemCallImplementations[ NUM_SYSTEM_CALLS ];
xMPU_SETTINGS * pxMpuSettings;
uint32_t * pulSystemCallStack;
uint32_t ulStackFrameSize, ulSystemCallLocation, i;
#if defined( __ARMCC_VERSION )
/* Declaration when these variable are defined in code instead of being
* exported from linker scripts. */
extern uint32_t * __syscalls_flash_start__;
@ -1154,17 +1158,27 @@ void vPortSVCHandler_C( uint32_t * pulCallerStackAddress ) /* PRIVILEGED_FUNCTIO
#endif /* #if defined( __ARMCC_VERSION ) */
ulSystemCallLocation = pulTaskStack[ portOFFSET_TO_PC ];
pxMpuSettings = xTaskGetMPUSettings( pxCurrentTCB );
/* If the request did not come from the system call section, do nothing. */
/* Checks:
* 1. SVC is raised from the system call section (i.e. application is
* not raising SVC directly).
* 2. pxMpuSettings->xSystemCallStackInfo.pulTaskStack must be NULL as
* it is non-NULL only during the execution of a system call (i.e.
* between system call enter and exit).
* 3. System call is not for a kernel API disabled by the configuration
* in FreeRTOSConfig.h.
* 4. We do not need to check that ucSystemCallNumber is within range
* because the assembly SVC handler checks that before calling
* this function.
*/
if( ( ulSystemCallLocation >= ( uint32_t ) __syscalls_flash_start__ ) &&
( ulSystemCallLocation <= ( uint32_t ) __syscalls_flash_end__ ) )
( ulSystemCallLocation <= ( uint32_t ) __syscalls_flash_end__ ) &&
( pxMpuSettings->xSystemCallStackInfo.pulTaskStack == NULL ) &&
( uxSystemCallImplementations[ ucSystemCallNumber ] != ( UBaseType_t ) 0 ) )
{
pxMpuSettings = xTaskGetMPUSettings( pxCurrentTCB );
pulSystemCallStack = pxMpuSettings->xSystemCallStackInfo.pulSystemCallStack;
/* This is not NULL only for the duration of the system call. */
configASSERT( pxMpuSettings->xSystemCallStackInfo.pulTaskStack == NULL );
#if ( ( configENABLE_FPU == 1 ) || ( configENABLE_MVE == 1 ) )
{
if( ( ulLR & portEXC_RETURN_STACK_FRAME_TYPE_MASK ) == 0UL )
@ -1198,9 +1212,13 @@ void vPortSVCHandler_C( uint32_t * pulCallerStackAddress ) /* PRIVILEGED_FUNCTIO
pulSystemCallStack[ i ] = pulTaskStack[ i ];
}
/* Store the value of the LR and PSPLIM registers before the SVC was raised. We need to
* restore it when we exit from the system call. */
/* Store the value of the Link Register before the SVC was raised.
* It contains the address of the caller of the System Call entry
* point (i.e. the caller of the MPU_<API>). We need to restore it
* when we exit from the system call. */
pxMpuSettings->xSystemCallStackInfo.ulLinkRegisterAtSystemCallEntry = pulTaskStack[ portOFFSET_TO_LR ];
/* Store the value of the PSPLIM register before the SVC was raised.
* We need to restore it when we exit from the system call. */
#if ( portUSE_PSPLIM_REGISTER == 1 )
{
__asm volatile ( "mrs %0, psplim" : "=r" ( pxMpuSettings->xSystemCallStackInfo.ulStackLimitRegisterAtSystemCallEntry ) );
@ -1215,6 +1233,12 @@ void vPortSVCHandler_C( uint32_t * pulCallerStackAddress ) /* PRIVILEGED_FUNCTIO
}
#endif
/* Start executing the system call upon returning from this handler. */
pulSystemCallStack[ portOFFSET_TO_PC ] = uxSystemCallImplementations[ ucSystemCallNumber ];
/* Raise a request to exit from the system call upon finishing the
* system call. */
pulSystemCallStack[ portOFFSET_TO_LR ] = ( uint32_t ) vRequestSystemCallExit;
/* Remember the location where we should copy the stack frame when we exit from
* the system call. */
pxMpuSettings->xSystemCallStackInfo.pulTaskStack = pulTaskStack + ulStackFrameSize;
@ -1251,127 +1275,9 @@ void vPortSVCHandler_C( uint32_t * pulCallerStackAddress ) /* PRIVILEGED_FUNCTIO
#if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) )
void vSystemCallEnter_1( uint32_t * pulTaskStack,
uint32_t ulLR ) /* PRIVILEGED_FUNCTION */
void vRequestSystemCallExit( void ) /* __attribute__( ( naked ) ) PRIVILEGED_FUNCTION */
{
extern TaskHandle_t pxCurrentTCB;
xMPU_SETTINGS * pxMpuSettings;
uint32_t * pulSystemCallStack;
uint32_t ulStackFrameSize, ulSystemCallLocation, i;
#if defined( __ARMCC_VERSION )
/* Declaration when these variable are defined in code instead of being
* exported from linker scripts. */
extern uint32_t * __syscalls_flash_start__;
extern uint32_t * __syscalls_flash_end__;
#else
/* Declaration when these variable are exported from linker scripts. */
extern uint32_t __syscalls_flash_start__[];
extern uint32_t __syscalls_flash_end__[];
#endif /* #if defined( __ARMCC_VERSION ) */
ulSystemCallLocation = pulTaskStack[ portOFFSET_TO_PC ];
/* If the request did not come from the system call section, do nothing. */
if( ( ulSystemCallLocation >= ( uint32_t ) __syscalls_flash_start__ ) &&
( ulSystemCallLocation <= ( uint32_t ) __syscalls_flash_end__ ) )
{
pxMpuSettings = xTaskGetMPUSettings( pxCurrentTCB );
pulSystemCallStack = pxMpuSettings->xSystemCallStackInfo.pulSystemCallStack;
/* This is not NULL only for the duration of the system call. */
configASSERT( pxMpuSettings->xSystemCallStackInfo.pulTaskStack == NULL );
#if ( ( configENABLE_FPU == 1 ) || ( configENABLE_MVE == 1 ) )
{
if( ( ulLR & portEXC_RETURN_STACK_FRAME_TYPE_MASK ) == 0UL )
{
/* Extended frame i.e. FPU in use. */
ulStackFrameSize = 26;
__asm volatile (
" vpush {s0} \n" /* Trigger lazy stacking. */
" vpop {s0} \n" /* Nullify the affect of the above instruction. */
::: "memory"
);
}
else
{
/* Standard frame i.e. FPU not in use. */
ulStackFrameSize = 8;
}
}
#else /* if ( ( configENABLE_FPU == 1 ) || ( configENABLE_MVE == 1 ) ) */
{
ulStackFrameSize = 8;
}
#endif /* configENABLE_FPU || configENABLE_MVE */
/* Make space on the system call stack for the stack frame and
* the parameter passed on the stack. We only need to copy one
* parameter but we still reserve 2 spaces to keep the stack
* double word aligned. */
pulSystemCallStack = pulSystemCallStack - ulStackFrameSize - 2UL;
/* Copy the stack frame. */
for( i = 0; i < ulStackFrameSize; i++ )
{
pulSystemCallStack[ i ] = pulTaskStack[ i ];
}
/* Copy the parameter which is passed the stack. */
if( ( pulTaskStack[ portOFFSET_TO_PSR ] & portPSR_STACK_PADDING_MASK ) == portPSR_STACK_PADDING_MASK )
{
pulSystemCallStack[ ulStackFrameSize ] = pulTaskStack[ ulStackFrameSize + 1 ];
/* Record if the hardware used padding to force the stack pointer
* to be double word aligned. */
pxMpuSettings->ulTaskFlags |= portSTACK_FRAME_HAS_PADDING_FLAG;
}
else
{
pulSystemCallStack[ ulStackFrameSize ] = pulTaskStack[ ulStackFrameSize ];
/* Record if the hardware used padding to force the stack pointer
* to be double word aligned. */
pxMpuSettings->ulTaskFlags &= ( ~portSTACK_FRAME_HAS_PADDING_FLAG );
}
/* Store the value of the LR and PSPLIM registers before the SVC was raised.
* We need to restore it when we exit from the system call. */
pxMpuSettings->xSystemCallStackInfo.ulLinkRegisterAtSystemCallEntry = pulTaskStack[ portOFFSET_TO_LR ];
#if ( portUSE_PSPLIM_REGISTER == 1 )
{
__asm volatile ( "mrs %0, psplim" : "=r" ( pxMpuSettings->xSystemCallStackInfo.ulStackLimitRegisterAtSystemCallEntry ) );
}
#endif
/* Use the pulSystemCallStack in thread mode. */
__asm volatile ( "msr psp, %0" : : "r" ( pulSystemCallStack ) );
#if ( portUSE_PSPLIM_REGISTER == 1 )
{
__asm volatile ( "msr psplim, %0" : : "r" ( pxMpuSettings->xSystemCallStackInfo.pulSystemCallStackLimit ) );
}
#endif
/* Remember the location where we should copy the stack frame when we exit from
* the system call. */
pxMpuSettings->xSystemCallStackInfo.pulTaskStack = pulTaskStack + ulStackFrameSize;
/* We ensure in pxPortInitialiseStack that the system call stack is
* double word aligned and therefore, there is no need of padding.
* Clear the bit[9] of stacked xPSR. */
pulSystemCallStack[ portOFFSET_TO_PSR ] &= ( ~portPSR_STACK_PADDING_MASK );
/* Raise the privilege for the duration of the system call. */
__asm volatile (
" mrs r0, control \n" /* Obtain current control value. */
" movs r1, #1 \n" /* r1 = 1. */
" bics r0, r1 \n" /* Clear nPRIV bit. */
" msr control, r0 \n" /* Write back new control value. */
::: "r0", "r1", "memory"
);
}
__asm volatile ( "svc %0 \n" ::"i" ( portSVC_SYSTEM_CALL_EXIT ) : "memory" );
}
#endif /* ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) */
@ -1388,24 +1294,32 @@ void vPortSVCHandler_C( uint32_t * pulCallerStackAddress ) /* PRIVILEGED_FUNCTIO
uint32_t ulStackFrameSize, ulSystemCallLocation, i;
#if defined( __ARMCC_VERSION )
/* Declaration when these variable are defined in code instead of being
* exported from linker scripts. */
extern uint32_t * __syscalls_flash_start__;
extern uint32_t * __syscalls_flash_end__;
extern uint32_t * __privileged_functions_start__;
extern uint32_t * __privileged_functions_end__;
#else
/* Declaration when these variable are exported from linker scripts. */
extern uint32_t __syscalls_flash_start__[];
extern uint32_t __syscalls_flash_end__[];
extern uint32_t __privileged_functions_start__[];
extern uint32_t __privileged_functions_end__[];
#endif /* #if defined( __ARMCC_VERSION ) */
ulSystemCallLocation = pulSystemCallStack[ portOFFSET_TO_PC ];
pxMpuSettings = xTaskGetMPUSettings( pxCurrentTCB );
/* If the request did not come from the system call section, do nothing. */
if( ( ulSystemCallLocation >= ( uint32_t ) __syscalls_flash_start__ ) &&
( ulSystemCallLocation <= ( uint32_t ) __syscalls_flash_end__ ) )
/* Checks:
* 1. SVC is raised from the privileged code (i.e. application is not
* raising SVC directly). This SVC is only raised from
* vRequestSystemCallExit which is in the privileged code section.
* 2. pxMpuSettings->xSystemCallStackInfo.pulTaskStack must not be NULL -
* this means that we previously entered a system call and the
* application is not attempting to exit without entering a system
* call.
*/
if( ( ulSystemCallLocation >= ( uint32_t ) __privileged_functions_start__ ) &&
( ulSystemCallLocation <= ( uint32_t ) __privileged_functions_end__ ) &&
( pxMpuSettings->xSystemCallStackInfo.pulTaskStack != NULL ) )
{
pxMpuSettings = xTaskGetMPUSettings( pxCurrentTCB );
pulTaskStack = pxMpuSettings->xSystemCallStackInfo.pulTaskStack;
#if ( ( configENABLE_FPU == 1 ) || ( configENABLE_MVE == 1 ) )
@ -1444,9 +1358,14 @@ void vPortSVCHandler_C( uint32_t * pulCallerStackAddress ) /* PRIVILEGED_FUNCTIO
/* Use the pulTaskStack in thread mode. */
__asm volatile ( "msr psp, %0" : : "r" ( pulTaskStack ) );
/* Restore the LR and PSPLIM to what they were at the time of
* system call entry. */
/* Return to the caller of the System Call entry point (i.e. the
* caller of the MPU_<API>). */
pulTaskStack[ portOFFSET_TO_PC ] = pxMpuSettings->xSystemCallStackInfo.ulLinkRegisterAtSystemCallEntry;
/* Ensure that LR has a valid value.*/
pulTaskStack[ portOFFSET_TO_LR ] = pxMpuSettings->xSystemCallStackInfo.ulLinkRegisterAtSystemCallEntry;
/* Restore the PSPLIM register to what it was at the time of
* system call entry. */
#if ( portUSE_PSPLIM_REGISTER == 1 )
{
__asm volatile ( "msr psplim, %0" : : "r" ( pxMpuSettings->xSystemCallStackInfo.ulStackLimitRegisterAtSystemCallEntry ) );
@ -1780,6 +1699,12 @@ BaseType_t xPortStartScheduler( void ) /* PRIVILEGED_FUNCTION */
/* Initialize the critical nesting count ready for the first task. */
ulCriticalNesting = 0;
#if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) )
{
xSchedulerRunning = pdTRUE;
}
#endif
/* Start the first task. */
vStartFirstTask();
@ -2062,7 +1987,7 @@ BaseType_t xPortIsInsideInterrupt( void )
#endif /* #if ( ( configASSERT_DEFINED == 1 ) && ( portHAS_ARMV8M_MAIN_EXTENSION == 1 ) ) */
/*-----------------------------------------------------------*/
#if ( ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) )
#if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) )
void vPortGrantAccessToKernelObject( TaskHandle_t xInternalTaskHandle,
int32_t lInternalIndexOfKernelObject ) /* PRIVILEGED_FUNCTION */
@ -2078,10 +2003,10 @@ BaseType_t xPortIsInsideInterrupt( void )
xTaskMpuSettings->ulAccessControlList[ ulAccessControlListEntryIndex ] |= ( 1U << ulAccessControlListEntryBit );
}
#endif /* #if ( ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) ) */
#endif /* #if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) ) */
/*-----------------------------------------------------------*/
#if ( ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) )
#if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) )
void vPortRevokeAccessToKernelObject( TaskHandle_t xInternalTaskHandle,
int32_t lInternalIndexOfKernelObject ) /* PRIVILEGED_FUNCTION */
@ -2097,10 +2022,10 @@ BaseType_t xPortIsInsideInterrupt( void )
xTaskMpuSettings->ulAccessControlList[ ulAccessControlListEntryIndex ] &= ~( 1U << ulAccessControlListEntryBit );
}
#endif /* #if ( ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) ) */
#endif /* #if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) && ( configENABLE_ACCESS_CONTROL_LIST == 1 ) ) */
/*-----------------------------------------------------------*/
#if ( configUSE_MPU_WRAPPERS_V1 == 0 )
#if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) )
#if ( configENABLE_ACCESS_CONTROL_LIST == 1 )
@ -2108,21 +2033,34 @@ BaseType_t xPortIsInsideInterrupt( void )
{
uint32_t ulAccessControlListEntryIndex, ulAccessControlListEntryBit;
BaseType_t xAccessGranted = pdFALSE;
const xMPU_SETTINGS * xTaskMpuSettings = xTaskGetMPUSettings( NULL ); /* Calling task's MPU settings. */
const xMPU_SETTINGS * xTaskMpuSettings;
ulAccessControlListEntryIndex = ( ( uint32_t ) lInternalIndexOfKernelObject / portACL_ENTRY_SIZE_BITS );
ulAccessControlListEntryBit = ( ( uint32_t ) lInternalIndexOfKernelObject % portACL_ENTRY_SIZE_BITS );
if( ( xTaskMpuSettings->ulTaskFlags & portTASK_IS_PRIVILEGED_FLAG ) == portTASK_IS_PRIVILEGED_FLAG )
if( xSchedulerRunning == pdFALSE )
{
/* Grant access to all the kernel objects before the scheduler
* is started. It is necessary because there is no task running
* yet and therefore, we cannot use the permissions of any
* task. */
xAccessGranted = pdTRUE;
}
else
{
if( ( xTaskMpuSettings->ulAccessControlList[ ulAccessControlListEntryIndex ] & ( 1U << ulAccessControlListEntryBit ) ) != 0 )
xTaskMpuSettings = xTaskGetMPUSettings( NULL ); /* Calling task's MPU settings. */
ulAccessControlListEntryIndex = ( ( uint32_t ) lInternalIndexOfKernelObject / portACL_ENTRY_SIZE_BITS );
ulAccessControlListEntryBit = ( ( uint32_t ) lInternalIndexOfKernelObject % portACL_ENTRY_SIZE_BITS );
if( ( xTaskMpuSettings->ulTaskFlags & portTASK_IS_PRIVILEGED_FLAG ) == portTASK_IS_PRIVILEGED_FLAG )
{
xAccessGranted = pdTRUE;
}
else
{
if( ( xTaskMpuSettings->ulAccessControlList[ ulAccessControlListEntryIndex ] & ( 1U << ulAccessControlListEntryBit ) ) != 0 )
{
xAccessGranted = pdTRUE;
}
}
}
return xAccessGranted;
@ -2141,5 +2079,5 @@ BaseType_t xPortIsInsideInterrupt( void )
#endif /* #if ( configENABLE_ACCESS_CONTROL_LIST == 1 ) */
#endif /* #if ( configUSE_MPU_WRAPPERS_V1 == 0 ) */
#endif /* #if ( ( configENABLE_MPU == 1 ) && ( configUSE_MPU_WRAPPERS_V1 == 0 ) ) */
/*-----------------------------------------------------------*/

View file

@ -36,6 +36,9 @@
/* Portasm includes. */
#include "portasm.h"
/* System call numbers includes. */
#include "mpu_syscall_numbers.h"
/* MPU_WRAPPERS_INCLUDED_FROM_API_FILE is needed to be defined only for the
* header files. */
#undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE
@ -522,7 +525,6 @@ void vClearInterruptMask( __attribute__( ( unused ) ) uint32_t ulMask ) /* __att
".syntax unified \n"
".extern vPortSVCHandler_C \n"
".extern vSystemCallEnter \n"
".extern vSystemCallEnter_1 \n"
".extern vSystemCallExit \n"
" \n"
"tst lr, #4 \n"
@ -533,10 +535,8 @@ void vClearInterruptMask( __attribute__( ( unused ) ) uint32_t ulMask ) /* __att
"ldr r1, [r0, #24] \n"
"ldrb r2, [r1, #-2] \n"
"cmp r2, %0 \n"
"beq syscall_enter \n"
"blt syscall_enter \n"
"cmp r2, %1 \n"
"beq syscall_enter_1 \n"
"cmp r2, %2 \n"
"beq syscall_exit \n"
"b vPortSVCHandler_C \n"
" \n"
@ -544,16 +544,12 @@ void vClearInterruptMask( __attribute__( ( unused ) ) uint32_t ulMask ) /* __att
" mov r1, lr \n"
" b vSystemCallEnter \n"
" \n"
"syscall_enter_1: \n"
" mov r1, lr \n"
" b vSystemCallEnter_1 \n"
" \n"
"syscall_exit: \n"
" mov r1, lr \n"
" b vSystemCallExit \n"
" \n"
: /* No outputs. */
: "i" ( portSVC_SYSTEM_CALL_ENTER ), "i" ( portSVC_SYSTEM_CALL_ENTER_1 ), "i" ( portSVC_SYSTEM_CALL_EXIT )
: "i" ( NUM_SYSTEM_CALLS ), "i" ( portSVC_SYSTEM_CALL_EXIT )
: "r0", "r1", "r2", "memory"
);
}

View file

@ -322,14 +322,12 @@ extern void vClearInterruptMask( uint32_t ulMask ) /* __attribute__(( naked )) P
/**
* @brief SVC numbers.
*/
#define portSVC_ALLOCATE_SECURE_CONTEXT 0
#define portSVC_FREE_SECURE_CONTEXT 1
#define portSVC_START_SCHEDULER 2
#define portSVC_RAISE_PRIVILEGE 3
#define portSVC_SYSTEM_CALL_ENTER 4 /* System calls with upto 4 parameters. */
#define portSVC_SYSTEM_CALL_ENTER_1 5 /* System calls with 5 parameters. */
#define portSVC_SYSTEM_CALL_EXIT 6
#define portSVC_YIELD 7
#define portSVC_ALLOCATE_SECURE_CONTEXT 100
#define portSVC_FREE_SECURE_CONTEXT 101
#define portSVC_START_SCHEDULER 102
#define portSVC_RAISE_PRIVILEGE 103
#define portSVC_SYSTEM_CALL_EXIT 104
#define portSVC_YIELD 105
/*-----------------------------------------------------------*/
/**