uboot/lib/string.c
<<
>>
Prefs
   1/*
   2 *  linux/lib/string.c
   3 *
   4 *  Copyright (C) 1991, 1992  Linus Torvalds
   5 */
   6
   7/*
   8 * stupid library routines.. The optimized versions should generally be found
   9 * as inline code in <asm-xx/string.h>
  10 *
  11 * These are buggy as well..
  12 *
  13 * * Fri Jun 25 1999, Ingo Oeser <ioe@informatik.tu-chemnitz.de>
  14 * -  Added strsep() which will replace strtok() soon (because strsep() is
  15 *    reentrant and should be faster). Use only strsep() in new code, please.
  16 */
  17
  18#include <linux/types.h>
  19#include <linux/string.h>
  20#include <linux/ctype.h>
  21#include <malloc.h>
  22
  23
  24#if 0 /* not used - was: #ifndef __HAVE_ARCH_STRNICMP */
  25/**
  26 * strnicmp - Case insensitive, length-limited string comparison
  27 * @s1: One string
  28 * @s2: The other string
  29 * @len: the maximum number of characters to compare
  30 */
  31int strnicmp(const char *s1, const char *s2, size_t len)
  32{
  33        /* Yes, Virginia, it had better be unsigned */
  34        unsigned char c1, c2;
  35
  36        c1 = 0; c2 = 0;
  37        if (len) {
  38                do {
  39                        c1 = *s1; c2 = *s2;
  40                        s1++; s2++;
  41                        if (!c1)
  42                                break;
  43                        if (!c2)
  44                                break;
  45                        if (c1 == c2)
  46                                continue;
  47                        c1 = tolower(c1);
  48                        c2 = tolower(c2);
  49                        if (c1 != c2)
  50                                break;
  51                } while (--len);
  52        }
  53        return (int)c1 - (int)c2;
  54}
  55#endif
  56
  57char * ___strtok;
  58
  59#ifndef __HAVE_ARCH_STRCPY
  60/**
  61 * strcpy - Copy a %NUL terminated string
  62 * @dest: Where to copy the string to
  63 * @src: Where to copy the string from
  64 */
  65char * strcpy(char * dest,const char *src)
  66{
  67        char *tmp = dest;
  68
  69        while ((*dest++ = *src++) != '\0')
  70                /* nothing */;
  71        return tmp;
  72}
  73#endif
  74
  75#ifndef __HAVE_ARCH_STRNCPY
  76/**
  77 * strncpy - Copy a length-limited, %NUL-terminated string
  78 * @dest: Where to copy the string to
  79 * @src: Where to copy the string from
  80 * @count: The maximum number of bytes to copy
  81 *
  82 * Note that unlike userspace strncpy, this does not %NUL-pad the buffer.
  83 * However, the result is not %NUL-terminated if the source exceeds
  84 * @count bytes.
  85 */
  86char * strncpy(char * dest,const char *src,size_t count)
  87{
  88        char *tmp = dest;
  89
  90        while (count-- && (*dest++ = *src++) != '\0')
  91                /* nothing */;
  92
  93        return tmp;
  94}
  95#endif
  96
  97#ifndef __HAVE_ARCH_STRCAT
  98/**
  99 * strcat - Append one %NUL-terminated string to another
 100 * @dest: The string to be appended to
 101 * @src: The string to append to it
 102 */
 103char * strcat(char * dest, const char * src)
 104{
 105        char *tmp = dest;
 106
 107        while (*dest)
 108                dest++;
 109        while ((*dest++ = *src++) != '\0')
 110                ;
 111
 112        return tmp;
 113}
 114#endif
 115
 116#ifndef __HAVE_ARCH_STRNCAT
 117/**
 118 * strncat - Append a length-limited, %NUL-terminated string to another
 119 * @dest: The string to be appended to
 120 * @src: The string to append to it
 121 * @count: The maximum numbers of bytes to copy
 122 *
 123 * Note that in contrast to strncpy, strncat ensures the result is
 124 * terminated.
 125 */
 126char * strncat(char *dest, const char *src, size_t count)
 127{
 128        char *tmp = dest;
 129
 130        if (count) {
 131                while (*dest)
 132                        dest++;
 133                while ((*dest++ = *src++)) {
 134                        if (--count == 0) {
 135                                *dest = '\0';
 136                                break;
 137                        }
 138                }
 139        }
 140
 141        return tmp;
 142}
 143#endif
 144
 145#ifndef __HAVE_ARCH_STRCMP
 146/**
 147 * strcmp - Compare two strings
 148 * @cs: One string
 149 * @ct: Another string
 150 */
 151int strcmp(const char * cs,const char * ct)
 152{
 153        register signed char __res;
 154
 155        while (1) {
 156                if ((__res = *cs - *ct++) != 0 || !*cs++)
 157                        break;
 158        }
 159
 160        return __res;
 161}
 162#endif
 163
 164#ifndef __HAVE_ARCH_STRNCMP
 165/**
 166 * strncmp - Compare two length-limited strings
 167 * @cs: One string
 168 * @ct: Another string
 169 * @count: The maximum number of bytes to compare
 170 */
 171int strncmp(const char * cs,const char * ct,size_t count)
 172{
 173        register signed char __res = 0;
 174
 175        while (count) {
 176                if ((__res = *cs - *ct++) != 0 || !*cs++)
 177                        break;
 178                count--;
 179        }
 180
 181        return __res;
 182}
 183#endif
 184
 185#ifndef __HAVE_ARCH_STRCHR
 186/**
 187 * strchr - Find the first occurrence of a character in a string
 188 * @s: The string to be searched
 189 * @c: The character to search for
 190 */
 191char * strchr(const char * s, int c)
 192{
 193        for(; *s != (char) c; ++s)
 194                if (*s == '\0')
 195                        return NULL;
 196        return (char *) s;
 197}
 198#endif
 199
 200#ifndef __HAVE_ARCH_STRRCHR
 201/**
 202 * strrchr - Find the last occurrence of a character in a string
 203 * @s: The string to be searched
 204 * @c: The character to search for
 205 */
 206char * strrchr(const char * s, int c)
 207{
 208       const char *p = s + strlen(s);
 209       do {
 210           if (*p == (char)c)
 211               return (char *)p;
 212       } while (--p >= s);
 213       return NULL;
 214}
 215#endif
 216
 217
 218/**
 219 * skip_spaces - Removes leading whitespace from @str.
 220 * @str: The string to be stripped.
 221 *
 222 * Returns a pointer to the first non-whitespace character in @str.
 223 */
 224char *skip_spaces(const char *str)
 225{
 226        while (isspace(*str))
 227                ++str;
 228        return (char *)str;
 229}
 230
 231/**
 232 * strim - Removes leading and trailing whitespace from @s.
 233 * @s: The string to be stripped.
 234 *
 235 * Note that the first trailing whitespace is replaced with a %NUL-terminator
 236 * in the given string @s. Returns a pointer to the first non-whitespace
 237 * character in @s.
 238 */
 239char *strim(char *s)
 240{
 241        size_t size;
 242        char *end;
 243
 244        s = skip_spaces(s);
 245        size = strlen(s);
 246        if (!size)
 247                return s;
 248
 249        end = s + size - 1;
 250        while (end >= s && isspace(*end))
 251                end--;
 252        *(end + 1) = '\0';
 253
 254        return s;
 255}
 256#ifndef __HAVE_ARCH_STRLEN
 257/**
 258 * strlen - Find the length of a string
 259 * @s: The string to be sized
 260 */
 261size_t strlen(const char * s)
 262{
 263        const char *sc;
 264
 265        for (sc = s; *sc != '\0'; ++sc)
 266                /* nothing */;
 267        return sc - s;
 268}
 269#endif
 270
 271#ifndef __HAVE_ARCH_STRNLEN
 272/**
 273 * strnlen - Find the length of a length-limited string
 274 * @s: The string to be sized
 275 * @count: The maximum number of bytes to search
 276 */
 277size_t strnlen(const char * s, size_t count)
 278{
 279        const char *sc;
 280
 281        for (sc = s; count-- && *sc != '\0'; ++sc)
 282                /* nothing */;
 283        return sc - s;
 284}
 285#endif
 286
 287#ifndef __HAVE_ARCH_STRDUP
 288char * strdup(const char *s)
 289{
 290        char *new;
 291
 292        if ((s == NULL) ||
 293            ((new = malloc (strlen(s) + 1)) == NULL) ) {
 294                return NULL;
 295        }
 296
 297        strcpy (new, s);
 298        return new;
 299}
 300#endif
 301
 302#ifndef __HAVE_ARCH_STRSPN
 303/**
 304 * strspn - Calculate the length of the initial substring of @s which only
 305 *      contain letters in @accept
 306 * @s: The string to be searched
 307 * @accept: The string to search for
 308 */
 309size_t strspn(const char *s, const char *accept)
 310{
 311        const char *p;
 312        const char *a;
 313        size_t count = 0;
 314
 315        for (p = s; *p != '\0'; ++p) {
 316                for (a = accept; *a != '\0'; ++a) {
 317                        if (*p == *a)
 318                                break;
 319                }
 320                if (*a == '\0')
 321                        return count;
 322                ++count;
 323        }
 324
 325        return count;
 326}
 327#endif
 328
 329#ifndef __HAVE_ARCH_STRPBRK
 330/**
 331 * strpbrk - Find the first occurrence of a set of characters
 332 * @cs: The string to be searched
 333 * @ct: The characters to search for
 334 */
 335char * strpbrk(const char * cs,const char * ct)
 336{
 337        const char *sc1,*sc2;
 338
 339        for( sc1 = cs; *sc1 != '\0'; ++sc1) {
 340                for( sc2 = ct; *sc2 != '\0'; ++sc2) {
 341                        if (*sc1 == *sc2)
 342                                return (char *) sc1;
 343                }
 344        }
 345        return NULL;
 346}
 347#endif
 348
 349#ifndef __HAVE_ARCH_STRTOK
 350/**
 351 * strtok - Split a string into tokens
 352 * @s: The string to be searched
 353 * @ct: The characters to search for
 354 *
 355 * WARNING: strtok is deprecated, use strsep instead.
 356 */
 357char * strtok(char * s,const char * ct)
 358{
 359        char *sbegin, *send;
 360
 361        sbegin  = s ? s : ___strtok;
 362        if (!sbegin) {
 363                return NULL;
 364        }
 365        sbegin += strspn(sbegin,ct);
 366        if (*sbegin == '\0') {
 367                ___strtok = NULL;
 368                return( NULL );
 369        }
 370        send = strpbrk( sbegin, ct);
 371        if (send && *send != '\0')
 372                *send++ = '\0';
 373        ___strtok = send;
 374        return (sbegin);
 375}
 376#endif
 377
 378#ifndef __HAVE_ARCH_STRSEP
 379/**
 380 * strsep - Split a string into tokens
 381 * @s: The string to be searched
 382 * @ct: The characters to search for
 383 *
 384 * strsep() updates @s to point after the token, ready for the next call.
 385 *
 386 * It returns empty tokens, too, behaving exactly like the libc function
 387 * of that name. In fact, it was stolen from glibc2 and de-fancy-fied.
 388 * Same semantics, slimmer shape. ;)
 389 */
 390char * strsep(char **s, const char *ct)
 391{
 392        char *sbegin = *s, *end;
 393
 394        if (sbegin == NULL)
 395                return NULL;
 396
 397        end = strpbrk(sbegin, ct);
 398        if (end)
 399                *end++ = '\0';
 400        *s = end;
 401
 402        return sbegin;
 403}
 404#endif
 405
 406#ifndef __HAVE_ARCH_STRSWAB
 407/**
 408 * strswab - swap adjacent even and odd bytes in %NUL-terminated string
 409 * s: address of the string
 410 *
 411 * returns the address of the swapped string or NULL on error. If
 412 * string length is odd, last byte is untouched.
 413 */
 414char *strswab(const char *s)
 415{
 416        char *p, *q;
 417
 418        if ((NULL == s) || ('\0' == *s)) {
 419                return (NULL);
 420        }
 421
 422        for (p=(char *)s, q=p+1; (*p != '\0') && (*q != '\0'); p+=2, q+=2) {
 423                char  tmp;
 424
 425                tmp = *p;
 426                *p  = *q;
 427                *q  = tmp;
 428        }
 429
 430        return (char *) s;
 431}
 432#endif
 433
 434#ifndef __HAVE_ARCH_MEMSET
 435/**
 436 * memset - Fill a region of memory with the given value
 437 * @s: Pointer to the start of the area.
 438 * @c: The byte to fill the area with
 439 * @count: The size of the area.
 440 *
 441 * Do not use memset() to access IO space, use memset_io() instead.
 442 */
 443void * memset(void * s,int c,size_t count)
 444{
 445        unsigned long *sl = (unsigned long *) s;
 446        unsigned long cl = 0;
 447        char *s8;
 448        int i;
 449
 450        /* do it one word at a time (32 bits or 64 bits) while possible */
 451        if ( ((ulong)s & (sizeof(*sl) - 1)) == 0) {
 452                for (i = 0; i < sizeof(*sl); i++) {
 453                        cl <<= 8;
 454                        cl |= c & 0xff;
 455                }
 456                while (count >= sizeof(*sl)) {
 457                        *sl++ = cl;
 458                        count -= sizeof(*sl);
 459                }
 460        }
 461        /* fill 8 bits at a time */
 462        s8 = (char *)sl;
 463        while (count--)
 464                *s8++ = c;
 465
 466        return s;
 467}
 468#endif
 469
 470#ifndef __HAVE_ARCH_BCOPY
 471/**
 472 * bcopy - Copy one area of memory to another
 473 * @src: Where to copy from
 474 * @dest: Where to copy to
 475 * @count: The size of the area.
 476 *
 477 * Note that this is the same as memcpy(), with the arguments reversed.
 478 * memcpy() is the standard, bcopy() is a legacy BSD function.
 479 *
 480 * You should not use this function to access IO space, use memcpy_toio()
 481 * or memcpy_fromio() instead.
 482 */
 483char * bcopy(const char * src, char * dest, int count)
 484{
 485        char *tmp = dest;
 486
 487        while (count--)
 488                *tmp++ = *src++;
 489
 490        return dest;
 491}
 492#endif
 493
 494#ifndef __HAVE_ARCH_MEMCPY
 495/**
 496 * memcpy - Copy one area of memory to another
 497 * @dest: Where to copy to
 498 * @src: Where to copy from
 499 * @count: The size of the area.
 500 *
 501 * You should not use this function to access IO space, use memcpy_toio()
 502 * or memcpy_fromio() instead.
 503 */
 504void * memcpy(void *dest, const void *src, size_t count)
 505{
 506        unsigned long *dl = (unsigned long *)dest, *sl = (unsigned long *)src;
 507        char *d8, *s8;
 508
 509        if (src == dest)
 510                return dest;
 511
 512        /* while all data is aligned (common case), copy a word at a time */
 513        if ( (((ulong)dest | (ulong)src) & (sizeof(*dl) - 1)) == 0) {
 514                while (count >= sizeof(*dl)) {
 515                        *dl++ = *sl++;
 516                        count -= sizeof(*dl);
 517                }
 518        }
 519        /* copy the reset one byte at a time */
 520        d8 = (char *)dl;
 521        s8 = (char *)sl;
 522        while (count--)
 523                *d8++ = *s8++;
 524
 525        return dest;
 526}
 527#endif
 528
 529#ifndef __HAVE_ARCH_MEMMOVE
 530/**
 531 * memmove - Copy one area of memory to another
 532 * @dest: Where to copy to
 533 * @src: Where to copy from
 534 * @count: The size of the area.
 535 *
 536 * Unlike memcpy(), memmove() copes with overlapping areas.
 537 */
 538void * memmove(void * dest,const void *src,size_t count)
 539{
 540        char *tmp, *s;
 541
 542        if (src == dest)
 543                return dest;
 544
 545        if (dest <= src) {
 546                tmp = (char *) dest;
 547                s = (char *) src;
 548                while (count--)
 549                        *tmp++ = *s++;
 550                }
 551        else {
 552                tmp = (char *) dest + count;
 553                s = (char *) src + count;
 554                while (count--)
 555                        *--tmp = *--s;
 556                }
 557
 558        return dest;
 559}
 560#endif
 561
 562#ifndef __HAVE_ARCH_MEMCMP
 563/**
 564 * memcmp - Compare two areas of memory
 565 * @cs: One area of memory
 566 * @ct: Another area of memory
 567 * @count: The size of the area.
 568 */
 569int memcmp(const void * cs,const void * ct,size_t count)
 570{
 571        const unsigned char *su1, *su2;
 572        int res = 0;
 573
 574        for( su1 = cs, su2 = ct; 0 < count; ++su1, ++su2, count--)
 575                if ((res = *su1 - *su2) != 0)
 576                        break;
 577        return res;
 578}
 579#endif
 580
 581#ifndef __HAVE_ARCH_MEMSCAN
 582/**
 583 * memscan - Find a character in an area of memory.
 584 * @addr: The memory area
 585 * @c: The byte to search for
 586 * @size: The size of the area.
 587 *
 588 * returns the address of the first occurrence of @c, or 1 byte past
 589 * the area if @c is not found
 590 */
 591void * memscan(void * addr, int c, size_t size)
 592{
 593        unsigned char * p = (unsigned char *) addr;
 594
 595        while (size) {
 596                if (*p == c)
 597                        return (void *) p;
 598                p++;
 599                size--;
 600        }
 601        return (void *) p;
 602}
 603#endif
 604
 605#ifndef __HAVE_ARCH_STRSTR
 606/**
 607 * strstr - Find the first substring in a %NUL terminated string
 608 * @s1: The string to be searched
 609 * @s2: The string to search for
 610 */
 611char * strstr(const char * s1,const char * s2)
 612{
 613        int l1, l2;
 614
 615        l2 = strlen(s2);
 616        if (!l2)
 617                return (char *) s1;
 618        l1 = strlen(s1);
 619        while (l1 >= l2) {
 620                l1--;
 621                if (!memcmp(s1,s2,l2))
 622                        return (char *) s1;
 623                s1++;
 624        }
 625        return NULL;
 626}
 627#endif
 628
 629#ifndef __HAVE_ARCH_MEMCHR
 630/**
 631 * memchr - Find a character in an area of memory.
 632 * @s: The memory area
 633 * @c: The byte to search for
 634 * @n: The size of the area.
 635 *
 636 * returns the address of the first occurrence of @c, or %NULL
 637 * if @c is not found
 638 */
 639void *memchr(const void *s, int c, size_t n)
 640{
 641        const unsigned char *p = s;
 642        while (n-- != 0) {
 643                if ((unsigned char)c == *p++) {
 644                        return (void *)(p-1);
 645                }
 646        }
 647        return NULL;
 648}
 649
 650#endif
 651