blob: 5a2211f092029f2a2974cbb0fd216dee36fd103f [file] [log] [blame]
Linus Torvalds1da177e2005-04-16 15:20:36 -07001/* $Id: memmove.S,v 1.2 2001/07/27 11:51:09 gniibe Exp $
2 *
3 * "memmove" implementation of SuperH
4 *
5 * Copyright (C) 1999 Niibe Yutaka
6 *
7 */
8
9/*
10 * void *memmove(void *dst, const void *src, size_t n);
11 * The memory areas may overlap.
12 */
13
14#include <linux/linkage.h>
15ENTRY(memmove)
16 ! if dest > src, call memcpy (it copies in decreasing order)
17 cmp/hi r5,r4
18 bf 1f
19 mov.l 2f,r0
20 jmp @r0
21 nop
22 .balign 4
232: .long memcpy
241:
25 sub r5,r4 ! From here, r4 has the distance to r0
26 tst r6,r6
27 bt/s 9f ! if n=0, do nothing
28 mov r5,r0
29 add r6,r5
30 mov #12,r1
31 cmp/gt r6,r1
32 bt/s 8f ! if it's too small, copy a byte at once
33 add #-1,r4
34 add #1,r4
35 !
36 ! [ ... ] DST [ ... ] SRC
37 ! [ ... ] [ ... ]
38 ! : :
39 ! r0+r4--> [ ... ] r0 --> [ ... ]
40 ! : :
41 ! [ ... ] [ ... ]
42 ! r5 -->
43 !
44 mov r4,r1
45 mov #3,r2
46 and r2,r1
47 shll2 r1
48 mov r0,r3 ! Save the value on R0 to R3
49 mova jmptable,r0
50 add r1,r0
51 mov.l @r0,r1
52 jmp @r1
53 mov r3,r0 ! and back to R0
54 .balign 4
55jmptable:
56 .long case0
57 .long case1
58 .long case2
59 .long case3
60
61 ! copy a byte at once
628: mov.b @r0+,r1
63 cmp/hs r5,r0
64 bf/s 8b ! while (r0<r5)
65 mov.b r1,@(r0,r4)
66 add #1,r4
679:
68 add r4,r0
69 rts
70 sub r6,r0
71
72case_none:
73 bra 8b
74 add #-1,r4
75
76case0:
77 !
78 ! GHIJ KLMN OPQR --> GHIJ KLMN OPQR
79 !
80 ! First, align to long word boundary
81 mov r0,r3
82 and r2,r3
83 tst r3,r3
84 bt/s 2f
85 add #-1,r4
86 mov #4,r2
87 sub r3,r2
881: dt r2
89 mov.b @r0+,r1
90 bf/s 1b
91 mov.b r1,@(r0,r4)
92 !
932: ! Second, copy a long word at once
94 add #-3,r4
95 add #-3,r5
963: mov.l @r0+,r1
97 cmp/hs r5,r0
98 bf/s 3b
99 mov.l r1,@(r0,r4)
100 add #3,r5
101 !
102 ! Third, copy a byte at once, if necessary
103 cmp/eq r5,r0
104 bt/s 9b
105 add #4,r4
106 bra 8b
107 add #-1,r4
108
109case3:
110 !
111 ! GHIJ KLMN OPQR --> ...G HIJK LMNO PQR.
112 !
113 ! First, align to long word boundary
114 mov r0,r3
115 and r2,r3
116 tst r3,r3
117 bt/s 2f
118 add #-1,r4
119 mov #4,r2
120 sub r3,r2
1211: dt r2
122 mov.b @r0+,r1
123 bf/s 1b
124 mov.b r1,@(r0,r4)
125 !
1262: ! Second, read a long word and write a long word at once
127 add #-2,r4
128 mov.l @(r0,r4),r1
129 add #-7,r5
130 add #-4,r4
131 !
132#ifdef __LITTLE_ENDIAN__
133 shll8 r1
1343: mov r1,r3 ! JIHG
135 shlr8 r3 ! xJIH
136 mov.l @r0+,r1 ! NMLK
137 mov r1,r2
138 shll16 r2
139 shll8 r2 ! Kxxx
140 or r2,r3 ! KJIH
141 cmp/hs r5,r0
142 bf/s 3b
143 mov.l r3,@(r0,r4)
144#else
145 shlr8 r1
1463: mov r1,r3 ! GHIJ
147 shll8 r3 ! HIJx
148 mov.l @r0+,r1 ! KLMN
149 mov r1,r2
150 shlr16 r2
151 shlr8 r2 ! xxxK
152 or r2,r3 ! HIJK
153 cmp/hs r5,r0
154 bf/s 3b
155 mov.l r3,@(r0,r4)
156#endif
157 add #7,r5
158 !
159 ! Third, copy a byte at once, if necessary
160 cmp/eq r5,r0
161 bt/s 9b
162 add #7,r4
163 add #-3,r0
164 bra 8b
165 add #-1,r4
166
167case2:
168 !
169 ! GHIJ KLMN OPQR --> ..GH IJKL MNOP QR..
170 !
171 ! First, align to word boundary
172 tst #1,r0
173 bt/s 2f
174 add #-1,r4
175 mov.b @r0+,r1
176 mov.b r1,@(r0,r4)
177 !
1782: ! Second, read a word and write a word at once
179 add #-1,r4
180 add #-1,r5
181 !
1823: mov.w @r0+,r1
183 cmp/hs r5,r0
184 bf/s 3b
185 mov.w r1,@(r0,r4)
186 add #1,r5
187 !
188 ! Third, copy a byte at once, if necessary
189 cmp/eq r5,r0
190 bt/s 9b
191 add #2,r4
192 mov.b @r0,r1
193 mov.b r1,@(r0,r4)
194 bra 9b
195 add #1,r0
196
197case1:
198 !
199 ! GHIJ KLMN OPQR --> .GHI JKLM NOPQ R...
200 !
201 ! First, align to long word boundary
202 mov r0,r3
203 and r2,r3
204 tst r3,r3
205 bt/s 2f
206 add #-1,r4
207 mov #4,r2
208 sub r3,r2
2091: dt r2
210 mov.b @r0+,r1
211 bf/s 1b
212 mov.b r1,@(r0,r4)
213 !
2142: ! Second, read a long word and write a long word at once
215 mov.l @(r0,r4),r1
216 add #-7,r5
217 add #-4,r4
218 !
219#ifdef __LITTLE_ENDIAN__
220 shll16 r1
221 shll8 r1
2223: mov r1,r3 ! JIHG
223 shlr16 r3
224 shlr8 r3 ! xxxJ
225 mov.l @r0+,r1 ! NMLK
226 mov r1,r2
227 shll8 r2 ! MLKx
228 or r2,r3 ! MLKJ
229 cmp/hs r5,r0
230 bf/s 3b
231 mov.l r3,@(r0,r4)
232#else
233 shlr16 r1
234 shlr8 r1
2353: mov r1,r3 ! GHIJ
236 shll16 r3
237 shll8 r3 ! Jxxx
238 mov.l @r0+,r1 ! KLMN
239 mov r1,r2
240 shlr8 r2 ! xKLM
241 or r2,r3 ! JKLM
242 cmp/hs r5,r0
243 bf/s 3b ! while(r0<r5)
244 mov.l r3,@(r0,r4)
245#endif
246 add #7,r5
247 !
248 ! Third, copy a byte at once, if necessary
249 cmp/eq r5,r0
250 bt/s 9b
251 add #5,r4
252 add #-3,r0
253 bra 8b
254 add #-1,r4