This is an automated email from the ASF dual-hosted git repository.

kasjer pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/mynewt-core.git

commit 5aaf383824924223db6ea5097bbf9727629faded
Author: Jerzy Kasenberg <[email protected]>
AuthorDate: Mon Jun 1 23:48:25 2026 +0200

    baselibc/memcpy: Update memcpy() for Cortex-M
    
    memcpy used to work in descending order to minimize code size.
    Updates ARM memcpy version to work in ascending order.
    For aligned buffers time to copy does not changes significantly
    when buffer to copy increases by 1 which was the case when even
    for aligned buffers code performed unaligned reads when nuber
    of bytes to copy was not multiply of 4.
    
    Code enables 32-bit copy for Cortex-M0 (which was not
    the case), aligned buffers are copied much faster now.
    
    This change also improves performance on memory mapped
    QSPI flashes when reading successful data is much faster
    then reading in reverse direction.
---
 libc/baselibc/src/memcpy.c | 47 ++++++++++++++++++++++++++++------------------
 1 file changed, 29 insertions(+), 18 deletions(-)

diff --git a/libc/baselibc/src/memcpy.c b/libc/baselibc/src/memcpy.c
index 07f5080f1..1e683f92c 100644
--- a/libc/baselibc/src/memcpy.c
+++ b/libc/baselibc/src/memcpy.c
@@ -23,27 +23,38 @@ void *memcpy(void *dst, const void *src, size_t n)
         (void)p;
         (void)q;
 
-#if defined(__ARM_FEATURE_UNALIGNED)
-        /*
-         * We can speed up a bit by moving 32-bit words if unaligned access is
-         * supported (e.g. Cortex-M3/4/7/33).
-         */
         asm (".syntax unified           \n"
-             "       b    test1         \n"
-             "loop1: ldr  r3, [r1, r2]  \n"
-             "       str  r3, [r0, r2]  \n"
-             "test1: subs r2, #4        \n"
-             "       bpl  loop1         \n"
-             "       add  r2, #4        \n"
-            );
+             "       push {r0, r4}      \n"
+#if !defined(__ARM_FEATURE_UNALIGNED)
+             /*
+              * For Cortex-M0 check if copy by 32-bit is possible, if not
+              * copy everything by byte.
+              */
+             "       movs r3, r0        \n"
+             "       orrs r3, r1        \n"
+             "       lsls r3, #30       \n"
+             "       bne  2f            \n"
 #endif
-
-        asm (".syntax unified           \n"
-             "       b    test2         \n"
-             "loop2: ldrb r3, [r1, r2]  \n"
+             "       lsrs r3, r2, #2    \n"
+             "       beq  2f            \n"
+             "       lsls r4, r3, #2    \n"
+             "       subs r2, r2, r4    \n"
+             "       rsbs r4, #0        \n"
+             "       subs r0, r4        \n"
+             "       subs r1, r4        \n"
+             "1:     ldr  r3, [r1, r4]  \n"
+             "       str  r3, [r0, r4]  \n"
+             "       adds r4, #4        \n"
+             "       bmi  1b            \n"
+             "2:     rsbs r2, #0        \n"
+             "       beq  4f            \n"
+             "       subs r0, r2        \n"
+             "       subs r1, r2        \n"
+             "3:     ldrb r3, [r1, r2]  \n"
              "       strb r3, [r0, r2]  \n"
-             "test2: subs r2, #1        \n"
-             "       bpl  loop2         \n"
+             "       adds r2, #1        \n"
+             "       bmi  3b            \n"
+             "4:     pop  {r0, r4}      \n"
             );
 #else
        while (n--) {

Reply via email to