diff options
author | Victor Do Nascimento <Victor.DoNascimento@arm.com> | 2022-06-22 15:07:31 +0100 |
---|---|---|
committer | Szabolcs Nagy <szabolcs.nagy@arm.com> | 2022-06-22 15:07:31 +0100 |
commit | 8bf2238fc0571d673b593c1ec2f72f4179a8ec79 (patch) | |
tree | bb897fe21fae87963b6ca45e1c8f0365439cd0ce | |
parent | f931b0e187330bdd38dd0149cc16d9a103502936 (diff) | |
download | arm-optimized-routines-8bf2238fc0571d673b593c1ec2f72f4179a8ec79.tar.gz |
string: Add M-profile PACBTI implementation of memchr
Ensure BTI indirect branch landing pads (BTI) and pointer authentication
code genetaion (PAC) and verification instructions (BXAUT) are
conditionally added to assembly when branch protection is requested
-rw-r--r-- | string/arm/memchr.S | 40 |
1 files changed, 37 insertions, 3 deletions
diff --git a/string/arm/memchr.S b/string/arm/memchr.S index 1271ca1..4f7d8f4 100644 --- a/string/arm/memchr.S +++ b/string/arm/memchr.S @@ -23,7 +23,11 @@ @ Removed unneeded cbz from align loop .syntax unified +#if __ARM_ARCH_8M_MAIN__ + /* keep config inherited from -march= */ +#else .arch armv7-a +#endif @ this lets us check a flag in a 00/ff byte easily in either endianness #ifdef __ARMEB__ @@ -33,17 +37,22 @@ #endif .thumb +#include "../pacbti.h" + @ --------------------------------------------------------------------------- .thumb_func .align 2 .p2align 4,,15 .global __memchr_arm .type __memchr_arm,%function + .fnstart + .cfi_startproc __memchr_arm: @ r0 = start of memory to scan @ r1 = character to look for @ r2 = length @ returns r0 = pointer to character or NULL if not found + pacbti_prologue and r1,r1,#0xff @ Don't think we can trust the caller to actually pass a char cmp r2,#16 @ If it's short don't bother with anything clever @@ -64,6 +73,19 @@ __memchr_arm: 10: @ At this point, we are aligned, we know we have at least 8 bytes to work with push {r4,r5,r6,r7} + .save {r4-r7} + .cfi_adjust_cfa_offset 16 +#ifdef __ARM_FEATURE_PAC_DEFAULT + .cfi_offset 4, -8 + .cfi_offset 5, -12 + .cfi_offset 6, -16 + .cfi_offset 7, -20 +#else + .cfi_offset 4, -4 + .cfi_offset 5, -8 + .cfi_offset 6, -12 + .cfi_offset 7, -16 +#endif /* __ARM_FEATURE_PAC_DEFAULT */ orr r1, r1, r1, lsl #8 @ expand the match word across to all bytes orr r1, r1, r1, lsl #16 bic r4, r2, #7 @ Number of double words to work with @@ -83,6 +105,11 @@ __memchr_arm: bne 15b @ (Flags from the subs above) If not run out of bytes then go around again pop {r4,r5,r6,r7} + .cfi_restore 7 + .cfi_restore 6 + .cfi_restore 5 + .cfi_restore 4 + .cfi_adjust_cfa_offset -16 and r1,r1,#0xff @ Get r1 back to a single character from the expansion above and r2,r2,#7 @ Leave the count remaining as the number after the double words have been done @@ -98,11 +125,11 @@ __memchr_arm: 40: movs r0,#0 @ not found - bx lr + pacbti_epilogue 50: subs r0,r0,#1 @ found - bx lr + pacbti_epilogue 60: @ We're here because the fast path found a hit - now we have to track down exactly which word it was @ r0 points to the start of the double word after the one that was tested @@ -126,7 +153,14 @@ __memchr_arm: 61: pop {r4,r5,r6,r7} + .cfi_restore 7 + .cfi_restore 6 + .cfi_restore 5 + .cfi_restore 4 + .cfi_adjust_cfa_offset -16 subs r0,r0,#1 - bx lr + pacbti_epilogue + .cfi_endproc + .fnend .size __memchr_arm, . - __memchr_arm |