Loading...
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
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