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