1/* strcat (dest, src) -- Append SRC on the end of DEST.
2   For SPARC v7.
3   Copyright (C) 1996-2022 Free Software Foundation, Inc.
4   This file is part of the GNU C Library.
5
6   The GNU C Library is free software; you can redistribute it and/or
7   modify it under the terms of the GNU Lesser General Public
8   License as published by the Free Software Foundation; either
9   version 2.1 of the License, or (at your option) any later version.
10
11   The GNU C Library is distributed in the hope that it will be useful,
12   but WITHOUT ANY WARRANTY; without even the implied warranty of
13   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14   Lesser General Public License for more details.
15
16   You should have received a copy of the GNU Lesser General Public
17   License along with the GNU C Library; if not, see
18   <https://www.gnu.org/licenses/>.  */
19
20#include <sysdep.h>
21
22	/* Normally, this uses ((xword - 0x01010101) & 0x80808080) test
23	   to find out if any byte in xword could be zero. This is fast, but
24	   also gives false alarm for any byte in range 0x81-0xff. It does
25	   not matter for correctness, as if this test tells us there could
26	   be some zero byte, we check it byte by byte, but if bytes with
27	   high bits set are common in the strings, then this will give poor
28	   performance. You can #define EIGHTBIT_NOT_RARE and the algorithm
29	   will use one tick slower, but more precise test
30	   ((xword - 0x01010101) & (~xword) & 0x80808080),
31	   which does not give any false alarms (but if some bits are set,
32	   one cannot assume from it which bytes are zero and which are not).
33	   It is yet to be measured, what is the correct default for glibc
34	   in these days for an average user.
35	 */
36
37	.text
38	.align		4
39
40ENTRY(strcat)
41	mov		%o0, %g2
42	andcc		%o0, 3, %g0
43	be		30f
44	 sethi		%hi(0x80808080), %o4
45
46	ldub		[%o0], %o5
47	cmp		%o5, 0
48	be		1f
49	 add		%o0, 1, %o0
50	andcc		%o0, 3, %g0
51	be		7f
52	 or		%o4, %lo(0x80808080), %o3
53	ldub		[%o0], %o5
54	cmp		%o5, 0
55	be		2f
56	 add		%o0, 1, %o0
57	andcc		%o0, 3, %g0
58	be		8f
59	 sethi		%hi(0x01010101), %o4
60	ldub		[%o0], %o5
61	cmp		%o5, 0
62	be		3f
63	 add		%o0, 1, %o0
64	b		9f
65	 or		%o4, %lo(0x01010101), %o2
661:	or		%o4, %lo(0x80808080), %o3
672:	sethi		%hi(0x01010101), %o4
683:	or		%o4, %lo(0x01010101), %o2
69	b		3f
70	 sub		%o0, 1, %o0
71
7230:	or		%o4, %lo(0x80808080), %o3
737:	sethi		%hi(0x01010101), %o4
748:	or		%o4, %lo(0x01010101), %o2
759:	ld		[%o0], %o5
767:	sub		%o5, %o2, %o4
77#ifdef EIGHTBIT_NOT_RARE
78	andn		%o4, %o5, %o4
79#endif
80	andcc		%o4, %o3, %g0
81	be		9b
82	 add		%o0, 4, %o0
83
84	srl		%o5, 24, %g5
85	andcc		%g5, 0xff, %g0
86	be		3f
87	 add		%o0, -4, %o0
88	srl		%o5, 16, %g5
89	andcc		%g5, 0xff, %g0
90	be		3f
91	 add		%o0, 1, %o0
92	srl		%o5, 8, %g5
93	andcc		%g5, 0xff, %g0
94	be		3f
95	 add		%o0, 1, %o0
96	andcc		%o5, 0xff, %g0
97	add		%o0, 2, %o0
98	bne,a		7b
99	 ld		[%o0], %o5
100	sub		%o0, 1, %o0
1013:	andcc		%o1, 3, %o4
102	be		4f
103	 nop
104
105	cmp		%o4, 2
106	be		11f
107	 cmp		%o4, 3
108	ldub		[%o1], %o5
109	add		%o1, 1, %o1
110	stb		%o5, [%o0]
111	be		13f
112	 cmp		%o5, 0
113	be		0f
114	 add		%o0, 1, %o0
11511:	lduh		[%o1], %o5
116	add		%o1, 2, %o1
117	srl		%o5, 8, %o4
118	cmp		%o4, 0
119	stb		%o4, [%o0]
120	bne,a		12f
121	 stb		%o5, [%o0 + 1]
122	retl
123	 mov		%g2, %o0
12412:	andcc		%o5, 0xff, %o5
125	bne		4f
126	 add		%o0, 2, %o0
127	retl
128	 mov 		%g2, %o0
12913:	bne		4f
130	 add		%o0, 1, %o0
131	retl
132	 mov		%g2, %o0
133
1344:	andcc		%o0, 3, %g3
135	bne		12f
1361:	ld		[%o1], %o5
137	add		%o1, 4, %o1
138	sub		%o5, %o2, %o4
139#ifdef EIGHTBIT_NOT_RARE
140	andn		%o4, %o5, %o4
141#endif
142	add		%o0, 4, %o0
143	andcc		%o4, %o3, %g0
144	be,a		1b
145	 st		%o5, [%o0 - 4]
146
147	srl		%o5, 24, %g5
148	andcc		%g5, 0xff, %g0
149	be		1f
150	 srl		%o5, 16, %g5
151	andcc		%g5, 0xff, %g0
152	be		2f
153	 srl		%o5, 8, %g5
154	andcc		%g5, 0xff, %g0
155	be		3f
156	 andcc		%o5, 0xff, %g0
157	bne		1b
158	 st		%o5, [%o0 - 4]
159	retl
160	 mov		%g2, %o0
1613:	srl		%o5, 16, %o5
162	sth		%o5, [%o0 - 4]
163	stb		%g0, [%o0 - 2]
164	retl
165	 mov		%g2, %o0
1662:	srl		%o5, 16, %o5
167	sth		%o5, [%o0 - 4]
168	retl
169	 mov		%g2, %o0
1701:	stb		%g0, [%o0 - 4]
171	retl
172	 mov		%g2, %o0
173
17412:	add		%o1, 4, %o1
175	sub		%o5, %o2, %o4
176	cmp		%g3, 2
177	be		2f
178	 cmp		%g3, 3
179	be		3f
180	 andcc		%o4, %o3, %g0
181	bne		5f
182	 srl		%o5, 24, %g5
183	stb		%g5, [%o0]
184	sub		%o0, 1, %o0
185	srl		%o5, 8, %g5
186	sth		%g5, [%o0 + 2]
1871:	add		%o0, 4, %o0
1884:	sll		%o5, 24, %g6
189	ld		[%o1], %o5
190	add		%o1, 4, %o1
191	srl		%o5, 8, %g5
192	sub		%o5, %o2, %o4
193#ifdef EIGHTBIT_NOT_RARE
194	andn		%o4, %o5, %o4
195#endif
196	or		%g5, %g6, %g5
197	andcc		%o4, %o3, %g0
198	be,a		1b
199	 st		%g5, [%o0]
200	srl		%o5, 24, %o4
201	andcc		%o4, 0xff, %g0
202	be		6f
203	 srl		%o5, 16, %o4
204	andcc		%o4, 0xff, %g0
205	be		7f
206	 srl		%o5, 8, %o4
207	st		%g5, [%o0]
208	andcc		%o4, 0xff, %g0
209	be		0f
210	 andcc		%o5, 0xff, %g0
2111:	bne		4b
212	 add		%o0, 4, %o0
2139:	stb		%g0, [%o0]
2140:	retl
215	 mov		%g2, %o0
216
2176:	srl		%g5, 16, %g5
218	sth		%g5, [%o0]
219	retl
220	 mov		%g2, %o0
221
2227:	srl		%g5, 16, %g5
223	sth		%g5, [%o0]
224	stb		%g0, [%o0 + 2]
225	retl
226	 mov		%g2, %o0
227
2285:	andcc		%g5, 0xff, %g4
229	be		9b
230	 srl		%o5, 16, %g5
231	andcc		%g5, 0xff, %g0
232	be		7f
233	 srl		%o5, 8, %g5
234	andcc		%g5, 0xff, %g0
235	stb		%g4, [%o0]
236	sth		%g5, [%o0 + 1]
237	sub		%o0, 1, %o0
238	bne		1b
239	 andcc		%o5, 0xff, %g0
240	retl
241	 mov		%g2, %o0
242
2437:	stb		%g4, [%o0]
244	stb		%g0, [%o0 + 1]
245	retl
246	 mov		%g2, %o0
247
2482:	andcc		%o4, %o3, %g0
249	bne		5f
250	 srl		%o5, 16, %g5
251	sth		%g5, [%o0]
252	sub		%o0, 2, %o0
2531:	add		%o0, 4, %o0
2544:	sll		%o5, 16, %g6
255	ld		[%o1], %o5
256	add		%o1, 4, %o1
257	srl		%o5, 16, %g5
258	sub		%o5, %o2, %o4
259#ifdef EIGHTBIT_NOT_RARE
260	andn		%o4, %o5, %o4
261#endif
262	or		%g5, %g6, %g5
263	andcc		%o4, %o3, %g0
264	be,a		1b
265	 st		%g5, [%o0]
266	srl		%o5, 24, %o4
267	andcc		%o4, 0xff, %g0
268	be		7f
269	 srl		%o5, 16, %o4
270	st		%g5, [%o0]
271	andcc		%o4, 0xff, %g0
272	be		0b
273	 srl		%o5, 8, %o4
2741:	andcc		%o4, 0xff, %g0
275	be		8f
276	 andcc		%o5, 0xff, %g0
277	bne		4b
278	 add		%o0, 4, %o0
279	sth		%o5, [%o0]
280	retl
281	 mov		%g2, %o0
282
2837:	srl		%g5, 16, %g5
284	sth		%g5, [%o0]
285	stb		%g0, [%o0 + 2]
286	retl
287	 mov		%g2, %o0
288
2898:	stb		%g0, [%o0 + 4]
290	retl
291	 mov		%g2, %o0
292
2935:	srl		%o5, 24, %g5
294	andcc		%g5, 0xff, %g0
295	be		9b
296	 srl		%o5, 16, %g5
297	andcc		%g5, 0xff, %g0
298	sth		%g5, [%o0]
299	sub		%o0, 2, %o0
300	bne		1b
301	 srl		%o5, 8, %o4
302	retl
303	 mov		%g2, %o0
304
3053:	bne		5f
306	 srl		%o5, 24, %g5
307	stb		%g5, [%o0]
308	sub		%o0, 3, %o0
3091:	add		%o0, 4, %o0
3104:	sll		%o5, 8, %g6
311	ld		[%o1], %o5
312	add		%o1, 4, %o1
313	srl		%o5, 24, %g5
314	sub		%o5, %o2, %o4
315#ifdef EIGHTBIT_NOT_RARE
316	andn		%o4, %o5, %o4
317#endif
318	or		%g5, %g6, %g5
319	andcc		%o4, %o3, %g0
320	be		1b
321	 st		%g5, [%o0]
322	srl		%o5, 24, %o4
323	andcc		%o4, 0xff, %g0
324	be		0b
325	 srl		%o5, 16, %o4
3261:	andcc		%o4, 0xff, %g0
327	be		8b
328	 srl		%o5, 8, %o4
329	andcc		%o4, 0xff, %g0
330	be		9f
331	 andcc		%o5, 0xff, %g0
332	bne		4b
333	 add		%o0, 4, %o0
334	srl		%o5, 8, %o5
335	sth		%o5, [%o0]
336	stb		%g0, [%o0 + 2]
337	retl
338	 mov		%g2, %o0
3399:	srl		%o5, 8, %o5
340	sth		%o5, [%o0 + 4]
341	retl
342	 mov		%g2, %o0
3435:	andcc		%g5, 0xff, %g0
344	stb		%g5, [%o0]
345	sub		%o0, 3, %o0
346	bne		1b
347	 srl		%o5, 16, %o4
348	retl
349	 mov		%g2, %o0
350END(strcat)
351libc_hidden_builtin_def (strcat)
352