diff -uprN src/string/riscv64/strlen.S src/string/riscv64/strlen.S --- src/string/riscv64/strlen.S 1970-01-01 08:00:00.000000000 +0800 +++ src/string/riscv64/strlen.S 2023-04-18 13:37:22.644057680 +0800 @@ -0,0 +1,82 @@ +# size_t strlen(const char *str) +# a0 holds *str +.global strlen +.type strlen,@function +strlen: +#ifdef __riscv_vector + mv t0, a0 # Save start + csrr t1, vlenb + addi t1, t1, -1 + add a3, t0, t1 + not t1, t1 + and a3, a3, t1 + sub a4, a3, t0 + beq a3, t0, loop # if already aligned + +unaligned: + lbu t1, 0(t0) + beqz t1, found + addi t0, t0, 1 + blt t0, a3, unaligned + +loop: + vsetvli a1, x0, e8, m8, ta, ma # Vector of bytes of maximum length + vle8ff.v v8, (t0) # Load bytes + csrr a1, vl # Get bytes read + vmseq.vi v0, v8, 0 # Set v0[i] where v8[i] = 0 + vfirst.m a2, v0 # Find first set bit + add t0, t0, a1 # Bump pointer + bltz a2, loop # Not found? + + add a3, a3, a1 # Sum start + bump + add t0, t0, a2 # Add index + sub a3, t0, a3 # Subtract start address+bump + add a0, a3, a4 + ret + +found: + sub a0, t0, a0 + ret + +#else + mv a5, a0 + andi a4, a0, 7 + beqz a4, aligned # if already aligned + +unaligned: + lbu a4, 0(a5) + beqz a4, count + addi a5, a5, 1 + andi a4, a5, 7 + bnez a4, unaligned + +aligned: + la t0, magic + ld a1, 0(t0) + ld a2, 8(t0) + +loop: + ld a3, 0(a5) + add a4, a3, a1 + not a3, a3 + and a4, a4, a3 + and a4, a4, a2 + bnez a4, found + addi a5, a5, 8 + j loop + +found: + lbu a4, 0(a5) + beqz a4, count + addi a5, a5, 1 + j found + +count: + sub a0, a5, a0 + ret + +.section .data +magic: + .dword 0xfefefefefefefeff + .dword 0x8080808080808080 +#endif