SPRADD8 November 2024 F29H850TU , F29H859TU-Q1
Dead zone code commonly occurs in real-time applications.
The code block below shows the the ternary operator '?' based approach to implementing dead zone code. The C29 (10 cycles, independent of input) outperforms the C28 (25-36 cycles, dependent on input) and Cortex-M7 (23-35 cycles, dependent on input). This efficiency is achieved through the delayed return instruction (RETD) and well-utilized delay slots containing compare (CMPF) and assignment (SELECT) instructions.
float deadzone(float in)
{
float out;
float out_pos = in - 1.0f;
float out_neg = in + 1.0f;
out = (in > 1.0f)? out_pos : ((in > -1.0f)? 0.0f : out_neg);
return out;
}
C29 Implementation
Function call:
CALL @deadzone
|| LD.32 M0,@in1
;---------CALLD occurs
ST.32 @out1,M0
deadzone:
ONEF M1
|| NEGONEF M2
SADDF M3,M0,M2
|| CMPF TDM0,M.GT,M0,M2
|| SADDF M2,M0,M1
|| RETD
ZERO M4
CMPF TDM1,M.GT,M0,M1
|| SELECT TDM0,M0,M4,M2
SELECT TDM1,M0,M3,M0
C28 Implementation
Function call: MOVW DP,#_in1
MOV32 R0H,@_in1
LCR #_deadzone
MOVW DP,#_out1
MOV32 @_out1,R0H
_deadzone:
ADDB SP,#2
CMPF32 R0H,#16256
MOVST0 ZF, NF
B $C$L1,LEQ
ADDF32 R0H,R0H,#49024
B $C$L3,UNC
$C$L1:
CMPF32 R0H,#49024
MOVST0 ZF, NF
B $C$L2,LEQ
ZERO R0H
B $C$L3,UNC
$C$L2:
ADDF32 R0H,R0H,#16256
$C$L3:
SUBB SP,#2
LRETR
M7 Implementation
Function call:
VLDR S0,[R6, #+144]
BL deadzone
VSTR S0,[R6, #+152]
deadzone:
MOVS R0,#+1
MOVT R0,#+16256
VMOV S2,R0
VMOV.F32 S1,S0
VCMP.F32 S1,S2
FMSTAT
VMOV.F32 S0,#1.0
VADD.F32 S0,S1,S0
BLT.N deadzone_0
VMOV.F32 S3,#-1.0
VADD.F32 S0,S1,S3
BX LR
deadzone_0:
MVN R1,#+1082130432
VMOV S4,R1
VCMP.F32 S1,S4
FMSTAT
ITT GE
MOVGE R0,#+0
VMOVGE S0,R0
BX LR