@@ -488,7 +488,7 @@ PRIVILEGED_DATA static volatile TickType_t xTickCount = ( TickType_t ) configINI
488
488
PRIVILEGED_DATA static volatile UBaseType_t uxTopReadyPriority = tskIDLE_PRIORITY ;
489
489
PRIVILEGED_DATA static volatile BaseType_t xSchedulerRunning = pdFALSE ;
490
490
PRIVILEGED_DATA static volatile TickType_t xPendedTicks = ( TickType_t ) 0U ;
491
- PRIVILEGED_DATA static volatile BaseType_t xYieldPendings [ configNUMBER_OF_CORES ] = { pdFALSE };
491
+ PRIVILEGED_DATA volatile BaseType_t xYieldPendings [ configNUMBER_OF_CORES ] = { pdFALSE };
492
492
PRIVILEGED_DATA static volatile BaseType_t xNumOfOverflows = ( BaseType_t ) 0 ;
493
493
PRIVILEGED_DATA static UBaseType_t uxTaskNumber = ( UBaseType_t ) 0U ;
494
494
PRIVILEGED_DATA static volatile TickType_t xNextTaskUnblockTime = ( TickType_t ) 0U ; /* Initialised to portMAX_DELAY before the scheduler starts. */
@@ -522,6 +522,11 @@ PRIVILEGED_DATA static volatile configRUN_TIME_COUNTER_TYPE ulTotalRunTime[ conf
522
522
523
523
#endif
524
524
525
+ #if ( ( portUSING_GRANULAR_LOCKS == 1 ) && ( configNUMBER_OF_CORES > 1 ) )
526
+ PRIVILEGED_DATA static portSPINLOCK_TYPE xTaskSpinlock = portINIT_KERNEL_TASK_SPINLOCK_STATIC ;
527
+ PRIVILEGED_DATA static portSPINLOCK_TYPE xISRSpinlock = portINIT_KERNEL_ISR_SPINLOCK_STATIC ;
528
+ #endif /* #if ( ( portUSING_GRANULAR_LOCKS == 1 ) && ( configNUMBER_OF_CORES > 1 ) ) */
529
+
525
530
/*-----------------------------------------------------------*/
526
531
527
532
/* File private functions. --------------------------------*/
@@ -531,14 +536,14 @@ PRIVILEGED_DATA static volatile configRUN_TIME_COUNTER_TYPE ulTotalRunTime[ conf
531
536
*/
532
537
static BaseType_t prvCreateIdleTasks ( void );
533
538
534
- #if ( configNUMBER_OF_CORES > 1 )
539
+ #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) )
535
540
536
541
/*
537
542
* Checks to see if another task moved the current task out of the ready
538
543
* list while it was waiting to enter a critical section and yields, if so.
539
544
*/
540
545
static void prvCheckForRunStateChange ( void );
541
- #endif /* #if ( configNUMBER_OF_CORES > 1 ) */
546
+ #endif /* #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) ) */
542
547
543
548
#if ( configNUMBER_OF_CORES > 1 )
544
549
@@ -802,7 +807,7 @@ static void prvAddNewTaskToReadyList( TCB_t * pxNewTCB ) PRIVILEGED_FUNCTION;
802
807
#endif /* #if ( ( configUSE_TRACE_FACILITY == 1 ) && ( configUSE_STATS_FORMATTING_FUNCTIONS > 0 ) ) */
803
808
/*-----------------------------------------------------------*/
804
809
805
- #if ( configNUMBER_OF_CORES > 1 )
810
+ #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) )
806
811
static void prvCheckForRunStateChange ( void )
807
812
{
808
813
UBaseType_t uxPrevCriticalNesting ;
@@ -863,7 +868,7 @@ static void prvAddNewTaskToReadyList( TCB_t * pxNewTCB ) PRIVILEGED_FUNCTION;
863
868
}
864
869
}
865
870
}
866
- #endif /* #if ( configNUMBER_OF_CORES > 1 ) */
871
+ #endif /* #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) ) */
867
872
868
873
/*-----------------------------------------------------------*/
869
874
@@ -3871,26 +3876,45 @@ void vTaskSuspendAll( void )
3871
3876
* do not otherwise exhibit real time behaviour. */
3872
3877
portSOFTWARE_BARRIER ();
3873
3878
3874
- portGET_TASK_LOCK ();
3875
-
3876
- /* uxSchedulerSuspended is increased after prvCheckForRunStateChange. The
3877
- * purpose is to prevent altering the variable when fromISR APIs are readying
3878
- * it. */
3879
- if ( uxSchedulerSuspended == 0U )
3879
+ #if ( portUSING_GRANULAR_LOCKS == 1 )
3880
3880
{
3881
- prvCheckForRunStateChange ();
3881
+ portGET_SPINLOCK ( & xTaskSpinlock );
3882
+ portGET_SPINLOCK ( & xISRSpinlock );
3883
+
3884
+ /* Increment xPreemptionDisable to prevent preemption and also
3885
+ * track whether to yield in xTaskResumeAll(). */
3886
+ pxCurrentTCBs [ portGET_CORE_ID () ]-> xPreemptionDisable ++ ;
3887
+
3888
+ /* The scheduler is suspended if uxSchedulerSuspended is non-zero. An increment
3889
+ * is used to allow calls to vTaskSuspendAll() to nest. */
3890
+ ++ uxSchedulerSuspended ;
3891
+
3892
+ portRELEASE_SPINLOCK ( & xISRSpinlock );
3882
3893
}
3883
- else
3894
+ # else /* #if ( portUSING_GRANULAR_LOCKS == 1 ) */
3884
3895
{
3885
- mtCOVERAGE_TEST_MARKER ();
3886
- }
3896
+ portGET_TASK_LOCK ();
3887
3897
3888
- portGET_ISR_LOCK ();
3898
+ /* uxSchedulerSuspended is increased after prvCheckForRunStateChange. The
3899
+ * purpose is to prevent altering the variable when fromISR APIs are readying
3900
+ * it. */
3901
+ if ( uxSchedulerSuspended == 0U )
3902
+ {
3903
+ prvCheckForRunStateChange ();
3904
+ }
3905
+ else
3906
+ {
3907
+ mtCOVERAGE_TEST_MARKER ();
3908
+ }
3889
3909
3890
- /* The scheduler is suspended if uxSchedulerSuspended is non-zero. An increment
3891
- * is used to allow calls to vTaskSuspendAll() to nest. */
3892
- ++ uxSchedulerSuspended ;
3893
- portRELEASE_ISR_LOCK ();
3910
+ portGET_ISR_LOCK ();
3911
+
3912
+ /* The scheduler is suspended if uxSchedulerSuspended is non-zero. An increment
3913
+ * is used to allow calls to vTaskSuspendAll() to nest. */
3914
+ ++ uxSchedulerSuspended ;
3915
+ portRELEASE_ISR_LOCK ();
3916
+ }
3917
+ #endif /* #if ( portUSING_GRANULAR_LOCKS == 1 ) */
3894
3918
3895
3919
portCLEAR_INTERRUPT_MASK ( ulState );
3896
3920
}
@@ -3996,7 +4020,24 @@ BaseType_t xTaskResumeAll( void )
3996
4020
configASSERT ( uxSchedulerSuspended != 0U );
3997
4021
3998
4022
uxSchedulerSuspended = ( UBaseType_t ) ( uxSchedulerSuspended - 1U );
3999
- portRELEASE_TASK_LOCK ();
4023
+ #if ( ( portUSING_GRANULAR_LOCKS == 1 ) && ( configNUMBER_OF_CORES > 1 ) )
4024
+ {
4025
+ configASSERT ( pxCurrentTCBs [ portGET_CORE_ID () ]-> xPreemptionDisable > 0 );
4026
+
4027
+ /* Decrement xPreemptionDisable. If 0, it means this we are not
4028
+ * in a nested suspension scenario, thus this function and yield
4029
+ * if necessary. */
4030
+ pxCurrentTCBs [ portGET_CORE_ID () ]-> xPreemptionDisable -- ;
4031
+
4032
+ /* Release the kernel's task spinlock that was held throughout
4033
+ * the kernel suspension. */
4034
+ portRELEASE_SPINLOCK ( & xTaskSpinlock );
4035
+ }
4036
+ #else /* #if ( ( portUSING_GRANULAR_LOCKS == 1 ) && ( configNUMBER_OF_CORES > 1 ) ) */
4037
+ {
4038
+ portRELEASE_TASK_LOCK ();
4039
+ }
4040
+ #endif /* #if ( ( portUSING_GRANULAR_LOCKS == 1 ) && ( configNUMBER_OF_CORES > 1 ) ) */
4000
4041
4001
4042
if ( uxSchedulerSuspended == ( UBaseType_t ) 0U )
4002
4043
{
@@ -6968,7 +7009,7 @@ static void prvResetNextTaskUnblockTime( void )
6968
7009
#endif /* #if ( ( portCRITICAL_NESTING_IN_TCB == 1 ) && ( configNUMBER_OF_CORES == 1 ) ) */
6969
7010
/*-----------------------------------------------------------*/
6970
7011
6971
- #if ( configNUMBER_OF_CORES > 1 )
7012
+ #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) )
6972
7013
6973
7014
void vTaskEnterCritical ( void )
6974
7015
{
@@ -7014,11 +7055,10 @@ static void prvResetNextTaskUnblockTime( void )
7014
7055
traceRETURN_vTaskEnterCritical ();
7015
7056
}
7016
7057
7017
- #endif /* #if ( configNUMBER_OF_CORES > 1 ) */
7018
-
7058
+ #endif /* #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) ) */
7019
7059
/*-----------------------------------------------------------*/
7020
7060
7021
- #if ( configNUMBER_OF_CORES > 1 )
7061
+ #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) )
7022
7062
7023
7063
UBaseType_t vTaskEnterCriticalFromISR ( void )
7024
7064
{
@@ -7047,7 +7087,7 @@ static void prvResetNextTaskUnblockTime( void )
7047
7087
return uxSavedInterruptStatus ;
7048
7088
}
7049
7089
7050
- #endif /* #if ( configNUMBER_OF_CORES > 1 ) */
7090
+ #endif /* #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) ) */
7051
7091
/*-----------------------------------------------------------*/
7052
7092
7053
7093
#if ( ( portCRITICAL_NESTING_IN_TCB == 1 ) && ( configNUMBER_OF_CORES == 1 ) )
@@ -7095,7 +7135,7 @@ static void prvResetNextTaskUnblockTime( void )
7095
7135
#endif /* #if ( ( portCRITICAL_NESTING_IN_TCB == 1 ) && ( configNUMBER_OF_CORES == 1 ) ) */
7096
7136
/*-----------------------------------------------------------*/
7097
7137
7098
- #if ( configNUMBER_OF_CORES > 1 )
7138
+ #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) )
7099
7139
7100
7140
void vTaskExitCritical ( void )
7101
7141
{
@@ -7153,10 +7193,10 @@ static void prvResetNextTaskUnblockTime( void )
7153
7193
traceRETURN_vTaskExitCritical ();
7154
7194
}
7155
7195
7156
- #endif /* #if ( configNUMBER_OF_CORES > 1 ) */
7196
+ #endif /* #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) ) */
7157
7197
/*-----------------------------------------------------------*/
7158
7198
7159
- #if ( configNUMBER_OF_CORES > 1 )
7199
+ #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) )
7160
7200
7161
7201
void vTaskExitCriticalFromISR ( UBaseType_t uxSavedInterruptStatus )
7162
7202
{
@@ -7195,7 +7235,29 @@ static void prvResetNextTaskUnblockTime( void )
7195
7235
traceRETURN_vTaskExitCriticalFromISR ();
7196
7236
}
7197
7237
7198
- #endif /* #if ( configNUMBER_OF_CORES > 1 ) */
7238
+ #endif /* #if ( ( portUSING_GRANULAR_LOCKS == 0 ) && ( configNUMBER_OF_CORES > 1 ) ) */
7239
+ /*-----------------------------------------------------------*/
7240
+
7241
+ #if ( ( portUSING_GRANULAR_LOCKS == 1 ) && ( configNUMBER_OF_CORES > 1 ) )
7242
+
7243
+ BaseType_t xTaskUnlockCanYield ( void )
7244
+ {
7245
+ BaseType_t xReturn ;
7246
+ BaseType_t xCoreID = portGET_CORE_ID ();
7247
+
7248
+ if ( ( xYieldPendings [ xCoreID ] == pdTRUE ) && ( uxSchedulerSuspended == pdFALSE ) && ( pxCurrentTCBs [ xCoreID ]-> xPreemptionDisable == pdFALSE ) )
7249
+ {
7250
+ xReturn = pdTRUE ;
7251
+ }
7252
+ else
7253
+ {
7254
+ xReturn = pdFALSE ;
7255
+ }
7256
+
7257
+ return xReturn ;
7258
+ }
7259
+
7260
+ #endif /* #if ( ( portUSING_GRANULAR_LOCKS == 1 ) && ( configNUMBER_OF_CORES > 1 ) ) */
7199
7261
/*-----------------------------------------------------------*/
7200
7262
7201
7263
#if ( configUSE_STATS_FORMATTING_FUNCTIONS > 0 )
0 commit comments