in GCC/TriCore_38xa/port.c [407:459]
void vPortReclaimCSA( uint32_t *pxTCB )
{
uint32_t pxHeadCSA, pxTailCSA, pxFreeCSA;
uint32_t *pulNextCSA;
/* A pointer to the first CSA in the list of CSAs consumed by the task is
stored in the first element of the tasks TCB structure (where the stack
pointer would be on a traditional stack based architecture). */
pxHeadCSA = ( *pxTCB ) & portCSA_FCX_MASK;
/* Mask off everything in the CSA link field other than the address. If
the address is NULL, then the CSA is not linking anywhere and there is
nothing to do. */
pxTailCSA = pxHeadCSA;
/* Convert the link value to contain just a raw address and store this
in a local variable. */
pulNextCSA = portCSA_TO_ADDRESS( pxTailCSA );
/* Iterate over the CSAs that were consumed as part of the task. The
first field in the CSA is the pointer to then next CSA. Mask off
everything in the pointer to the next CSA, other than the link address.
If this is NULL, then the CSA currently being pointed to is the last in
the chain. */
while( 0UL != ( pulNextCSA[ 0 ] & portCSA_FCX_MASK ) )
{
/* Clear all bits of the pointer to the next in the chain, other
than the address bits themselves. */
pulNextCSA[ 0 ] = pulNextCSA[ 0 ] & portCSA_FCX_MASK;
/* Move the pointer to point to the next CSA in the list. */
pxTailCSA = pulNextCSA[ 0 ];
/* Update the local pointer to the CSA. */
pulNextCSA = portCSA_TO_ADDRESS( pxTailCSA );
}
_disable();
{
/* Look up the current free CSA head. */
_dsync();
pxFreeCSA = __MFCR( $FCX );
/* Join the current Free onto the Tail of what is being reclaimed. */
portCSA_TO_ADDRESS( pxTailCSA )[ 0 ] = pxFreeCSA;
/* Move the head of the reclaimed into the Free. */
_dsync();
_mtcr( $FCX, pxHeadCSA );
_isync();
}
_enable();
}