]> git.ipfire.org Git - thirdparty/glibc.git/blob - sysdeps/sparc/sparc64/strchr.S
Update.
[thirdparty/glibc.git] / sysdeps / sparc / sparc64 / strchr.S
1 /* strchr (str, ch) -- Return pointer to first occurrence of CH in STR.
2 For SPARC v9.
3 Copyright (C) 1998, 1999 Free Software Foundation, Inc.
4 This file is part of the GNU C Library.
5 Contributed by Jan Vondrak <jvon4518@ss1000.ms.mff.cuni.cz> and
6 Jakub Jelinek <jj@ultra.linux.cz>.
7
8 The GNU C Library is free software; you can redistribute it and/or
9 modify it under the terms of the GNU Library General Public License as
10 published by the Free Software Foundation; either version 2 of the
11 License, or (at your option) any later version.
12
13 The GNU C Library is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 Library General Public License for more details.
17
18 You should have received a copy of the GNU Library General Public
19 License along with the GNU C Library; see the file COPYING.LIB. If not,
20 write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
21 Boston, MA 02111-1307, USA. */
22
23 #include <sysdep.h>
24 #include <asm/asi.h>
25 #ifndef XCC
26 #define XCC xcc
27 #define USE_BPR
28 #endif
29
30 /* Normally, this uses
31 ((xword - 0x0101010101010101) & 0x8080808080808080) test
32 to find out if any byte in xword could be zero. This is fast, but
33 also gives false alarm for any byte in range 0x81-0xff. It does
34 not matter for correctness, as if this test tells us there could
35 be some zero byte, we check it byte by byte, but if bytes with
36 high bits set are common in the strings, then this will give poor
37 performance. You can #define EIGHTBIT_NOT_RARE and the algorithm
38 will use one tick slower, but more precise test
39 ((xword - 0x0101010101010101) & (~xword) & 0x8080808080808080),
40 which does not give any false alarms (but if some bits are set,
41 one cannot assume from it which bytes are zero and which are not).
42 It is yet to be measured, what is the correct default for glibc
43 in these days for an average user.
44 */
45
46 .text
47 .align 32
48 ENTRY(strchr)
49 andcc %o1, 0xff, %o1 /* IEU1 Group */
50 be,pn %icc, 17f /* CTI */
51 sllx %o1, 8, %g3 /* IEU0 Group */
52 sethi %hi(0x01010101), %g1 /* IEU1 */
53
54 or %g3, %o1, %g3 /* IEU0 Group */
55 ldub [%o0], %o3 /* Load */
56 sllx %g3, 16, %g5 /* IEU0 Group */
57 or %g1, %lo(0x01010101), %g1 /* IEU1 */
58
59 sllx %g1, 32, %g2 /* IEU0 Group */
60 brz,pn %o3, 5f /* CTI+IEU1 */
61 orcc %g3, %g5, %g3 /* IEU1 Group */
62 sllx %g3, 32, %g5 /* IEU0 */
63
64 cmp %o3, %o1 /* IEU1 Group */
65 be,pn %xcc, 14f /* CTI */
66 or %g1, %g2, %g1 /* IEU0 */
67 andcc %o0, 7, %g0 /* IEU1 Group */
68
69 bne,a,pn %icc, 15f /* CTI */
70 add %o0, 1, %o0 /* IEU0 */
71 ldx [%o0], %o3 /* Load Group */
72 1: sllx %g1, 7, %g2 /* IEU0 */
73
74 or %g3, %g5, %g3 /* IEU1 */
75 add %o0, 8, %o0 /* IEU0 Group */
76 xor %o3, %g3, %o4 /* IEU1 */
77 /* %g1 = 0101010101010101 *
78 * %g2 = 8080088080808080 *
79 * %g3 = c c c c c c c c *
80 * %o3 = value *
81 * %o4 = value XOR c */
82 2: sub %o3, %g1, %o2 /* IEU0 Group */
83
84 sub %o4, %g1, %o5 /* IEU1 */
85 #ifdef EIGHTBIT_NOT_RARE
86 andn %o2, %o3, %g7 /* IEU0 Group */
87 andn %o5, %o4, %o5 /* IEU1 */
88 ldxa [%o0] ASI_PNF, %o3 /* Load */
89 or %o5, %g7, %o5 /* IEU0 Group */
90 #else
91 ldxa [%o0] ASI_PNF, %o3 /* Load */
92 or %o5, %o2, %o5 /* IEU0 Group */
93 #endif
94 add %o0, 8, %o0 /* IEU1 */
95
96 andcc %o5, %g2, %g0 /* IEU1 Group */
97 be,a,pt %xcc, 2b /* CTI */
98 xor %o3, %g3, %o4 /* IEU0 */
99 srlx %o5, 32, %g5 /* IEU0 Group */
100
101 add %o2, %g1, %o2 /* IEU1 */
102 3: andcc %g5, %g2, %g0 /* IEU1 Group */
103 be,pn %xcc, 4f /* CTI */
104 srlx %o2, 56, %g5 /* IEU0 */
105
106 andcc %g5, 0xff, %g0 /* IEU1 Group */
107 be,pn %icc, 5f /* CTI */
108 srlx %o4, 56, %g5 /* IEU0 */
109 andcc %g5, 0xff, %g0 /* IEU1 Group */
110
111 be,pn %icc, 6f /* CTI */
112 srlx %o2, 48, %g5 /* IEU0 */
113 andcc %g5, 0xff, %g0 /* IEU1 Group */
114 be,pn %icc, 5f /* CTI */
115
116 srlx %o4, 48, %g5 /* IEU0 */
117 andcc %g5, 0xff, %g0 /* IEU1 Group */
118 be,pn %icc, 7f /* CTI */
119 srlx %o2, 40, %g5 /* IEU0 */
120
121 andcc %g5, 0xff, %g0 /* IEU1 Group */
122 be,pn %icc, 5f /* CTI */
123 srlx %o4, 40, %g5 /* IEU0 */
124 andcc %g5, 0xff, %g0 /* IEU1 Group */
125
126 be,pn %icc, 8f /* CTI */
127 srlx %o2, 32, %g5 /* IEU0 */
128 andcc %g5, 0xff, %g0 /* IEU1 Group */
129 be,pn %icc, 5f /* CTI */
130
131 srlx %o4, 32, %g5 /* IEU0 */
132 andcc %g5, 0xff, %g0 /* IEU1 Group */
133 be,pn %icc, 9f /* CTI */
134 4: srlx %o2, 24, %g5 /* IEU0 */
135
136 andcc %g5, 0xff, %g0 /* IEU1 Group */
137 be,pn %icc, 5f /* CTI */
138 srlx %o4, 24, %g5 /* IEU0 */
139 andcc %g5, 0xff, %g0 /* IEU1 Group */
140
141 be,pn %icc, 10f /* CTI */
142 srlx %o2, 16, %g5 /* IEU0 */
143 andcc %g5, 0xff, %g0 /* IEU1 Group */
144 be,pn %icc, 5f /* CTI */
145
146 srlx %o4, 16, %g5 /* IEU0 */
147 andcc %g5, 0xff, %g0 /* IEU1 Group */
148 be,pn %icc, 11f /* CTI */
149 srlx %o2, 8, %g5 /* IEU0 */
150
151 andcc %g5, 0xff, %g0 /* IEU1 Group */
152 be,pn %icc, 5f /* CTI */
153 srlx %o4, 8, %g5 /* IEU0 */
154 andcc %g5, 0xff, %g0 /* IEU1 Group */
155
156 be,pn %icc, 12f /* CTI */
157 andcc %o2, 0xff, %g0 /* IEU1 Group */
158 be,pn %icc, 5f /* CTI */
159 sub %o3, %g1, %o2 /* IEU0 */
160
161 andcc %o4, 0xff, %g0 /* IEU1 Group */
162 be,pn %icc, 13f /* CTI */
163 xor %o3, %g3, %o4 /* IEU0 */
164 ldxa [%o0] ASI_PNF, %o3 /* Load Group */
165
166 sub %o4, %g1, %o5 /* IEU0 */
167 or %o5, %o2, %o5 /* IEU1 */
168 add %o0, 8, %o0 /* IEU0 Group */
169 andcc %o5, %g2, %g0 /* IEU1 */
170
171 be,a,pt %xcc, 2b /* CTI */
172 xor %o3, %g3, %o4 /* IEU0 Group */
173 srlx %o5, 32, %g5 /* IEU0 Group */
174 ba,pt %xcc, 3b /* CTI */
175
176 add %o2, %g1, %o2 /* IEU1 */
177
178 .align 16
179 5: retl /* CTI+IEU1 Group */
180 clr %o0 /* IEU0 */
181 6: retl /* CTI+IEU1 Group */
182 add %o0, -16, %o0 /* IEU0 */
183
184 7: retl /* CTI+IEU1 Group */
185 add %o0, -15, %o0 /* IEU0 */
186 8: retl /* CTI+IEU1 Group */
187 add %o0, -14, %o0 /* IEU0 */
188
189 9: retl /* CTI+IEU1 Group */
190 add %o0, -13, %o0 /* IEU0 */
191 10: retl /* CTI+IEU1 Group */
192 add %o0, -12, %o0 /* IEU0 */
193
194 11: retl /* CTI+IEU1 Group */
195 add %o0, -11, %o0 /* IEU0 */
196 12: retl /* CTI+IEU1 Group */
197 add %o0, -10, %o0 /* IEU0 */
198
199 13: retl /* CTI+IEU1 Group */
200 add %o0, -9, %o0 /* IEU0 */
201 14: retl /* CTI+IEU1 Group */
202 nop /* IEU0 */
203
204 .align 16
205 15: ldub [%o0], %o3 /* Load Group */
206 16: andcc %o0, 7, %g0 /* IEU1 */
207 be,a,pn %icc, 1b /* CTI */
208 ldx [%o0], %o3 /* Load Group */
209
210 andcc %o3, 0xff, %g0 /* IEU1 Group */
211 be,pn %icc, 5b /* CTI */
212 add %o0, 1, %o0 /* IEU0 */
213 cmp %o3, %o1 /* IEU1 Group */
214
215 bne,a,pn %icc, 16b /* CTI */
216 ldub [%o0], %o3 /* Load */
217 retl /* CTI+IEU1 Group */
218 add %o0, -1, %o0 /* IEU0 */
219
220 /* strchr (str, 0) */
221 .align 32
222 nop
223 .align 16
224 17: sethi %hi(0x01010101), %g1 /* IEU0 Group */
225 ldub [%o0], %o3 /* Load */
226 or %g1, %lo(0x01010101), %g1 /* IEU0 Group */
227 sllx %g1, 32, %g2 /* IEU0 Group */
228
229 andcc %o0, 7, %g0 /* IEU1 */
230 or %g1, %g2, %g1 /* IEU0 Group */
231 bne,pn %icc, 32f /* CTI */
232 sllx %g1, 7, %g2 /* IEU0 Group */
233
234 brz,pn %o3, 30f /* CTI+IEU1 */
235 ldx [%o0], %o3 /* Load */
236 18: add %o0, 8, %o0 /* IEU0 Group */
237 19: sub %o3, %g1, %o2 /* IEU0 Group */
238
239 #ifdef EIGHTBIT_NOT_RARE
240 andn %o2, %o3, %g7 /* IEU0 Group */
241 ldxa [%o0] ASI_PNF, %o3 /* Load */
242 andcc %g7, %g2, %g0 /* IEU1 Group */
243 #else
244 ldxa [%o0] ASI_PNF, %o3 /* Load */
245 andcc %o2, %g2, %g0 /* IEU1 Group */
246 #endif
247 be,pt %xcc, 19b /* CTI */
248 add %o0, 8, %o0 /* IEU0 */
249
250 addcc %o2, %g1, %g3 /* IEU1 Group */
251 srlx %o2, 32, %o2 /* IEU0 */
252 20: andcc %o2, %g2, %g0 /* IEU1 Group */
253 be,pn %xcc, 21f /* CTI */
254
255 srlx %g3, 56, %o2 /* IEU0 */
256 andcc %o2, 0xff, %g0 /* IEU1 Group */
257 be,pn %icc, 29f /* CTI */
258 srlx %g3, 48, %o2 /* IEU0 */
259
260 andcc %o2, 0xff, %g0 /* IEU1 Group */
261 be,pn %icc, 28f /* CTI */
262 srlx %g3, 40, %o2 /* IEU0 */
263 andcc %o2, 0xff, %g0 /* IEU1 Group */
264
265 be,pn %icc, 27f /* CTI */
266 srlx %g3, 32, %o2 /* IEU0 */
267 andcc %o2, 0xff, %g0 /* IEU1 Group */
268 be,pn %icc, 26f /* CTI */
269
270 21: srlx %g3, 24, %o2 /* IEU0 */
271 andcc %o2, 0xff, %g0 /* IEU1 Group */
272 be,pn %icc, 25f /* CTI */
273 srlx %g3, 16, %o2 /* IEU0 */
274
275 andcc %o2, 0xff, %g0 /* IEU1 Group */
276 be,pn %icc, 24f /* CTI */
277 srlx %g3, 8, %o2 /* IEU0 */
278 andcc %o2, 0xff, %g0 /* IEU1 Group */
279
280 be,pn %icc, 23f /* CTI */
281 sub %o3, %g1, %o2 /* IEU0 */
282 andcc %g3, 0xff, %g0 /* IEU1 Group */
283 be,pn %icc, 22f /* CTI */
284
285 ldxa [%o0] ASI_PNF, %o3 /* Load */
286 andcc %o2, %g2, %g0 /* IEU1 Group */
287 be,pt %xcc, 19b /* CTI */
288 add %o0, 8, %o0 /* IEU0 */
289
290 addcc %o2, %g1, %g3 /* IEU1 Group */
291 ba,pt %xcc, 20b /* CTI */
292 srlx %o2, 32, %o2 /* IEU0 */
293
294 .align 16
295 22: retl /* CTI+IEU1 Group */
296 add %o0, -9, %o0 /* IEU0 */
297 23: retl /* CTI+IEU1 Group */
298 add %o0, -10, %o0 /* IEU0 */
299
300 24: retl /* CTI+IEU1 Group */
301 add %o0, -11, %o0 /* IEU0 */
302 25: retl /* CTI+IEU1 Group */
303 add %o0, -12, %o0 /* IEU0 */
304
305 26: retl /* CTI+IEU1 Group */
306 add %o0, -13, %o0 /* IEU0 */
307 27: retl /* CTI+IEU1 Group */
308 add %o0, -14, %o0 /* IEU0 */
309
310 28: retl /* CTI+IEU1 Group */
311 add %o0, -15, %o0 /* IEU0 */
312 29: retl /* CTI+IEU1 Group */
313 add %o0, -16, %o0 /* IEU0 */
314
315 30: retl /* CTI+IEU1 Group */
316 nop /* IEU0 */
317
318 .align 16
319 32: andcc %o0, 7, %g0 /* IEU1 Group */
320 be,a,pn %icc, 18b /* CTI */
321 ldx [%o0], %o3 /* Load */
322 add %o0, 1, %o0 /* IEU0 Group */
323
324 brnz,a,pt %o3, 32b /* CTI+IEU1 */
325 lduba [%o0] ASI_PNF, %o3 /* Load */
326 retl /* CTI+IEU1 Group */
327 add %o0, -1, %o0 /* IEU0 */
328 END(strchr)
329
330 .align 32
331 ENTRY(strrchr)
332 andcc %o1, 0xff, %o1 /* IEU1 Group */
333 be,pn %icc, 17b /* CTI */
334 clr %g4 /* IEU0 */
335 andcc %o0, 7, %g0 /* IEU1 Group */
336
337 bne,pn %icc, 13f /* CTI */
338 sllx %o1, 8, %g3 /* IEU0 */
339 ldx [%o0], %o3 /* Load Group */
340 1: sethi %hi(0x01010101), %g1 /* IEU0 */
341
342 or %g3, %o1, %g3 /* IEU1 */
343 sllx %g3, 16, %g5 /* IEU0 Group */
344 or %g1, %lo(0x01010101), %g1 /* IEU1 */
345 sllx %g1, 32, %g2 /* IEU0 Group */
346
347 or %g3, %g5, %g3 /* IEU1 */
348 sllx %g3, 32, %g5 /* IEU0 Group */
349 or %g1, %g2, %g1 /* IEU1 */
350 sllx %g1, 7, %g2 /* IEU0 Group */
351
352 or %g3, %g5, %g3 /* IEU1 */
353 add %o0, 8, %o0 /* IEU0 Group */
354 xor %o3, %g3, %o4 /* IEU1 */
355 /* %g1 = 0101010101010101 *
356 * %g2 = 8080088080808080 *
357 * %g3 = c c c c c c c c *
358 * %o3 = value *
359 * %o4 = value XOR c */
360 2: sub %o3, %g1, %o2 /* IEU0 Group */
361
362 3: sub %o4, %g1, %o5 /* IEU1 */
363 #ifdef EIGHTBIT_NOT_RARE
364 andn %o2, %o3, %g7 /* IEU0 Group */
365 andn %o5, %o4, %o5 /* IEU1 */
366 ldxa [%o0] ASI_PNF, %o3 /* Load */
367
368 or %o5, %g7, %o5 /* IEU0 Group */
369 #else
370 ldxa [%o0] ASI_PNF, %o3 /* Load */
371
372 or %o5, %o2, %o5 /* IEU0 Group */
373 #endif
374 add %o0, 8, %o0 /* IEU1 */
375 andcc %o5, %g2, %g0 /* IEU1 Group */
376 be,a,pt %xcc, 2b /* CTI */
377
378 xor %o3, %g3, %o4 /* IEU0 */
379 srlx %o5, 32, %g5 /* IEU0 Group */
380 add %o2, %g1, %o2 /* IEU1 */
381 andcc %g5, %g2, %g0 /* IEU1 Group */
382
383 be,pn %xcc, 7f /* CTI */
384 srlx %o2, 56, %g5 /* IEU0 */
385 andcc %g5, 0xff, %g0 /* IEU1 Group */
386 be,pn %icc, 12f /* CTI */
387
388 srlx %o4, 56, %g5 /* IEU0 */
389 andcc %g5, 0xff, %g0 /* IEU1 Group */
390 srlx %o2, 48, %g5 /* IEU0 */
391 be,a,pn %icc, 4f /* CTI */
392
393 add %o0, -16, %g4 /* IEU0 Group */
394 4: andcc %g5, 0xff, %g0 /* IEU1 Group */
395 be,pn %icc, 12f /* CTI */
396 srlx %o4, 48, %g5 /* IEU0 */
397
398 andcc %g5, 0xff, %g0 /* IEU1 Group */
399 srlx %o2, 40, %g5 /* IEU0 */
400 be,a,pn %icc, 5f /* CTI */
401 add %o0, -15, %g4 /* IEU0 Group */
402
403 5: andcc %g5, 0xff, %g0 /* IEU1 Group */
404 be,pn %icc, 12f /* CTI */
405 srlx %o4, 40, %g5 /* IEU0 */
406 andcc %g5, 0xff, %g0 /* IEU1 Group */
407
408 srlx %o2, 32, %g5 /* IEU0 */
409 be,a,pn %icc, 6f /* CTI */
410 add %o0, -14, %g4 /* IEU0 Group */
411 6: andcc %g5, 0xff, %g0 /* IEU1 Group */
412
413 be,pn %icc, 12f /* CTI */
414 srlx %o4, 32, %g5 /* IEU0 */
415 andcc %g5, 0xff, %g0 /* IEU1 Group */
416 be,a,pn %icc, 7f /* CTI */
417
418 add %o0, -13, %g4 /* IEU0 */
419 7: srlx %o2, 24, %g5 /* IEU0 */
420 andcc %g5, 0xff, %g0 /* IEU1 Group */
421 be,pn %icc, 12f /* CTI */
422
423 srlx %o4, 24, %g5 /* IEU0 */
424 andcc %g5, 0xff, %g0 /* IEU1 Group */
425 srlx %o2, 16, %g5 /* IEU0 */
426 be,a,pn %icc, 8f /* CTI */
427
428 add %o0, -12, %g4 /* IEU0 Group */
429 8: andcc %g5, 0xff, %g0 /* IEU1 Group */
430 be,pn %icc, 12f /* CTI */
431 srlx %o4, 16, %g5 /* IEU0 */
432
433 andcc %g5, 0xff, %g0 /* IEU1 Group */
434 srlx %o2, 8, %g5 /* IEU0 */
435 be,a,pn %icc, 9f /* CTI */
436 add %o0, -11, %g4 /* IEU0 Group */
437
438 9: andcc %g5, 0xff, %g0 /* IEU1 Group */
439 be,pn %icc, 12f /* CTI */
440 srlx %o4, 8, %g5 /* IEU0 */
441 andcc %g5, 0xff, %g0 /* IEU1 Group */
442
443 be,a,pn %icc, 10f /* CTI */
444 add %o0, -10, %g4 /* IEU0 */
445 10: andcc %o2, 0xff, %g0 /* IEU1 Group */
446 be,pn %icc, 12f /* CTI */
447
448 sub %o3, %g1, %o2 /* IEU0 */
449 andcc %o4, 0xff, %g0 /* IEU1 Group */
450 be,a,pn %icc, 11f /* CTI */
451 add %o0, -9, %g4 /* IEU0 */
452
453 11: ba,pt %xcc, 3b /* CTI Group */
454 xor %o3, %g3, %o4 /* IEU0 Group */
455 12: retl /* CTI+IEU1 Group */
456 mov %g4, %o0 /* IEU0 */
457
458 .align 16
459 13: ldub [%o0], %o3 /* Load Group */
460 add %o0, 1, %o0 /* IEU0 */
461 14: andcc %o3, 0xff, %g0 /* IEU1 Group */
462 be,pn %icc, 12b /* CTI */
463
464 cmp %o3, %o1 /* IEU1 Group */
465 ldub [%o0], %o3 /* Load */
466 be,a,pn %icc, 15f /* CTI */
467 add %o0, -1, %g4 /* IEU0 Group */
468
469 15: andcc %o0, 7, %g0 /* IEU1 Group */
470 bne,a,pt %icc, 14b /* CTI */
471 add %o0, 1, %o0 /* IEU0 */
472 ba,pt %xcc, 1b /* CTI Group */
473
474 ldx [%o0], %o3 /* Load */
475 END(strrchr)
476
477 weak_alias (strchr, index)
478 weak_alias (strrchr, rindex)