[PATCH v3 03/15] riscv: add vectorized strchr
Pincheng Wang
pincheng.plct@isrc.iscas.ac.cn
Fri Aug 14 02:26:44 GMT 2026
The vector implementation scans the string in vector-length chunks using
fault-only-first loads (vle8ff.v), locating the target byte and the
terminating NUL in the same pass while never crossing into an unmapped
page. This provides significant performance improvements on RVV-capable
hardware. Use conditional compilation to fall back to the generic
implementation when __riscv_vector is not available, maintaining
compatibility with non-vector RISC-V systems.
Signed-off-by: Pincheng Wang <pincheng.plct@isrc.iscas.ac.cn>
---
newlib/libc/machine/riscv/Makefile.inc | 2 ++
newlib/libc/machine/riscv/strchr-asm.S | 25 +++++++++++++++++++++++++
newlib/libc/machine/riscv/strchr.c | 5 +++++
3 files changed, 32 insertions(+)
create mode 100644 newlib/libc/machine/riscv/strchr-asm.S
create mode 100644 newlib/libc/machine/riscv/strchr.c
diff --git a/newlib/libc/machine/riscv/Makefile.inc b/newlib/libc/machine/riscv/Makefile.inc
index d3f72e471..01a0aaf50 100644
--- a/newlib/libc/machine/riscv/Makefile.inc
+++ b/newlib/libc/machine/riscv/Makefile.inc
@@ -20,6 +20,8 @@ libc_a_SOURCES += \
%D%/memset.S \
%D%/setjmp.S \
%D%/stpcpy.c \
+ %D%/strchr-asm.S \
+ %D%/strchr.c \
%D%/strcmp.S \
%D%/strcpy.c \
%D%/strlen-asm.S \
diff --git a/newlib/libc/machine/riscv/strchr-asm.S b/newlib/libc/machine/riscv/strchr-asm.S
new file mode 100644
index 000000000..8cbd44ecf
--- /dev/null
+++ b/newlib/libc/machine/riscv/strchr-asm.S
@@ -0,0 +1,25 @@
+#include <sys/asm.h>
+
+#if defined(__riscv_vector) && !defined(__riscv_e) && !defined(__OPTIMIZE_SIZE__) && !defined(PREFER_SIZE_OVER_SPEED)
+ENTRY(strchr)
+.Lloop:
+ vsetvli t0, zero, e8, m1, ta, ma
+ vle8ff.v v0, (a0)
+ vmseq.vi v8, v0, 0
+ vmseq.vx v9, v0, a1
+ vfirst.m a2, v8 /* first occurrence of \0 */
+ vfirst.m a3, v9 /* first occurrence of a1 */
+ sltz a4, a3
+ sltu a5, a2, a3
+ or a4, a4, a5
+ beqz a4, .Lfound /* found a1, not preceded by \0? */
+ csrr a6, vl
+ add a0, a0, a6
+ bltz a2, .Lloop /* didn't find \0? */
+ li a0, 0
+ ret
+.Lfound:
+ add a0, a0, a3
+ ret
+END(strchr)
+#endif
diff --git a/newlib/libc/machine/riscv/strchr.c b/newlib/libc/machine/riscv/strchr.c
new file mode 100644
index 000000000..459d3c5d8
--- /dev/null
+++ b/newlib/libc/machine/riscv/strchr.c
@@ -0,0 +1,5 @@
+#if defined(__OPTIMIZE_SIZE__) || defined(PREFER_SIZE_OVER_SPEED) || !defined(__riscv_vector) || defined(__riscv_e)
+# include "../../string/strchr.c"
+#else
+/* strchr defined in strchr-asm.S */
+#endif
--
2.39.5
More information about the Newlib
mailing list