linux/arch/sh/lib/memcpy.S
<<
>>
Prefs
   1/* SPDX-License-Identifier: GPL-2.0 */
   2/* $Id: memcpy.S,v 1.3 2001/07/27 11:50:52 gniibe Exp $
   3 *
   4 * "memcpy" implementation of SuperH
   5 *
   6 * Copyright (C) 1999  Niibe Yutaka
   7 *
   8 */
   9
  10/*
  11 * void *memcpy(void *dst, const void *src, size_t n);
  12 * No overlap between the memory of DST and of SRC are assumed.
  13 */
  14
  15#include <linux/linkage.h>
  16ENTRY(memcpy)
  17        tst     r6,r6
  18        bt/s    9f              ! if n=0, do nothing
  19         mov    r4,r0
  20        sub     r4,r5           ! From here, r5 has the distance to r0
  21        add     r6,r0           ! From here, r0 points the end of copying point
  22        mov     #12,r1
  23        cmp/gt  r6,r1
  24        bt/s    7f              ! if it's too small, copy a byte at once
  25         add    #-1,r5
  26        add     #1,r5
  27        !                       From here, r6 is free
  28        !
  29        !      r4   -->  [ ...  ] DST             [ ...  ] SRC
  30        !                [ ...  ]                 [ ...  ]
  31        !                  :                        :
  32        !      r0   -->  [ ...  ]       r0+r5 --> [ ...  ]
  33        !
  34        !
  35        mov     r5,r1
  36        mov     #3,r2
  37        and     r2,r1
  38        shll2   r1
  39        mov     r0,r3           ! Save the value on R0 to R3
  40        mova    jmptable,r0
  41        add     r1,r0
  42        mov.l   @r0,r1
  43        jmp     @r1
  44         mov    r3,r0           ! and back to R0
  45        .balign 4
  46jmptable:
  47        .long   case0
  48        .long   case1
  49        .long   case2
  50        .long   case3
  51
  52        ! copy a byte at once
  537:      mov     r4,r2
  54        add     #1,r2
  558:
  56        cmp/hi  r2,r0
  57        mov.b   @(r0,r5),r1
  58        bt/s    8b                      ! while (r0>r2)
  59         mov.b  r1,@-r0
  609:
  61        rts
  62         nop
  63
  64case0:
  65        !
  66        !       GHIJ KLMN OPQR -->  GHIJ KLMN OPQR
  67        !
  68        ! First, align to long word boundary
  69        mov     r0,r3
  70        and     r2,r3
  71        tst     r3,r3
  72        bt/s    2f
  73         add    #-4,r5
  74        add     #3,r5
  751:      dt      r3
  76        mov.b   @(r0,r5),r1
  77        bf/s    1b
  78         mov.b  r1,@-r0
  79        !
  80        add     #-3,r5
  812:      ! Second, copy a long word at once
  82        mov     r4,r2
  83        add     #7,r2
  843:      mov.l   @(r0,r5),r1
  85        cmp/hi  r2,r0
  86        bt/s    3b
  87         mov.l  r1,@-r0
  88        !
  89        ! Third, copy a byte at once, if necessary
  90        cmp/eq  r4,r0
  91        bt/s    9b
  92         add    #3,r5
  93        bra     8b
  94         add    #-6,r2
  95
  96case1:
  97        !
  98        !       GHIJ KLMN OPQR -->  ...G HIJK LMNO PQR.
  99        !
 100        ! First, align to long word boundary
 101        mov     r0,r3
 102        and     r2,r3
 103        tst     r3,r3
 104        bt/s    2f
 105         add    #-1,r5
 1061:      dt      r3
 107        mov.b   @(r0,r5),r1
 108        bf/s    1b
 109         mov.b  r1,@-r0
 110        !
 1112:      ! Second, read a long word and write a long word at once
 112        mov.l   @(r0,r5),r1
 113        add     #-4,r5
 114        mov     r4,r2
 115        add     #7,r2
 116        !
 117#ifdef __LITTLE_ENDIAN__
 1183:      mov     r1,r3           ! RQPO
 119        shll16  r3
 120        shll8   r3              ! Oxxx
 121        mov.l   @(r0,r5),r1     ! NMLK
 122        mov     r1,r6
 123        shlr8   r6              ! xNML
 124        or      r6,r3           ! ONML
 125        cmp/hi  r2,r0
 126        bt/s    3b
 127         mov.l  r3,@-r0
 128#else
 1293:      mov     r1,r3           ! OPQR
 130        shlr16  r3
 131        shlr8   r3              ! xxxO
 132        mov.l   @(r0,r5),r1     ! KLMN
 133        mov     r1,r6
 134        shll8   r6              ! LMNx
 135        or      r6,r3           ! LMNO
 136        cmp/hi  r2,r0
 137        bt/s    3b
 138         mov.l  r3,@-r0
 139#endif
 140        !
 141        ! Third, copy a byte at once, if necessary
 142        cmp/eq  r4,r0
 143        bt/s    9b
 144         add    #4,r5
 145        bra     8b
 146         add    #-6,r2
 147
 148case2:
 149        !
 150        !       GHIJ KLMN OPQR -->  ..GH IJKL MNOP QR..
 151        !
 152        ! First, align to word boundary
 153        tst     #1,r0
 154        bt/s    2f
 155         add    #-1,r5
 156        mov.b   @(r0,r5),r1
 157        mov.b   r1,@-r0
 158        !
 1592:      ! Second, read a word and write a word at once
 160        add     #-1,r5
 161        mov     r4,r2
 162        add     #3,r2
 163        !
 1643:      mov.w   @(r0,r5),r1
 165        cmp/hi  r2,r0
 166        bt/s    3b
 167         mov.w  r1,@-r0
 168        !
 169        ! Third, copy a byte at once, if necessary
 170        cmp/eq  r4,r0
 171        bt/s    9b
 172         add    #1,r5
 173        mov.b   @(r0,r5),r1
 174        rts
 175         mov.b  r1,@-r0
 176
 177case3:
 178        !
 179        !       GHIJ KLMN OPQR -->  .GHI JKLM NOPQ R...
 180        !
 181        ! First, align to long word boundary
 182        mov     r0,r3
 183        and     r2,r3
 184        tst     r3,r3
 185        bt/s    2f
 186         add    #-1,r5
 1871:      dt      r3
 188        mov.b   @(r0,r5),r1
 189        bf/s    1b
 190         mov.b  r1,@-r0
 191        !
 1922:      ! Second, read a long word and write a long word at once
 193        add     #-2,r5
 194        mov.l   @(r0,r5),r1
 195        add     #-4,r5
 196        mov     r4,r2
 197        add     #7,r2
 198        !
 199#ifdef __LITTLE_ENDIAN__
 2003:      mov     r1,r3           ! RQPO
 201        shll8   r3              ! QPOx
 202        mov.l   @(r0,r5),r1     ! NMLK
 203        mov     r1,r6
 204        shlr16  r6
 205        shlr8   r6              ! xxxN
 206        or      r6,r3           ! QPON
 207        cmp/hi  r2,r0
 208        bt/s    3b
 209         mov.l  r3,@-r0
 210#else
 2113:      mov     r1,r3           ! OPQR
 212        shlr8   r3              ! xOPQ
 213        mov.l   @(r0,r5),r1     ! KLMN
 214        mov     r1,r6
 215        shll16  r6
 216        shll8   r6              ! Nxxx
 217        or      r6,r3           ! NOPQ
 218        cmp/hi  r2,r0
 219        bt/s    3b
 220         mov.l  r3,@-r0
 221#endif
 222        !
 223        ! Third, copy a byte at once, if necessary
 224        cmp/eq  r4,r0
 225        bt/s    9b
 226         add    #6,r5
 227        bra     8b
 228         add    #-6,r2
 229