1 /* Optimized, inlined string functions. i486/x86-64 version. 2 Copyright (C) 2001-2015 Free Software Foundation, Inc. 3 This file is part of the GNU C Library. 4 5 The GNU C Library is free software; you can redistribute it and/or 6 modify it under the terms of the GNU Lesser General Public 7 License as published by the Free Software Foundation; either 8 version 2.1 of the License, or (at your option) any later version. 9 10 The GNU C Library is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 Lesser General Public License for more details. 14 15 You should have received a copy of the GNU Lesser General Public 16 License along with the GNU C Library; if not, see 17 <http://www.gnu.org/licenses/>. */ 18 19 #ifndef _STRING_H 20 # error "Never use <bits/string.h> directly; include <string.h> instead." 21 #endif 22 23 /* The ix86 processors can access unaligned multi-byte variables. */ 24 #define _STRING_ARCH_unaligned 1 25 26 /* Enable inline functions only for i486 or better when compiling for 27 ia32. */ 28 #if !defined __x86_64__ && (defined __i486__ || defined __pentium__ \ 29 || defined __pentiumpro__ || defined __pentium4__ \ 30 || defined __nocona__ || defined __atom__ \ 31 || defined __core2__ || defined __corei7__ \ 32 || defined __sandybridge__ || defined __haswell__ \ 33 || defined __bonnell__ || defined __silvermont__ \ 34 || defined __k6__ || defined __geode__ \ 35 || defined __k8__ || defined __athlon__ \ 36 || defined __amdfam10__ || defined __bdver1__ \ 37 || defined __bdver2__ || defined __bdver3__ \ 38 || defined __bdver4__ || defined __btver1__ \ 39 || defined __btver2__) 40 41 /* We only provide optimizations if the user selects them and if 42 GNU CC is used. */ 43 # if !defined __NO_STRING_INLINES && defined __USE_STRING_INLINES \ 44 && defined __GNUC__ && __GNUC__ >= 2 45 46 # ifndef __STRING_INLINE 47 # ifndef __extern_inline 48 # define __STRING_INLINE inline 49 # else 50 # define __STRING_INLINE __extern_inline 51 # endif 52 # endif 53 54 /* The macros are used in some of the optimized implementations below. */ 55 # define __STRING_SMALL_GET16(src, idx) \ 56 ((((const unsigned char *) (src))[idx + 1] << 8) \ 57 | ((const unsigned char *) (src))[idx]) 58 # define __STRING_SMALL_GET32(src, idx) \ 59 (((((const unsigned char *) (src))[idx + 3] << 8 \ 60 | ((const unsigned char *) (src))[idx + 2]) << 8 \ 61 | ((const unsigned char *) (src))[idx + 1]) << 8 \ 62 | ((const unsigned char *) (src))[idx]) 63 64 65 /* Copy N bytes of SRC to DEST. */ 66 # define _HAVE_STRING_ARCH_memcpy 1 67 # define memcpy(dest, src, n) \ 68 (__extension__ (__builtin_constant_p (n) \ 69 ? __memcpy_c ((dest), (src), (n)) \ 70 : __memcpy_g ((dest), (src), (n)))) 71 # define __memcpy_c(dest, src, n) \ 72 ((n) == 0 \ 73 ? (dest) \ 74 : (((n) % 4 == 0) \ 75 ? __memcpy_by4 (dest, src, n) \ 76 : (((n) % 2 == 0) \ 77 ? __memcpy_by2 (dest, src, n) \ 78 : __memcpy_g (dest, src, n)))) 79 80 __STRING_INLINE void *__memcpy_by4 (void *__dest, const void *__src, 81 size_t __n); 82 83 __STRING_INLINE void * 84 __memcpy_by4 (void *__dest, const void *__src, size_t __n) 85 { 86 register unsigned long int __d0, __d1; 87 register void *__tmp = __dest; 88 __asm__ __volatile__ 89 ("1:\n\t" 90 "movl (%2),%0\n\t" 91 "leal 4(%2),%2\n\t" 92 "movl %0,(%1)\n\t" 93 "leal 4(%1),%1\n\t" 94 "decl %3\n\t" 95 "jnz 1b" 96 : "=&r" (__d0), "=&r" (__tmp), "=&r" (__src), "=&r" (__d1) 97 : "1" (__tmp), "2" (__src), "3" (__n / 4) 98 : "memory", "cc"); 99 return __dest; 100 } 101 102 __STRING_INLINE void *__memcpy_by2 (void *__dest, const void *__src, 103 size_t __n); 104 105 __STRING_INLINE void * 106 __memcpy_by2 (void *__dest, const void *__src, size_t __n) 107 { 108 register unsigned long int __d0, __d1; 109 register void *__tmp = __dest; 110 __asm__ __volatile__ 111 ("shrl $1,%3\n\t" 112 "jz 2f\n" /* only a word */ 113 "1:\n\t" 114 "movl (%2),%0\n\t" 115 "leal 4(%2),%2\n\t" 116 "movl %0,(%1)\n\t" 117 "leal 4(%1),%1\n\t" 118 "decl %3\n\t" 119 "jnz 1b\n" 120 "2:\n\t" 121 "movw (%2),%w0\n\t" 122 "movw %w0,(%1)" 123 : "=&q" (__d0), "=&r" (__tmp), "=&r" (__src), "=&r" (__d1) 124 : "1" (__tmp), "2" (__src), "3" (__n / 2) 125 : "memory", "cc"); 126 return __dest; 127 } 128 129 __STRING_INLINE void *__memcpy_g (void *__dest, const void *__src, size_t __n); 130 131 __STRING_INLINE void * 132 __memcpy_g (void *__dest, const void *__src, size_t __n) 133 { 134 register unsigned long int __d0, __d1, __d2; 135 register void *__tmp = __dest; 136 __asm__ __volatile__ 137 ("cld\n\t" 138 "shrl $1,%%ecx\n\t" 139 "jnc 1f\n\t" 140 "movsb\n" 141 "1:\n\t" 142 "shrl $1,%%ecx\n\t" 143 "jnc 2f\n\t" 144 "movsw\n" 145 "2:\n\t" 146 "rep; movsl" 147 : "=&c" (__d0), "=&D" (__d1), "=&S" (__d2), 148 "=m" ( *(struct { __extension__ char __x[__n]; } *)__dest) 149 : "0" (__n), "1" (__tmp), "2" (__src), 150 "m" ( *(struct { __extension__ char __x[__n]; } *)__src) 151 : "cc"); 152 return __dest; 153 } 154 155 # define _HAVE_STRING_ARCH_memmove 1 156 # ifndef _FORCE_INLINES 157 /* Copy N bytes of SRC to DEST, guaranteeing 158 correct behavior for overlapping strings. */ 159 # define memmove(dest, src, n) __memmove_g (dest, src, n) 160 161 __STRING_INLINE void *__memmove_g (void *, const void *, size_t) 162 __asm__ ("memmove"); 163 164 __STRING_INLINE void * 165 __memmove_g (void *__dest, const void *__src, size_t __n) 166 { 167 register unsigned long int __d0, __d1, __d2; 168 register void *__tmp = __dest; 169 if (__dest < __src) 170 __asm__ __volatile__ 171 ("cld\n\t" 172 "rep; movsb" 173 : "=&c" (__d0), "=&S" (__d1), "=&D" (__d2), 174 "=m" ( *(struct { __extension__ char __x[__n]; } *)__dest) 175 : "0" (__n), "1" (__src), "2" (__tmp), 176 "m" ( *(struct { __extension__ char __x[__n]; } *)__src)); 177 else 178 __asm__ __volatile__ 179 ("decl %1\n\t" 180 "decl %2\n\t" 181 "std\n\t" 182 "rep; movsb\n\t" 183 "cld" 184 : "=&c" (__d0), "=&S" (__d1), "=&D" (__d2), 185 "=m" ( *(struct { __extension__ char __x[__n]; } *)__dest) 186 : "0" (__n), "1" (__n + (const char *) __src), 187 "2" (__n + (char *) __tmp), 188 "m" ( *(struct { __extension__ char __x[__n]; } *)__src)); 189 return __dest; 190 } 191 # endif 192 193 /* Compare N bytes of S1 and S2. */ 194 # define _HAVE_STRING_ARCH_memcmp 1 195 # ifndef _FORCE_INLINES 196 # ifndef __PIC__ 197 /* gcc has problems to spill registers when using PIC. */ 198 __STRING_INLINE int 199 memcmp (const void *__s1, const void *__s2, size_t __n) 200 { 201 register unsigned long int __d0, __d1, __d2; 202 register int __res; 203 __asm__ __volatile__ 204 ("cld\n\t" 205 "testl %3,%3\n\t" 206 "repe; cmpsb\n\t" 207 "je 1f\n\t" 208 "sbbl %0,%0\n\t" 209 "orl $1,%0\n" 210 "1:" 211 : "=&a" (__res), "=&S" (__d0), "=&D" (__d1), "=&c" (__d2) 212 : "0" (0), "1" (__s1), "2" (__s2), "3" (__n), 213 "m" ( *(struct { __extension__ char __x[__n]; } *)__s1), 214 "m" ( *(struct { __extension__ char __x[__n]; } *)__s2) 215 : "cc"); 216 return __res; 217 } 218 # endif 219 # endif 220 221 /* Set N bytes of S to C. */ 222 # define _HAVE_STRING_ARCH_memset 1 223 # define _USE_STRING_ARCH_memset 1 224 # define memset(s, c, n) \ 225 (__extension__ (__builtin_constant_p (n) && (n) <= 16 \ 226 ? ((n) == 1 \ 227 ? __memset_c1 ((s), (c)) \ 228 : __memset_gc ((s), (c), (n))) \ 229 : (__builtin_constant_p (c) \ 230 ? (__builtin_constant_p (n) \ 231 ? __memset_ccn ((s), (c), (n)) \ 232 : memset ((s), (c), (n))) \ 233 : (__builtin_constant_p (n) \ 234 ? __memset_gcn ((s), (c), (n)) \ 235 : memset ((s), (c), (n)))))) 236 237 # define __memset_c1(s, c) ({ void *__s = (s); \ 238 *((unsigned char *) __s) = (unsigned char) (c); \ 239 __s; }) 240 241 # define __memset_gc(s, c, n) \ 242 ({ void *__s = (s); \ 243 union { \ 244 unsigned int __ui; \ 245 unsigned short int __usi; \ 246 unsigned char __uc; \ 247 } *__u = __s; \ 248 unsigned int __c = ((unsigned int) ((unsigned char) (c))) * 0x01010101; \ 249 \ 250 /* We apply a trick here. `gcc' would implement the following \ 251 assignments using immediate operands. But this uses to much \ 252 memory (7, instead of 4 bytes). So we force the value in a \ 253 registers. */ \ 254 if ((n) == 3 || (n) >= 5) \ 255 __asm__ __volatile__ ("" : "=r" (__c) : "0" (__c)); \ 256 \ 257 /* This `switch' statement will be removed at compile-time. */ \ 258 switch (n) \ 259 { \ 260 case 15: \ 261 __u->__ui = __c; \ 262 __u = __extension__ ((void *) __u + 4); \ 263 case 11: \ 264 __u->__ui = __c; \ 265 __u = __extension__ ((void *) __u + 4); \ 266 case 7: \ 267 __u->__ui = __c; \ 268 __u = __extension__ ((void *) __u + 4); \ 269 case 3: \ 270 __u->__usi = (unsigned short int) __c; \ 271 __u = __extension__ ((void *) __u + 2); \ 272 __u->__uc = (unsigned char) __c; \ 273 break; \ 274 \ 275 case 14: \ 276 __u->__ui = __c; \ 277 __u = __extension__ ((void *) __u + 4); \ 278 case 10: \ 279 __u->__ui = __c; \ 280 __u = __extension__ ((void *) __u + 4); \ 281 case 6: \ 282 __u->__ui = __c; \ 283 __u = __extension__ ((void *) __u + 4); \ 284 case 2: \ 285 __u->__usi = (unsigned short int) __c; \ 286 break; \ 287 \ 288 case 13: \ 289 __u->__ui = __c; \ 290 __u = __extension__ ((void *) __u + 4); \ 291 case 9: \ 292 __u->__ui = __c; \ 293 __u = __extension__ ((void *) __u + 4); \ 294 case 5: \ 295 __u->__ui = __c; \ 296 __u = __extension__ ((void *) __u + 4); \ 297 case 1: \ 298 __u->__uc = (unsigned char) __c; \ 299 break; \ 300 \ 301 case 16: \ 302 __u->__ui = __c; \ 303 __u = __extension__ ((void *) __u + 4); \ 304 case 12: \ 305 __u->__ui = __c; \ 306 __u = __extension__ ((void *) __u + 4); \ 307 case 8: \ 308 __u->__ui = __c; \ 309 __u = __extension__ ((void *) __u + 4); \ 310 case 4: \ 311 __u->__ui = __c; \ 312 case 0: \ 313 break; \ 314 } \ 315 \ 316 __s; }) 317 318 # define __memset_ccn(s, c, n) \ 319 (((n) % 4 == 0) \ 320 ? __memset_ccn_by4 (s, ((unsigned int) ((unsigned char) (c))) * 0x01010101,\ 321 n) \ 322 : (((n) % 2 == 0) \ 323 ? __memset_ccn_by2 (s, \ 324 ((unsigned int) ((unsigned char) (c))) * 0x01010101,\ 325 n) \ 326 : memset (s, c, n))) 327 328 __STRING_INLINE void *__memset_ccn_by4 (void *__s, unsigned int __c, 329 size_t __n); 330 331 __STRING_INLINE void * 332 __memset_ccn_by4 (void *__s, unsigned int __c, size_t __n) 333 { 334 register void *__tmp = __s; 335 register unsigned long int __d0; 336 # ifdef __i686__ 337 __asm__ __volatile__ 338 ("cld\n\t" 339 "rep; stosl" 340 : "=&a" (__c), "=&D" (__tmp), "=&c" (__d0), 341 "=m" ( *(struct { __extension__ char __x[__n]; } *)__s) 342 : "0" ((unsigned int) __c), "1" (__tmp), "2" (__n / 4) 343 : "cc"); 344 # else 345 __asm__ __volatile__ 346 ("1:\n\t" 347 "movl %0,(%1)\n\t" 348 "addl $4,%1\n\t" 349 "decl %2\n\t" 350 "jnz 1b\n" 351 : "=&r" (__c), "=&r" (__tmp), "=&r" (__d0), 352 "=m" ( *(struct { __extension__ char __x[__n]; } *)__s) 353 : "0" ((unsigned int) __c), "1" (__tmp), "2" (__n / 4) 354 : "cc"); 355 # endif 356 return __s; 357 } 358 359 __STRING_INLINE void *__memset_ccn_by2 (void *__s, unsigned int __c, 360 size_t __n); 361 362 __STRING_INLINE void * 363 __memset_ccn_by2 (void *__s, unsigned int __c, size_t __n) 364 { 365 register unsigned long int __d0, __d1; 366 register void *__tmp = __s; 367 # ifdef __i686__ 368 __asm__ __volatile__ 369 ("cld\n\t" 370 "rep; stosl\n" 371 "stosw" 372 : "=&a" (__d0), "=&D" (__tmp), "=&c" (__d1), 373 "=m" ( *(struct { __extension__ char __x[__n]; } *)__s) 374 : "0" ((unsigned int) __c), "1" (__tmp), "2" (__n / 4) 375 : "cc"); 376 # else 377 __asm__ __volatile__ 378 ("1:\tmovl %0,(%1)\n\t" 379 "leal 4(%1),%1\n\t" 380 "decl %2\n\t" 381 "jnz 1b\n" 382 "movw %w0,(%1)" 383 : "=&q" (__d0), "=&r" (__tmp), "=&r" (__d1), 384 "=m" ( *(struct { __extension__ char __x[__n]; } *)__s) 385 : "0" ((unsigned int) __c), "1" (__tmp), "2" (__n / 4) 386 : "cc"); 387 #endif 388 return __s; 389 } 390 391 # define __memset_gcn(s, c, n) \ 392 (((n) % 4 == 0) \ 393 ? __memset_gcn_by4 (s, c, n) \ 394 : (((n) % 2 == 0) \ 395 ? __memset_gcn_by2 (s, c, n) \ 396 : memset (s, c, n))) 397 398 __STRING_INLINE void *__memset_gcn_by4 (void *__s, int __c, size_t __n); 399 400 __STRING_INLINE void * 401 __memset_gcn_by4 (void *__s, int __c, size_t __n) 402 { 403 register void *__tmp = __s; 404 register unsigned long int __d0; 405 __asm__ __volatile__ 406 ("movb %b0,%h0\n" 407 "pushw %w0\n\t" 408 "shll $16,%0\n\t" 409 "popw %w0\n" 410 "1:\n\t" 411 "movl %0,(%1)\n\t" 412 "addl $4,%1\n\t" 413 "decl %2\n\t" 414 "jnz 1b\n" 415 : "=&q" (__c), "=&r" (__tmp), "=&r" (__d0), 416 "=m" ( *(struct { __extension__ char __x[__n]; } *)__s) 417 : "0" ((unsigned int) __c), "1" (__tmp), "2" (__n / 4) 418 : "cc"); 419 return __s; 420 } 421 422 __STRING_INLINE void *__memset_gcn_by2 (void *__s, int __c, size_t __n); 423 424 __STRING_INLINE void * 425 __memset_gcn_by2 (void *__s, int __c, size_t __n) 426 { 427 register unsigned long int __d0, __d1; 428 register void *__tmp = __s; 429 __asm__ __volatile__ 430 ("movb %b0,%h0\n\t" 431 "pushw %w0\n\t" 432 "shll $16,%0\n\t" 433 "popw %w0\n" 434 "1:\n\t" 435 "movl %0,(%1)\n\t" 436 "leal 4(%1),%1\n\t" 437 "decl %2\n\t" 438 "jnz 1b\n" 439 "movw %w0,(%1)" 440 : "=&q" (__d0), "=&r" (__tmp), "=&r" (__d1), 441 "=m" ( *(struct { __extension__ char __x[__n]; } *)__s) 442 : "0" ((unsigned int) __c), "1" (__tmp), "2" (__n / 4) 443 : "cc"); 444 return __s; 445 } 446 447 448 /* Search N bytes of S for C. */ 449 # define _HAVE_STRING_ARCH_memchr 1 450 # ifndef _FORCE_INLINES 451 __STRING_INLINE void * 452 memchr (const void *__s, int __c, size_t __n) 453 { 454 register unsigned long int __d0; 455 # ifdef __i686__ 456 register unsigned long int __d1; 457 # endif 458 register unsigned char *__res; 459 if (__n == 0) 460 return NULL; 461 # ifdef __i686__ 462 __asm__ __volatile__ 463 ("cld\n\t" 464 "repne; scasb\n\t" 465 "cmovne %2,%0" 466 : "=D" (__res), "=&c" (__d0), "=&r" (__d1) 467 : "a" (__c), "0" (__s), "1" (__n), "2" (1), 468 "m" ( *(struct { __extension__ char __x[__n]; } *)__s) 469 : "cc"); 470 # else 471 __asm__ __volatile__ 472 ("cld\n\t" 473 "repne; scasb\n\t" 474 "je 1f\n\t" 475 "movl $1,%0\n" 476 "1:" 477 : "=D" (__res), "=&c" (__d0) 478 : "a" (__c), "0" (__s), "1" (__n), 479 "m" ( *(struct { __extension__ char __x[__n]; } *)__s) 480 : "cc"); 481 # endif 482 return __res - 1; 483 } 484 # endif 485 486 # define _HAVE_STRING_ARCH_memrchr 1 487 # ifndef _FORCE_INLINES 488 __STRING_INLINE void *__memrchr (const void *__s, int __c, size_t __n); 489 490 __STRING_INLINE void * 491 __memrchr (const void *__s, int __c, size_t __n) 492 { 493 register unsigned long int __d0; 494 # ifdef __i686__ 495 register unsigned long int __d1; 496 # endif 497 register void *__res; 498 if (__n == 0) 499 return NULL; 500 # ifdef __i686__ 501 __asm__ __volatile__ 502 ("std\n\t" 503 "repne; scasb\n\t" 504 "cmovne %2,%0\n\t" 505 "cld\n\t" 506 "incl %0" 507 : "=D" (__res), "=&c" (__d0), "=&r" (__d1) 508 : "a" (__c), "0" (__s + __n - 1), "1" (__n), "2" (-1), 509 "m" ( *(struct { __extension__ char __x[__n]; } *)__s) 510 : "cc"); 511 # else 512 __asm__ __volatile__ 513 ("std\n\t" 514 "repne; scasb\n\t" 515 "je 1f\n\t" 516 "orl $-1,%0\n" 517 "1:\tcld\n\t" 518 "incl %0" 519 : "=D" (__res), "=&c" (__d0) 520 : "a" (__c), "0" (__s + __n - 1), "1" (__n), 521 "m" ( *(struct { __extension__ char __x[__n]; } *)__s) 522 : "cc"); 523 # endif 524 return __res; 525 } 526 # ifdef __USE_GNU 527 # define memrchr(s, c, n) __memrchr ((s), (c), (n)) 528 # endif 529 # endif 530 531 /* Return pointer to C in S. */ 532 # define _HAVE_STRING_ARCH_rawmemchr 1 533 __STRING_INLINE void *__rawmemchr (const void *__s, int __c); 534 535 # ifndef _FORCE_INLINES 536 __STRING_INLINE void * 537 __rawmemchr (const void *__s, int __c) 538 { 539 register unsigned long int __d0; 540 register unsigned char *__res; 541 __asm__ __volatile__ 542 ("cld\n\t" 543 "repne; scasb\n\t" 544 : "=D" (__res), "=&c" (__d0) 545 : "a" (__c), "0" (__s), "1" (0xffffffff), 546 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 547 : "cc"); 548 return __res - 1; 549 } 550 # ifdef __USE_GNU 551 __STRING_INLINE void * 552 rawmemchr (const void *__s, int __c) 553 { 554 return __rawmemchr (__s, __c); 555 } 556 # endif /* use GNU */ 557 # endif 558 559 560 /* Return the length of S. */ 561 # define _HAVE_STRING_ARCH_strlen 1 562 # define strlen(str) \ 563 (__extension__ (__builtin_constant_p (str) \ 564 ? __builtin_strlen (str) \ 565 : __strlen_g (str))) 566 __STRING_INLINE size_t __strlen_g (const char *__str); 567 568 __STRING_INLINE size_t 569 __strlen_g (const char *__str) 570 { 571 register char __dummy; 572 register const char *__tmp = __str; 573 __asm__ __volatile__ 574 ("1:\n\t" 575 "movb (%0),%b1\n\t" 576 "leal 1(%0),%0\n\t" 577 "testb %b1,%b1\n\t" 578 "jne 1b" 579 : "=r" (__tmp), "=&q" (__dummy) 580 : "0" (__str), 581 "m" ( *(struct { char __x[0xfffffff]; } *)__str) 582 : "cc" ); 583 return __tmp - __str - 1; 584 } 585 586 587 /* Copy SRC to DEST. */ 588 # define _HAVE_STRING_ARCH_strcpy 1 589 # define strcpy(dest, src) \ 590 (__extension__ (__builtin_constant_p (src) \ 591 ? (sizeof ((src)[0]) == 1 && strlen (src) + 1 <= 8 \ 592 ? __strcpy_a_small ((dest), (src), strlen (src) + 1) \ 593 : (char *) memcpy ((char *) (dest), \ 594 (const char *) (src), \ 595 strlen (src) + 1)) \ 596 : __strcpy_g ((dest), (src)))) 597 598 # define __strcpy_a_small(dest, src, srclen) \ 599 (__extension__ ({ char *__dest = (dest); \ 600 union { \ 601 unsigned int __ui; \ 602 unsigned short int __usi; \ 603 unsigned char __uc; \ 604 char __c; \ 605 } *__u = (void *) __dest; \ 606 switch (srclen) \ 607 { \ 608 case 1: \ 609 __u->__uc = '\0'; \ 610 break; \ 611 case 2: \ 612 __u->__usi = __STRING_SMALL_GET16 (src, 0); \ 613 break; \ 614 case 3: \ 615 __u->__usi = __STRING_SMALL_GET16 (src, 0); \ 616 __u = __extension__ ((void *) __u + 2); \ 617 __u->__uc = '\0'; \ 618 break; \ 619 case 4: \ 620 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 621 break; \ 622 case 5: \ 623 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 624 __u = __extension__ ((void *) __u + 4); \ 625 __u->__uc = '\0'; \ 626 break; \ 627 case 6: \ 628 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 629 __u = __extension__ ((void *) __u + 4); \ 630 __u->__usi = __STRING_SMALL_GET16 (src, 4); \ 631 break; \ 632 case 7: \ 633 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 634 __u = __extension__ ((void *) __u + 4); \ 635 __u->__usi = __STRING_SMALL_GET16 (src, 4); \ 636 __u = __extension__ ((void *) __u + 2); \ 637 __u->__uc = '\0'; \ 638 break; \ 639 case 8: \ 640 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 641 __u = __extension__ ((void *) __u + 4); \ 642 __u->__ui = __STRING_SMALL_GET32 (src, 4); \ 643 break; \ 644 } \ 645 (char *) __dest; })) 646 647 __STRING_INLINE char *__strcpy_g (char *__dest, const char *__src); 648 649 __STRING_INLINE char * 650 __strcpy_g (char *__dest, const char *__src) 651 { 652 register char *__tmp = __dest; 653 register char __dummy; 654 __asm__ __volatile__ 655 ( 656 "1:\n\t" 657 "movb (%0),%b2\n\t" 658 "leal 1(%0),%0\n\t" 659 "movb %b2,(%1)\n\t" 660 "leal 1(%1),%1\n\t" 661 "testb %b2,%b2\n\t" 662 "jne 1b" 663 : "=&r" (__src), "=&r" (__tmp), "=&q" (__dummy), 664 "=m" ( *(struct { char __x[0xfffffff]; } *)__dest) 665 : "0" (__src), "1" (__tmp), 666 "m" ( *(struct { char __x[0xfffffff]; } *)__src) 667 : "cc"); 668 return __dest; 669 } 670 671 672 # ifdef __USE_GNU 673 # define _HAVE_STRING_ARCH_stpcpy 1 674 /* Copy SRC to DEST. */ 675 # define __stpcpy(dest, src) \ 676 (__extension__ (__builtin_constant_p (src) \ 677 ? (strlen (src) + 1 <= 8 \ 678 ? __stpcpy_a_small ((dest), (src), strlen (src) + 1) \ 679 : __stpcpy_c ((dest), (src), strlen (src) + 1)) \ 680 : __stpcpy_g ((dest), (src)))) 681 # define __stpcpy_c(dest, src, srclen) \ 682 ((srclen) % 4 == 0 \ 683 ? __mempcpy_by4 (dest, src, srclen) - 1 \ 684 : ((srclen) % 2 == 0 \ 685 ? __mempcpy_by2 (dest, src, srclen) - 1 \ 686 : __mempcpy_byn (dest, src, srclen) - 1)) 687 688 /* In glibc itself we use this symbol for namespace reasons. */ 689 # define stpcpy(dest, src) __stpcpy ((dest), (src)) 690 691 # define __stpcpy_a_small(dest, src, srclen) \ 692 (__extension__ ({ union { \ 693 unsigned int __ui; \ 694 unsigned short int __usi; \ 695 unsigned char __uc; \ 696 char __c; \ 697 } *__u = (void *) (dest); \ 698 switch (srclen) \ 699 { \ 700 case 1: \ 701 __u->__uc = '\0'; \ 702 break; \ 703 case 2: \ 704 __u->__usi = __STRING_SMALL_GET16 (src, 0); \ 705 __u = __extension__ ((void *) __u + 1); \ 706 break; \ 707 case 3: \ 708 __u->__usi = __STRING_SMALL_GET16 (src, 0); \ 709 __u = __extension__ ((void *) __u + 2); \ 710 __u->__uc = '\0'; \ 711 break; \ 712 case 4: \ 713 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 714 __u = __extension__ ((void *) __u + 3); \ 715 break; \ 716 case 5: \ 717 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 718 __u = __extension__ ((void *) __u + 4); \ 719 __u->__uc = '\0'; \ 720 break; \ 721 case 6: \ 722 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 723 __u = __extension__ ((void *) __u + 4); \ 724 __u->__usi = __STRING_SMALL_GET16 (src, 4); \ 725 __u = __extension__ ((void *) __u + 1); \ 726 break; \ 727 case 7: \ 728 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 729 __u = __extension__ ((void *) __u + 4); \ 730 __u->__usi = __STRING_SMALL_GET16 (src, 4); \ 731 __u = __extension__ ((void *) __u + 2); \ 732 __u->__uc = '\0'; \ 733 break; \ 734 case 8: \ 735 __u->__ui = __STRING_SMALL_GET32 (src, 0); \ 736 __u = __extension__ ((void *) __u + 4); \ 737 __u->__ui = __STRING_SMALL_GET32 (src, 4); \ 738 __u = __extension__ ((void *) __u + 3); \ 739 break; \ 740 } \ 741 (char *) __u; })) 742 743 __STRING_INLINE char *__mempcpy_by4 (char *__dest, const char *__src, 744 size_t __srclen); 745 746 __STRING_INLINE char * 747 __mempcpy_by4 (char *__dest, const char *__src, size_t __srclen) 748 { 749 register char *__tmp = __dest; 750 register unsigned long int __d0, __d1; 751 __asm__ __volatile__ 752 ("1:\n\t" 753 "movl (%2),%0\n\t" 754 "leal 4(%2),%2\n\t" 755 "movl %0,(%1)\n\t" 756 "leal 4(%1),%1\n\t" 757 "decl %3\n\t" 758 "jnz 1b" 759 : "=&r" (__d0), "=r" (__tmp), "=&r" (__src), "=&r" (__d1) 760 : "1" (__tmp), "2" (__src), "3" (__srclen / 4) 761 : "memory", "cc"); 762 return __tmp; 763 } 764 765 __STRING_INLINE char *__mempcpy_by2 (char *__dest, const char *__src, 766 size_t __srclen); 767 768 __STRING_INLINE char * 769 __mempcpy_by2 (char *__dest, const char *__src, size_t __srclen) 770 { 771 register char *__tmp = __dest; 772 register unsigned long int __d0, __d1; 773 __asm__ __volatile__ 774 ("shrl $1,%3\n\t" 775 "jz 2f\n" /* only a word */ 776 "1:\n\t" 777 "movl (%2),%0\n\t" 778 "leal 4(%2),%2\n\t" 779 "movl %0,(%1)\n\t" 780 "leal 4(%1),%1\n\t" 781 "decl %3\n\t" 782 "jnz 1b\n" 783 "2:\n\t" 784 "movw (%2),%w0\n\t" 785 "movw %w0,(%1)" 786 : "=&q" (__d0), "=r" (__tmp), "=&r" (__src), "=&r" (__d1), 787 "=m" ( *(struct { __extension__ char __x[__srclen]; } *)__dest) 788 : "1" (__tmp), "2" (__src), "3" (__srclen / 2), 789 "m" ( *(struct { __extension__ char __x[__srclen]; } *)__src) 790 : "cc"); 791 return __tmp + 2; 792 } 793 794 __STRING_INLINE char *__mempcpy_byn (char *__dest, const char *__src, 795 size_t __srclen); 796 797 __STRING_INLINE char * 798 __mempcpy_byn (char *__dest, const char *__src, size_t __srclen) 799 { 800 register unsigned long __d0, __d1; 801 register char *__tmp = __dest; 802 __asm__ __volatile__ 803 ("cld\n\t" 804 "shrl $1,%%ecx\n\t" 805 "jnc 1f\n\t" 806 "movsb\n" 807 "1:\n\t" 808 "shrl $1,%%ecx\n\t" 809 "jnc 2f\n\t" 810 "movsw\n" 811 "2:\n\t" 812 "rep; movsl" 813 : "=D" (__tmp), "=&c" (__d0), "=&S" (__d1), 814 "=m" ( *(struct { __extension__ char __x[__srclen]; } *)__dest) 815 : "0" (__tmp), "1" (__srclen), "2" (__src), 816 "m" ( *(struct { __extension__ char __x[__srclen]; } *)__src) 817 : "cc"); 818 return __tmp; 819 } 820 821 __STRING_INLINE char *__stpcpy_g (char *__dest, const char *__src); 822 823 __STRING_INLINE char * 824 __stpcpy_g (char *__dest, const char *__src) 825 { 826 register char *__tmp = __dest; 827 register char __dummy; 828 __asm__ __volatile__ 829 ( 830 "1:\n\t" 831 "movb (%0),%b2\n\t" 832 "leal 1(%0),%0\n\t" 833 "movb %b2,(%1)\n\t" 834 "leal 1(%1),%1\n\t" 835 "testb %b2,%b2\n\t" 836 "jne 1b" 837 : "=&r" (__src), "=r" (__tmp), "=&q" (__dummy), 838 "=m" ( *(struct { char __x[0xfffffff]; } *)__dest) 839 : "0" (__src), "1" (__tmp), 840 "m" ( *(struct { char __x[0xfffffff]; } *)__src) 841 : "cc"); 842 return __tmp - 1; 843 } 844 # endif 845 846 847 /* Copy no more than N characters of SRC to DEST. */ 848 # define _HAVE_STRING_ARCH_strncpy 1 849 # define strncpy(dest, src, n) \ 850 (__extension__ (__builtin_constant_p (src) \ 851 ? ((strlen (src) + 1 >= ((size_t) (n)) \ 852 ? (char *) memcpy ((char *) (dest), \ 853 (const char *) (src), n) \ 854 : __strncpy_cg ((dest), (src), strlen (src) + 1, n))) \ 855 : __strncpy_gg ((dest), (src), n))) 856 # define __strncpy_cg(dest, src, srclen, n) \ 857 (((srclen) % 4 == 0) \ 858 ? __strncpy_by4 (dest, src, srclen, n) \ 859 : (((srclen) % 2 == 0) \ 860 ? __strncpy_by2 (dest, src, srclen, n) \ 861 : __strncpy_byn (dest, src, srclen, n))) 862 863 __STRING_INLINE char *__strncpy_by4 (char *__dest, const char __src[], 864 size_t __srclen, size_t __n); 865 866 __STRING_INLINE char * 867 __strncpy_by4 (char *__dest, const char __src[], size_t __srclen, size_t __n) 868 { 869 register char *__tmp = __dest; 870 register int __dummy1, __dummy2; 871 __asm__ __volatile__ 872 ("1:\n\t" 873 "movl (%2),%0\n\t" 874 "leal 4(%2),%2\n\t" 875 "movl %0,(%1)\n\t" 876 "leal 4(%1),%1\n\t" 877 "decl %3\n\t" 878 "jnz 1b" 879 : "=&r" (__dummy1), "=r" (__tmp), "=&r" (__src), "=&r" (__dummy2), 880 "=m" ( *(struct { __extension__ char __x[__srclen]; } *)__dest) 881 : "1" (__tmp), "2" (__src), "3" (__srclen / 4), 882 "m" ( *(struct { __extension__ char __x[__srclen]; } *)__src) 883 : "cc"); 884 (void) memset (__tmp, '\0', __n - __srclen); 885 return __dest; 886 } 887 888 __STRING_INLINE char *__strncpy_by2 (char *__dest, const char __src[], 889 size_t __srclen, size_t __n); 890 891 __STRING_INLINE char * 892 __strncpy_by2 (char *__dest, const char __src[], size_t __srclen, size_t __n) 893 { 894 register char *__tmp = __dest; 895 register int __dummy1, __dummy2; 896 __asm__ __volatile__ 897 ("shrl $1,%3\n\t" 898 "jz 2f\n" /* only a word */ 899 "1:\n\t" 900 "movl (%2),%0\n\t" 901 "leal 4(%2),%2\n\t" 902 "movl %0,(%1)\n\t" 903 "leal 4(%1),%1\n\t" 904 "decl %3\n\t" 905 "jnz 1b\n" 906 "2:\n\t" 907 "movw (%2),%w0\n\t" 908 "movw %w0,(%1)\n\t" 909 : "=&q" (__dummy1), "=r" (__tmp), "=&r" (__src), "=&r" (__dummy2), 910 "=m" ( *(struct { __extension__ char __x[__srclen]; } *)__dest) 911 : "1" (__tmp), "2" (__src), "3" (__srclen / 2), 912 "m" ( *(struct { __extension__ char __x[__srclen]; } *)__src) 913 : "cc"); 914 (void) memset (__tmp + 2, '\0', __n - __srclen); 915 return __dest; 916 } 917 918 __STRING_INLINE char *__strncpy_byn (char *__dest, const char __src[], 919 size_t __srclen, size_t __n); 920 921 __STRING_INLINE char * 922 __strncpy_byn (char *__dest, const char __src[], size_t __srclen, size_t __n) 923 { 924 register unsigned long int __d0, __d1; 925 register char *__tmp = __dest; 926 __asm__ __volatile__ 927 ("cld\n\t" 928 "shrl $1,%1\n\t" 929 "jnc 1f\n\t" 930 "movsb\n" 931 "1:\n\t" 932 "shrl $1,%1\n\t" 933 "jnc 2f\n\t" 934 "movsw\n" 935 "2:\n\t" 936 "rep; movsl" 937 : "=D" (__tmp), "=&c" (__d0), "=&S" (__d1), 938 "=m" ( *(struct { __extension__ char __x[__srclen]; } *)__dest) 939 : "1" (__srclen), "0" (__tmp),"2" (__src), 940 "m" ( *(struct { __extension__ char __x[__srclen]; } *)__src) 941 : "cc"); 942 (void) memset (__tmp, '\0', __n - __srclen); 943 return __dest; 944 } 945 946 __STRING_INLINE char *__strncpy_gg (char *__dest, const char *__src, 947 size_t __n); 948 949 __STRING_INLINE char * 950 __strncpy_gg (char *__dest, const char *__src, size_t __n) 951 { 952 register char *__tmp = __dest; 953 register char __dummy; 954 if (__n > 0) 955 __asm__ __volatile__ 956 ("1:\n\t" 957 "movb (%0),%2\n\t" 958 "incl %0\n\t" 959 "movb %2,(%1)\n\t" 960 "incl %1\n\t" 961 "decl %3\n\t" 962 "je 3f\n\t" 963 "testb %2,%2\n\t" 964 "jne 1b\n\t" 965 "2:\n\t" 966 "movb %2,(%1)\n\t" 967 "incl %1\n\t" 968 "decl %3\n\t" 969 "jne 2b\n\t" 970 "3:" 971 : "=&r" (__src), "=&r" (__tmp), "=&q" (__dummy), "=&r" (__n) 972 : "0" (__src), "1" (__tmp), "3" (__n) 973 : "memory", "cc"); 974 975 return __dest; 976 } 977 978 979 /* Append SRC onto DEST. */ 980 # define _HAVE_STRING_ARCH_strcat 1 981 # define strcat(dest, src) \ 982 (__extension__ (__builtin_constant_p (src) \ 983 ? __strcat_c ((dest), (src), strlen (src) + 1) \ 984 : __strcat_g ((dest), (src)))) 985 986 __STRING_INLINE char *__strcat_c (char *__dest, const char __src[], 987 size_t __srclen); 988 989 __STRING_INLINE char * 990 __strcat_c (char *__dest, const char __src[], size_t __srclen) 991 { 992 # ifdef __i686__ 993 register unsigned long int __d0; 994 register char *__tmp; 995 __asm__ __volatile__ 996 ("repne; scasb" 997 : "=D" (__tmp), "=&c" (__d0), 998 "=m" ( *(struct { char __x[0xfffffff]; } *)__dest) 999 : "0" (__dest), "1" (0xffffffff), "a" (0), 1000 "m" ( *(struct { __extension__ char __x[__srclen]; } *)__src) 1001 : "cc"); 1002 --__tmp; 1003 # else 1004 register char *__tmp = __dest; 1005 __asm__ __volatile__ 1006 ("decl %0\n\t" 1007 "1:\n\t" 1008 "incl %0\n\t" 1009 "cmpb $0,(%0)\n\t" 1010 "jne 1b\n" 1011 : "=r" (__tmp), 1012 "=m" ( *(struct { char __x[0xfffffff]; } *)__dest) 1013 : "0" (__tmp), 1014 "m" ( *(struct { __extension__ char __x[__srclen]; } *)__src) 1015 : "cc"); 1016 # endif 1017 (void) memcpy (__tmp, __src, __srclen); 1018 return __dest; 1019 } 1020 1021 __STRING_INLINE char *__strcat_g (char *__dest, const char *__src); 1022 1023 __STRING_INLINE char * 1024 __strcat_g (char *__dest, const char *__src) 1025 { 1026 register char *__tmp = __dest; 1027 register char __dummy; 1028 __asm__ __volatile__ 1029 ("decl %1\n\t" 1030 "1:\n\t" 1031 "incl %1\n\t" 1032 "cmpb $0,(%1)\n\t" 1033 "jne 1b\n" 1034 "2:\n\t" 1035 "movb (%2),%b0\n\t" 1036 "incl %2\n\t" 1037 "movb %b0,(%1)\n\t" 1038 "incl %1\n\t" 1039 "testb %b0,%b0\n\t" 1040 "jne 2b\n" 1041 : "=&q" (__dummy), "=&r" (__tmp), "=&r" (__src), 1042 "=m" ( *(struct { char __x[0xfffffff]; } *)__dest) 1043 : "1" (__tmp), "2" (__src), 1044 "m" ( *(struct { char __x[0xfffffff]; } *)__src) 1045 : "memory", "cc"); 1046 return __dest; 1047 } 1048 1049 1050 /* Append no more than N characters from SRC onto DEST. */ 1051 # define _HAVE_STRING_ARCH_strncat 1 1052 # define strncat(dest, src, n) \ 1053 (__extension__ ({ char *__dest = (dest); \ 1054 __builtin_constant_p (src) && __builtin_constant_p (n) \ 1055 ? (strlen (src) < ((size_t) (n)) \ 1056 ? strcat (__dest, (src)) \ 1057 : (*(char *)__mempcpy (strchr (__dest, '\0'), \ 1058 (const char *) (src), \ 1059 (n)) = 0, __dest)) \ 1060 : __strncat_g (__dest, (src), (n)); })) 1061 1062 __STRING_INLINE char *__strncat_g (char *__dest, const char __src[], 1063 size_t __n); 1064 1065 __STRING_INLINE char * 1066 __strncat_g (char *__dest, const char __src[], size_t __n) 1067 { 1068 register char *__tmp = __dest; 1069 register char __dummy; 1070 # ifdef __i686__ 1071 __asm__ __volatile__ 1072 ("repne; scasb\n" 1073 "movl %4, %3\n\t" 1074 "decl %1\n\t" 1075 "1:\n\t" 1076 "subl $1,%3\n\t" 1077 "jc 2f\n\t" 1078 "movb (%2),%b0\n\t" 1079 "movsb\n\t" 1080 "testb %b0,%b0\n\t" 1081 "jne 1b\n\t" 1082 "decl %1\n" 1083 "2:\n\t" 1084 "movb $0,(%1)" 1085 : "=&a" (__dummy), "=&D" (__tmp), "=&S" (__src), "=&c" (__n) 1086 : "g" (__n), "0" (0), "1" (__tmp), "2" (__src), "3" (0xffffffff) 1087 : "memory", "cc"); 1088 # else 1089 --__tmp; 1090 __asm__ __volatile__ 1091 ("1:\n\t" 1092 "cmpb $0,1(%1)\n\t" 1093 "leal 1(%1),%1\n\t" 1094 "jne 1b\n" 1095 "2:\n\t" 1096 "subl $1,%3\n\t" 1097 "jc 3f\n\t" 1098 "movb (%2),%b0\n\t" 1099 "leal 1(%2),%2\n\t" 1100 "movb %b0,(%1)\n\t" 1101 "leal 1(%1),%1\n\t" 1102 "testb %b0,%b0\n\t" 1103 "jne 2b\n\t" 1104 "decl %1\n" 1105 "3:\n\t" 1106 "movb $0,(%1)" 1107 : "=&q" (__dummy), "=&r" (__tmp), "=&r" (__src), "=&r" (__n) 1108 : "1" (__tmp), "2" (__src), "3" (__n) 1109 : "memory", "cc"); 1110 #endif 1111 return __dest; 1112 } 1113 1114 1115 /* Compare S1 and S2. */ 1116 # define _HAVE_STRING_ARCH_strcmp 1 1117 # define strcmp(s1, s2) \ 1118 (__extension__ (__builtin_constant_p (s1) && __builtin_constant_p (s2) \ 1119 && (sizeof ((s1)[0]) != 1 || strlen (s1) >= 4) \ 1120 && (sizeof ((s2)[0]) != 1 || strlen (s2) >= 4) \ 1121 ? memcmp ((const char *) (s1), (const char *) (s2), \ 1122 (strlen (s1) < strlen (s2) \ 1123 ? strlen (s1) : strlen (s2)) + 1) \ 1124 : (__builtin_constant_p (s1) && sizeof ((s1)[0]) == 1 \ 1125 && sizeof ((s2)[0]) == 1 && strlen (s1) < 4 \ 1126 ? (__builtin_constant_p (s2) && sizeof ((s2)[0]) == 1 \ 1127 ? __strcmp_cc ((const unsigned char *) (s1), \ 1128 (const unsigned char *) (s2), \ 1129 strlen (s1)) \ 1130 : __strcmp_cg ((const unsigned char *) (s1), \ 1131 (const unsigned char *) (s2), \ 1132 strlen (s1))) \ 1133 : (__builtin_constant_p (s2) && sizeof ((s1)[0]) == 1 \ 1134 && sizeof ((s2)[0]) == 1 && strlen (s2) < 4 \ 1135 ? (__builtin_constant_p (s1) \ 1136 ? __strcmp_cc ((const unsigned char *) (s1), \ 1137 (const unsigned char *) (s2), \ 1138 strlen (s2)) \ 1139 : __strcmp_gc ((const unsigned char *) (s1), \ 1140 (const unsigned char *) (s2), \ 1141 strlen (s2))) \ 1142 : __strcmp_gg ((s1), (s2)))))) 1143 1144 # define __strcmp_cc(s1, s2, l) \ 1145 (__extension__ ({ register int __result = (s1)[0] - (s2)[0]; \ 1146 if (l > 0 && __result == 0) \ 1147 { \ 1148 __result = (s1)[1] - (s2)[1]; \ 1149 if (l > 1 && __result == 0) \ 1150 { \ 1151 __result = (s1)[2] - (s2)[2]; \ 1152 if (l > 2 && __result == 0) \ 1153 __result = (s1)[3] - (s2)[3]; \ 1154 } \ 1155 } \ 1156 __result; })) 1157 1158 # define __strcmp_cg(s1, s2, l1) \ 1159 (__extension__ ({ const unsigned char *__s2 = (s2); \ 1160 register int __result = (s1)[0] - __s2[0]; \ 1161 if (l1 > 0 && __result == 0) \ 1162 { \ 1163 __result = (s1)[1] - __s2[1]; \ 1164 if (l1 > 1 && __result == 0) \ 1165 { \ 1166 __result = (s1)[2] - __s2[2]; \ 1167 if (l1 > 2 && __result == 0) \ 1168 __result = (s1)[3] - __s2[3]; \ 1169 } \ 1170 } \ 1171 __result; })) 1172 1173 # define __strcmp_gc(s1, s2, l2) \ 1174 (__extension__ ({ const unsigned char *__s1 = (s1); \ 1175 register int __result = __s1[0] - (s2)[0]; \ 1176 if (l2 > 0 && __result == 0) \ 1177 { \ 1178 __result = __s1[1] - (s2)[1]; \ 1179 if (l2 > 1 && __result == 0) \ 1180 { \ 1181 __result = __s1[2] - (s2)[2]; \ 1182 if (l2 > 2 && __result == 0) \ 1183 __result = __s1[3] - (s2)[3]; \ 1184 } \ 1185 } \ 1186 __result; })) 1187 1188 __STRING_INLINE int __strcmp_gg (const char *__s1, const char *__s2); 1189 1190 __STRING_INLINE int 1191 __strcmp_gg (const char *__s1, const char *__s2) 1192 { 1193 register int __res; 1194 __asm__ __volatile__ 1195 ("1:\n\t" 1196 "movb (%1),%b0\n\t" 1197 "leal 1(%1),%1\n\t" 1198 "cmpb %b0,(%2)\n\t" 1199 "jne 2f\n\t" 1200 "leal 1(%2),%2\n\t" 1201 "testb %b0,%b0\n\t" 1202 "jne 1b\n\t" 1203 "xorl %0,%0\n\t" 1204 "jmp 3f\n" 1205 "2:\n\t" 1206 "movl $1,%0\n\t" 1207 "jb 3f\n\t" 1208 "negl %0\n" 1209 "3:" 1210 : "=q" (__res), "=&r" (__s1), "=&r" (__s2) 1211 : "1" (__s1), "2" (__s2), 1212 "m" ( *(struct { char __x[0xfffffff]; } *)__s1), 1213 "m" ( *(struct { char __x[0xfffffff]; } *)__s2) 1214 : "cc"); 1215 return __res; 1216 } 1217 1218 1219 /* Compare N characters of S1 and S2. */ 1220 # define _HAVE_STRING_ARCH_strncmp 1 1221 # define strncmp(s1, s2, n) \ 1222 (__extension__ (__builtin_constant_p (s1) && strlen (s1) < ((size_t) (n)) \ 1223 ? strcmp ((s1), (s2)) \ 1224 : (__builtin_constant_p (s2) && strlen (s2) < ((size_t) (n))\ 1225 ? strcmp ((s1), (s2)) \ 1226 : __strncmp_g ((s1), (s2), (n))))) 1227 1228 __STRING_INLINE int __strncmp_g (const char *__s1, const char *__s2, 1229 size_t __n); 1230 1231 __STRING_INLINE int 1232 __strncmp_g (const char *__s1, const char *__s2, size_t __n) 1233 { 1234 register int __res; 1235 __asm__ __volatile__ 1236 ("1:\n\t" 1237 "subl $1,%3\n\t" 1238 "jc 2f\n\t" 1239 "movb (%1),%b0\n\t" 1240 "incl %1\n\t" 1241 "cmpb %b0,(%2)\n\t" 1242 "jne 3f\n\t" 1243 "incl %2\n\t" 1244 "testb %b0,%b0\n\t" 1245 "jne 1b\n" 1246 "2:\n\t" 1247 "xorl %0,%0\n\t" 1248 "jmp 4f\n" 1249 "3:\n\t" 1250 "movl $1,%0\n\t" 1251 "jb 4f\n\t" 1252 "negl %0\n" 1253 "4:" 1254 : "=q" (__res), "=&r" (__s1), "=&r" (__s2), "=&r" (__n) 1255 : "1" (__s1), "2" (__s2), "3" (__n), 1256 "m" ( *(struct { __extension__ char __x[__n]; } *)__s1), 1257 "m" ( *(struct { __extension__ char __x[__n]; } *)__s2) 1258 : "cc"); 1259 return __res; 1260 } 1261 1262 1263 /* Find the first occurrence of C in S. */ 1264 # define _HAVE_STRING_ARCH_strchr 1 1265 # define _USE_STRING_ARCH_strchr 1 1266 # define strchr(s, c) \ 1267 (__extension__ (__builtin_constant_p (c) \ 1268 ? ((c) == '\0' \ 1269 ? (char *) __rawmemchr ((s), (c)) \ 1270 : __strchr_c ((s), ((c) & 0xff) << 8)) \ 1271 : __strchr_g ((s), (c)))) 1272 1273 __STRING_INLINE char *__strchr_c (const char *__s, int __c); 1274 1275 __STRING_INLINE char * 1276 __strchr_c (const char *__s, int __c) 1277 { 1278 register unsigned long int __d0; 1279 register char *__res; 1280 __asm__ __volatile__ 1281 ("1:\n\t" 1282 "movb (%0),%%al\n\t" 1283 "cmpb %%ah,%%al\n\t" 1284 "je 2f\n\t" 1285 "leal 1(%0),%0\n\t" 1286 "testb %%al,%%al\n\t" 1287 "jne 1b\n\t" 1288 "xorl %0,%0\n" 1289 "2:" 1290 : "=r" (__res), "=&a" (__d0) 1291 : "0" (__s), "1" (__c), 1292 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1293 : "cc"); 1294 return __res; 1295 } 1296 1297 __STRING_INLINE char *__strchr_g (const char *__s, int __c); 1298 1299 __STRING_INLINE char * 1300 __strchr_g (const char *__s, int __c) 1301 { 1302 register unsigned long int __d0; 1303 register char *__res; 1304 __asm__ __volatile__ 1305 ("movb %%al,%%ah\n" 1306 "1:\n\t" 1307 "movb (%0),%%al\n\t" 1308 "cmpb %%ah,%%al\n\t" 1309 "je 2f\n\t" 1310 "leal 1(%0),%0\n\t" 1311 "testb %%al,%%al\n\t" 1312 "jne 1b\n\t" 1313 "xorl %0,%0\n" 1314 "2:" 1315 : "=r" (__res), "=&a" (__d0) 1316 : "0" (__s), "1" (__c), 1317 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1318 : "cc"); 1319 return __res; 1320 } 1321 1322 1323 /* Find the first occurrence of C in S or the final NUL byte. */ 1324 # define _HAVE_STRING_ARCH_strchrnul 1 1325 # define __strchrnul(s, c) \ 1326 (__extension__ (__builtin_constant_p (c) \ 1327 ? ((c) == '\0' \ 1328 ? (char *) __rawmemchr ((s), c) \ 1329 : __strchrnul_c ((s), ((c) & 0xff) << 8)) \ 1330 : __strchrnul_g ((s), c))) 1331 1332 __STRING_INLINE char *__strchrnul_c (const char *__s, int __c); 1333 1334 __STRING_INLINE char * 1335 __strchrnul_c (const char *__s, int __c) 1336 { 1337 register unsigned long int __d0; 1338 register char *__res; 1339 __asm__ __volatile__ 1340 ("1:\n\t" 1341 "movb (%0),%%al\n\t" 1342 "cmpb %%ah,%%al\n\t" 1343 "je 2f\n\t" 1344 "leal 1(%0),%0\n\t" 1345 "testb %%al,%%al\n\t" 1346 "jne 1b\n\t" 1347 "decl %0\n" 1348 "2:" 1349 : "=r" (__res), "=&a" (__d0) 1350 : "0" (__s), "1" (__c), 1351 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1352 : "cc"); 1353 return __res; 1354 } 1355 1356 __STRING_INLINE char *__strchrnul_g (const char *__s, int __c); 1357 1358 __STRING_INLINE char * 1359 __strchrnul_g (const char *__s, int __c) 1360 { 1361 register unsigned long int __d0; 1362 register char *__res; 1363 __asm__ __volatile__ 1364 ("movb %%al,%%ah\n" 1365 "1:\n\t" 1366 "movb (%0),%%al\n\t" 1367 "cmpb %%ah,%%al\n\t" 1368 "je 2f\n\t" 1369 "leal 1(%0),%0\n\t" 1370 "testb %%al,%%al\n\t" 1371 "jne 1b\n\t" 1372 "decl %0\n" 1373 "2:" 1374 : "=r" (__res), "=&a" (__d0) 1375 : "0" (__s), "1" (__c), 1376 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1377 : "cc"); 1378 return __res; 1379 } 1380 # ifdef __USE_GNU 1381 # define strchrnul(s, c) __strchrnul ((s), (c)) 1382 # endif 1383 1384 1385 # if defined __USE_MISC || defined __USE_XOPEN_EXTENDED 1386 /* Find the first occurrence of C in S. This is the BSD name. */ 1387 # define _HAVE_STRING_ARCH_index 1 1388 # define index(s, c) \ 1389 (__extension__ (__builtin_constant_p (c) \ 1390 ? __strchr_c ((s), ((c) & 0xff) << 8) \ 1391 : __strchr_g ((s), (c)))) 1392 # endif 1393 1394 1395 /* Find the last occurrence of C in S. */ 1396 # define _HAVE_STRING_ARCH_strrchr 1 1397 # define strrchr(s, c) \ 1398 (__extension__ (__builtin_constant_p (c) \ 1399 ? __strrchr_c ((s), ((c) & 0xff) << 8) \ 1400 : __strrchr_g ((s), (c)))) 1401 1402 # ifdef __i686__ 1403 __STRING_INLINE char *__strrchr_c (const char *__s, int __c); 1404 1405 __STRING_INLINE char * 1406 __strrchr_c (const char *__s, int __c) 1407 { 1408 register unsigned long int __d0, __d1; 1409 register char *__res; 1410 __asm__ __volatile__ 1411 ("cld\n" 1412 "1:\n\t" 1413 "lodsb\n\t" 1414 "cmpb %h2,%b2\n\t" 1415 "cmove %1,%0\n\t" 1416 "testb %b2,%b2\n\t" 1417 "jne 1b" 1418 : "=d" (__res), "=&S" (__d0), "=&a" (__d1) 1419 : "0" (1), "1" (__s), "2" (__c), 1420 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1421 : "cc"); 1422 return __res - 1; 1423 } 1424 1425 __STRING_INLINE char *__strrchr_g (const char *__s, int __c); 1426 1427 __STRING_INLINE char * 1428 __strrchr_g (const char *__s, int __c) 1429 { 1430 register unsigned long int __d0, __d1; 1431 register char *__res; 1432 __asm__ __volatile__ 1433 ("movb %b2,%h2\n" 1434 "cld\n\t" 1435 "1:\n\t" 1436 "lodsb\n\t" 1437 "cmpb %h2,%b2\n\t" 1438 "cmove %1,%0\n\t" 1439 "testb %b2,%b2\n\t" 1440 "jne 1b" 1441 : "=d" (__res), "=&S" (__d0), "=&a" (__d1) 1442 : "0" (1), "1" (__s), "2" (__c), 1443 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1444 : "cc"); 1445 return __res - 1; 1446 } 1447 # else 1448 __STRING_INLINE char *__strrchr_c (const char *__s, int __c); 1449 1450 __STRING_INLINE char * 1451 __strrchr_c (const char *__s, int __c) 1452 { 1453 register unsigned long int __d0, __d1; 1454 register char *__res; 1455 __asm__ __volatile__ 1456 ("cld\n" 1457 "1:\n\t" 1458 "lodsb\n\t" 1459 "cmpb %%ah,%%al\n\t" 1460 "jne 2f\n\t" 1461 "leal -1(%%esi),%0\n" 1462 "2:\n\t" 1463 "testb %%al,%%al\n\t" 1464 "jne 1b" 1465 : "=d" (__res), "=&S" (__d0), "=&a" (__d1) 1466 : "0" (0), "1" (__s), "2" (__c), 1467 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1468 : "cc"); 1469 return __res; 1470 } 1471 1472 __STRING_INLINE char *__strrchr_g (const char *__s, int __c); 1473 1474 __STRING_INLINE char * 1475 __strrchr_g (const char *__s, int __c) 1476 { 1477 register unsigned long int __d0, __d1; 1478 register char *__res; 1479 __asm__ __volatile__ 1480 ("movb %%al,%%ah\n" 1481 "cld\n\t" 1482 "1:\n\t" 1483 "lodsb\n\t" 1484 "cmpb %%ah,%%al\n\t" 1485 "jne 2f\n\t" 1486 "leal -1(%%esi),%0\n" 1487 "2:\n\t" 1488 "testb %%al,%%al\n\t" 1489 "jne 1b" 1490 : "=r" (__res), "=&S" (__d0), "=&a" (__d1) 1491 : "0" (0), "1" (__s), "2" (__c), 1492 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1493 : "cc"); 1494 return __res; 1495 } 1496 # endif 1497 1498 1499 # if defined __USE_MISC || defined __USE_XOPEN_EXTENDED 1500 /* Find the last occurrence of C in S. This is the BSD name. */ 1501 # define _HAVE_STRING_ARCH_rindex 1 1502 # define rindex(s, c) \ 1503 (__extension__ (__builtin_constant_p (c) \ 1504 ? __strrchr_c ((s), ((c) & 0xff) << 8) \ 1505 : __strrchr_g ((s), (c)))) 1506 # endif 1507 1508 1509 /* Return the length of the initial segment of S which 1510 consists entirely of characters not in REJECT. */ 1511 # define _HAVE_STRING_ARCH_strcspn 1 1512 # define strcspn(s, reject) \ 1513 (__extension__ (__builtin_constant_p (reject) && sizeof ((reject)[0]) == 1 \ 1514 ? ((reject)[0] == '\0' \ 1515 ? strlen (s) \ 1516 : ((reject)[1] == '\0' \ 1517 ? __strcspn_c1 ((s), (((reject)[0] << 8) & 0xff00)) \ 1518 : __strcspn_cg ((s), (reject), strlen (reject)))) \ 1519 : __strcspn_g ((s), (reject)))) 1520 1521 __STRING_INLINE size_t __strcspn_c1 (const char *__s, int __reject); 1522 1523 # ifndef _FORCE_INLINES 1524 __STRING_INLINE size_t 1525 __strcspn_c1 (const char *__s, int __reject) 1526 { 1527 register unsigned long int __d0; 1528 register char *__res; 1529 __asm__ __volatile__ 1530 ("1:\n\t" 1531 "movb (%0),%%al\n\t" 1532 "leal 1(%0),%0\n\t" 1533 "cmpb %%ah,%%al\n\t" 1534 "je 2f\n\t" 1535 "testb %%al,%%al\n\t" 1536 "jne 1b\n" 1537 "2:" 1538 : "=r" (__res), "=&a" (__d0) 1539 : "0" (__s), "1" (__reject), 1540 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1541 : "cc"); 1542 return (__res - 1) - __s; 1543 } 1544 # endif 1545 1546 __STRING_INLINE size_t __strcspn_cg (const char *__s, const char __reject[], 1547 size_t __reject_len); 1548 1549 __STRING_INLINE size_t 1550 __strcspn_cg (const char *__s, const char __reject[], size_t __reject_len) 1551 { 1552 register unsigned long int __d0, __d1, __d2; 1553 register const char *__res; 1554 __asm__ __volatile__ 1555 ("cld\n" 1556 "1:\n\t" 1557 "lodsb\n\t" 1558 "testb %%al,%%al\n\t" 1559 "je 2f\n\t" 1560 "movl %5,%%edi\n\t" 1561 "movl %6,%%ecx\n\t" 1562 "repne; scasb\n\t" 1563 "jne 1b\n" 1564 "2:" 1565 : "=S" (__res), "=&a" (__d0), "=&c" (__d1), "=&D" (__d2) 1566 : "0" (__s), "d" (__reject), "g" (__reject_len) 1567 : "memory", "cc"); 1568 return (__res - 1) - __s; 1569 } 1570 1571 __STRING_INLINE size_t __strcspn_g (const char *__s, const char *__reject); 1572 # ifdef __PIC__ 1573 1574 __STRING_INLINE size_t 1575 __strcspn_g (const char *__s, const char *__reject) 1576 { 1577 register unsigned long int __d0, __d1, __d2; 1578 register const char *__res; 1579 __asm__ __volatile__ 1580 ("pushl %%ebx\n\t" 1581 "movl %4,%%edi\n\t" 1582 "cld\n\t" 1583 "repne; scasb\n\t" 1584 "notl %%ecx\n\t" 1585 "leal -1(%%ecx),%%ebx\n" 1586 "1:\n\t" 1587 "lodsb\n\t" 1588 "testb %%al,%%al\n\t" 1589 "je 2f\n\t" 1590 "movl %4,%%edi\n\t" 1591 "movl %%ebx,%%ecx\n\t" 1592 "repne; scasb\n\t" 1593 "jne 1b\n" 1594 "2:\n\t" 1595 "popl %%ebx" 1596 : "=S" (__res), "=&a" (__d0), "=&c" (__d1), "=&D" (__d2) 1597 : "r" (__reject), "0" (__s), "1" (0), "2" (0xffffffff) 1598 : "memory", "cc"); 1599 return (__res - 1) - __s; 1600 } 1601 # else 1602 __STRING_INLINE size_t 1603 __strcspn_g (const char *__s, const char *__reject) 1604 { 1605 register unsigned long int __d0, __d1, __d2, __d3; 1606 register const char *__res; 1607 __asm__ __volatile__ 1608 ("cld\n\t" 1609 "repne; scasb\n\t" 1610 "notl %%ecx\n\t" 1611 "leal -1(%%ecx),%%edx\n" 1612 "1:\n\t" 1613 "lodsb\n\t" 1614 "testb %%al,%%al\n\t" 1615 "je 2f\n\t" 1616 "movl %%ebx,%%edi\n\t" 1617 "movl %%edx,%%ecx\n\t" 1618 "repne; scasb\n\t" 1619 "jne 1b\n" 1620 "2:" 1621 : "=S" (__res), "=&a" (__d0), "=&c" (__d1), "=&D" (__d2), "=&d" (__d3) 1622 : "0" (__s), "1" (0), "2" (0xffffffff), "3" (__reject), "b" (__reject) 1623 /* Clobber memory, otherwise GCC cannot handle this. */ 1624 : "memory", "cc"); 1625 return (__res - 1) - __s; 1626 } 1627 # endif 1628 1629 1630 /* Return the length of the initial segment of S which 1631 consists entirely of characters in ACCEPT. */ 1632 # define _HAVE_STRING_ARCH_strspn 1 1633 # define strspn(s, accept) \ 1634 (__extension__ (__builtin_constant_p (accept) && sizeof ((accept)[0]) == 1 \ 1635 ? ((accept)[0] == '\0' \ 1636 ? ((void) (s), 0) \ 1637 : ((accept)[1] == '\0' \ 1638 ? __strspn_c1 ((s), (((accept)[0] << 8 ) & 0xff00)) \ 1639 : __strspn_cg ((s), (accept), strlen (accept)))) \ 1640 : __strspn_g ((s), (accept)))) 1641 1642 # ifndef _FORCE_INLINES 1643 __STRING_INLINE size_t __strspn_c1 (const char *__s, int __accept); 1644 1645 __STRING_INLINE size_t 1646 __strspn_c1 (const char *__s, int __accept) 1647 { 1648 register unsigned long int __d0; 1649 register char *__res; 1650 /* Please note that __accept never can be '\0'. */ 1651 __asm__ __volatile__ 1652 ("1:\n\t" 1653 "movb (%0),%b1\n\t" 1654 "leal 1(%0),%0\n\t" 1655 "cmpb %h1,%b1\n\t" 1656 "je 1b" 1657 : "=r" (__res), "=&q" (__d0) 1658 : "0" (__s), "1" (__accept), 1659 "m" ( *(struct { char __x[0xfffffff]; } *)__s) 1660 : "cc"); 1661 return (__res - 1) - __s; 1662 } 1663 # endif 1664 1665 __STRING_INLINE size_t __strspn_cg (const char *__s, const char __accept[], 1666 size_t __accept_len); 1667 1668 __STRING_INLINE size_t 1669 __strspn_cg (const char *__s, const char __accept[], size_t __accept_len) 1670 { 1671 register unsigned long int __d0, __d1, __d2; 1672 register const char *__res; 1673 __asm__ __volatile__ 1674 ("cld\n" 1675 "1:\n\t" 1676 "lodsb\n\t" 1677 "testb %%al,%%al\n\t" 1678 "je 2f\n\t" 1679 "movl %5,%%edi\n\t" 1680 "movl %6,%%ecx\n\t" 1681 "repne; scasb\n\t" 1682 "je 1b\n" 1683 "2:" 1684 : "=S" (__res), "=&a" (__d0), "=&c" (__d1), "=&D" (__d2) 1685 : "0" (__s), "g" (__accept), "g" (__accept_len), 1686 /* Since we do not know how large the memory we access it, use a 1687 really large amount. */ 1688 "m" ( *(struct { char __x[0xfffffff]; } *)__s), 1689 "m" ( *(struct { __extension__ char __x[__accept_len]; } *)__accept) 1690 : "cc"); 1691 return (__res - 1) - __s; 1692 } 1693 1694 __STRING_INLINE size_t __strspn_g (const char *__s, const char *__accept); 1695 # ifdef __PIC__ 1696 1697 __STRING_INLINE size_t 1698 __strspn_g (const char *__s, const char *__accept) 1699 { 1700 register unsigned long int __d0, __d1, __d2; 1701 register const char *__res; 1702 __asm__ __volatile__ 1703 ("pushl %%ebx\n\t" 1704 "cld\n\t" 1705 "repne; scasb\n\t" 1706 "notl %%ecx\n\t" 1707 "leal -1(%%ecx),%%ebx\n" 1708 "1:\n\t" 1709 "lodsb\n\t" 1710 "testb %%al,%%al\n\t" 1711 "je 2f\n\t" 1712 "movl %%edx,%%edi\n\t" 1713 "movl %%ebx,%%ecx\n\t" 1714 "repne; scasb\n\t" 1715 "je 1b\n" 1716 "2:\n\t" 1717 "popl %%ebx" 1718 : "=S" (__res), "=&a" (__d0), "=&c" (__d1), "=&D" (__d2) 1719 : "d" (__accept), "0" (__s), "1" (0), "2" (0xffffffff), "3" (__accept) 1720 : "memory", "cc"); 1721 return (__res - 1) - __s; 1722 } 1723 # else 1724 __STRING_INLINE size_t 1725 __strspn_g (const char *__s, const char *__accept) 1726 { 1727 register unsigned long int __d0, __d1, __d2, __d3; 1728 register const char *__res; 1729 __asm__ __volatile__ 1730 ("cld\n\t" 1731 "repne; scasb\n\t" 1732 "notl %%ecx\n\t" 1733 "leal -1(%%ecx),%%edx\n" 1734 "1:\n\t" 1735 "lodsb\n\t" 1736 "testb %%al,%%al\n\t" 1737 "je 2f\n\t" 1738 "movl %%ebx,%%edi\n\t" 1739 "movl %%edx,%%ecx\n\t" 1740 "repne; scasb\n\t" 1741 "je 1b\n" 1742 "2:" 1743 : "=S" (__res), "=&a" (__d0), "=&c" (__d1), "=&D" (__d2), "=&d" (__d3) 1744 : "0" (__s), "1" (0), "2" (0xffffffff), "3" (__accept), "b" (__accept) 1745 : "memory", "cc"); 1746 return (__res - 1) - __s; 1747 } 1748 # endif 1749 1750 1751 /* Find the first occurrence in S of any character in ACCEPT. */ 1752 # define _HAVE_STRING_ARCH_strpbrk 1 1753 # define strpbrk(s, accept) \ 1754 (__extension__ (__builtin_constant_p (accept) && sizeof ((accept)[0]) == 1 \ 1755 ? ((accept)[0] == '\0' \ 1756 ? ((void) (s), (char *) 0) \ 1757 : ((accept)[1] == '\0' \ 1758 ? strchr ((s), (accept)[0]) \ 1759 : __strpbrk_cg ((s), (accept), strlen (accept)))) \ 1760 : __strpbrk_g ((s), (accept)))) 1761 1762 __STRING_INLINE char *__strpbrk_cg (const char *__s, const char __accept[], 1763 size_t __accept_len); 1764 1765 __STRING_INLINE char * 1766 __strpbrk_cg (const char *__s, const char __accept[], size_t __accept_len) 1767 { 1768 register unsigned long int __d0, __d1, __d2; 1769 register char *__res; 1770 __asm__ __volatile__ 1771 ("cld\n" 1772 "1:\n\t" 1773 "lodsb\n\t" 1774 "testb %%al,%%al\n\t" 1775 "je 2f\n\t" 1776 "movl %5,%%edi\n\t" 1777 "movl %6,%%ecx\n\t" 1778 "repne; scasb\n\t" 1779 "jne 1b\n\t" 1780 "decl %0\n\t" 1781 "jmp 3f\n" 1782 "2:\n\t" 1783 "xorl %0,%0\n" 1784 "3:" 1785 : "=S" (__res), "=&a" (__d0), "=&c" (__d1), "=&D" (__d2) 1786 : "0" (__s), "d" (__accept), "g" (__accept_len) 1787 : "memory", "cc"); 1788 return __res; 1789 } 1790 1791 __STRING_INLINE char *__strpbrk_g (const char *__s, const char *__accept); 1792 # ifdef __PIC__ 1793 1794 __STRING_INLINE char * 1795 __strpbrk_g (const char *__s, const char *__accept) 1796 { 1797 register unsigned long int __d0, __d1, __d2; 1798 register char *__res; 1799 __asm__ __volatile__ 1800 ("pushl %%ebx\n\t" 1801 "movl %%edx,%%edi\n\t" 1802 "cld\n\t" 1803 "repne; scasb\n\t" 1804 "notl %%ecx\n\t" 1805 "leal -1(%%ecx),%%ebx\n" 1806 "1:\n\t" 1807 "lodsb\n\t" 1808 "testb %%al,%%al\n\t" 1809 "je 2f\n\t" 1810 "movl %%edx,%%edi\n\t" 1811 "movl %%ebx,%%ecx\n\t" 1812 "repne; scasb\n\t" 1813 "jne 1b\n\t" 1814 "decl %0\n\t" 1815 "jmp 3f\n" 1816 "2:\n\t" 1817 "xorl %0,%0\n" 1818 "3:\n\t" 1819 "popl %%ebx" 1820 : "=S" (__res), "=&a" (__d0), "=&c" (__d1), "=&D" (__d2) 1821 : "d" (__accept), "0" (__s), "1" (0), "2" (0xffffffff) 1822 : "memory", "cc"); 1823 return __res; 1824 } 1825 # else 1826 __STRING_INLINE char * 1827 __strpbrk_g (const char *__s, const char *__accept) 1828 { 1829 register unsigned long int __d0, __d1, __d2, __d3; 1830 register char *__res; 1831 __asm__ __volatile__ 1832 ("movl %%ebx,%%edi\n\t" 1833 "cld\n\t" 1834 "repne; scasb\n\t" 1835 "notl %%ecx\n\t" 1836 "leal -1(%%ecx),%%edx\n" 1837 "1:\n\t" 1838 "lodsb\n\t" 1839 "testb %%al,%%al\n\t" 1840 "je 2f\n\t" 1841 "movl %%ebx,%%edi\n\t" 1842 "movl %%edx,%%ecx\n\t" 1843 "repne; scasb\n\t" 1844 "jne 1b\n\t" 1845 "decl %0\n\t" 1846 "jmp 3f\n" 1847 "2:\n\t" 1848 "xorl %0,%0\n" 1849 "3:" 1850 : "=S" (__res), "=&a" (__d0), "=&c" (__d1), "=&d" (__d2), "=&D" (__d3) 1851 : "0" (__s), "1" (0), "2" (0xffffffff), "b" (__accept) 1852 : "memory", "cc"); 1853 return __res; 1854 } 1855 # endif 1856 1857 1858 /* Find the first occurrence of NEEDLE in HAYSTACK. */ 1859 # define _HAVE_STRING_ARCH_strstr 1 1860 # define strstr(haystack, needle) \ 1861 (__extension__ (__builtin_constant_p (needle) && sizeof ((needle)[0]) == 1 \ 1862 ? ((needle)[0] == '\0' \ 1863 ? (haystack) \ 1864 : ((needle)[1] == '\0' \ 1865 ? strchr ((haystack), (needle)[0]) \ 1866 : __strstr_cg ((haystack), (needle), \ 1867 strlen (needle)))) \ 1868 : __strstr_g ((haystack), (needle)))) 1869 1870 /* Please note that this function need not handle NEEDLEs with a 1871 length shorter than two. */ 1872 __STRING_INLINE char *__strstr_cg (const char *__haystack, 1873 const char __needle[], 1874 size_t __needle_len); 1875 1876 __STRING_INLINE char * 1877 __strstr_cg (const char *__haystack, const char __needle[], 1878 size_t __needle_len) 1879 { 1880 register unsigned long int __d0, __d1, __d2; 1881 register char *__res; 1882 __asm__ __volatile__ 1883 ("cld\n" \ 1884 "1:\n\t" 1885 "movl %6,%%edi\n\t" 1886 "movl %5,%%eax\n\t" 1887 "movl %4,%%ecx\n\t" 1888 "repe; cmpsb\n\t" 1889 "je 2f\n\t" 1890 "cmpb $0,-1(%%esi)\n\t" 1891 "leal 1(%%eax),%5\n\t" 1892 "jne 1b\n\t" 1893 "xorl %%eax,%%eax\n" 1894 "2:" 1895 : "=&a" (__res), "=&S" (__d0), "=&D" (__d1), "=&c" (__d2) 1896 : "g" (__needle_len), "1" (__haystack), "d" (__needle) 1897 : "memory", "cc"); 1898 return __res; 1899 } 1900 1901 __STRING_INLINE char *__strstr_g (const char *__haystack, 1902 const char *__needle); 1903 # ifdef __PIC__ 1904 1905 __STRING_INLINE char * 1906 __strstr_g (const char *__haystack, const char *__needle) 1907 { 1908 register unsigned long int __d0, __d1, __d2; 1909 register char *__res; 1910 __asm__ __volatile__ 1911 ("cld\n\t" 1912 "repne; scasb\n\t" 1913 "notl %%ecx\n\t" 1914 "pushl %%ebx\n\t" 1915 "decl %%ecx\n\t" /* NOTE! This also sets Z if searchstring='' */ 1916 "movl %%ecx,%%ebx\n" 1917 "1:\n\t" 1918 "movl %%edx,%%edi\n\t" 1919 "movl %%esi,%%eax\n\t" 1920 "movl %%ebx,%%ecx\n\t" 1921 "repe; cmpsb\n\t" 1922 "je 2f\n\t" /* also works for empty string, see above */ 1923 "cmpb $0,-1(%%esi)\n\t" 1924 "leal 1(%%eax),%%esi\n\t" 1925 "jne 1b\n\t" 1926 "xorl %%eax,%%eax\n" 1927 "2:\n\t" 1928 "popl %%ebx" 1929 : "=&a" (__res), "=&c" (__d0), "=&S" (__d1), "=&D" (__d2) 1930 : "0" (0), "1" (0xffffffff), "2" (__haystack), "3" (__needle), 1931 "d" (__needle) 1932 : "memory", "cc"); 1933 return __res; 1934 } 1935 # else 1936 __STRING_INLINE char * 1937 __strstr_g (const char *__haystack, const char *__needle) 1938 { 1939 register unsigned long int __d0, __d1, __d2, __d3; 1940 register char *__res; 1941 __asm__ __volatile__ 1942 ("cld\n\t" 1943 "repne; scasb\n\t" 1944 "notl %%ecx\n\t" 1945 "decl %%ecx\n\t" /* NOTE! This also sets Z if searchstring='' */ 1946 "movl %%ecx,%%edx\n" 1947 "1:\n\t" 1948 "movl %%ebx,%%edi\n\t" 1949 "movl %%esi,%%eax\n\t" 1950 "movl %%edx,%%ecx\n\t" 1951 "repe; cmpsb\n\t" 1952 "je 2f\n\t" /* also works for empty string, see above */ 1953 "cmpb $0,-1(%%esi)\n\t" 1954 "leal 1(%%eax),%%esi\n\t" 1955 "jne 1b\n\t" 1956 "xorl %%eax,%%eax\n" 1957 "2:" 1958 : "=&a" (__res), "=&c" (__d0), "=&S" (__d1), "=&D" (__d2), "=&d" (__d3) 1959 : "0" (0), "1" (0xffffffff), "2" (__haystack), "3" (__needle), 1960 "b" (__needle) 1961 : "memory", "cc"); 1962 return __res; 1963 } 1964 # endif 1965 1966 1967 /* Bit find functions. We define only the i686 version since for the other 1968 processors gcc generates good code. */ 1969 # if defined __USE_MISC || defined __USE_XOPEN_EXTENDED 1970 # ifdef __i686__ 1971 # define _HAVE_STRING_ARCH_ffs 1 1972 # define ffs(word) (__builtin_constant_p (word) \ 1973 ? __builtin_ffs (word) \ 1974 : ({ int __cnt, __tmp; \ 1975 __asm__ __volatile__ \ 1976 ("bsfl %2,%0\n\t" \ 1977 "cmovel %1,%0" \ 1978 : "=&r" (__cnt), "=r" (__tmp) \ 1979 : "rm" (word), "1" (-1)); \ 1980 __cnt + 1; })) 1981 1982 # ifndef ffsl 1983 # define ffsl(word) ffs(word) 1984 # endif 1985 # endif /* i686 */ 1986 # endif /* Misc || X/Open */ 1987 1988 # ifndef _FORCE_INLINES 1989 # undef __STRING_INLINE 1990 # endif 1991 1992 # endif /* use string inlines && GNU CC */ 1993 1994 #endif 1995