字符串函数实现---lib\string.c


  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.  * * Sat Feb 09 2002, Jason Thomas <jason@topic.com.au>, 
  18.  *                    Matthew Hawkins <matt@mh.dropbear.id.au> 
  19.  * -  Kissed strtok() goodbye 
  20.  */  
  21.   
  22. #include <linux/types.h>   
  23. #include <linux/string.h>   
  24. #include <linux/ctype.h>   
  25. #include <linux/module.h>   
  26.   
  27. #ifndef __HAVE_ARCH_STRNICMP   
  28. /** 
  29.  * strnicmp - Case insensitive, length-limited string comparison 
  30.  * @s1: One string 
  31.  * @s2: The other string 
  32.  * @len: the maximum number of characters to compare 
  33.  */  
  34. int strnicmp(const char *s1, const char *s2, size_t len)  
  35. {  
  36.     /* Yes, Virginia, it had better be unsigned */  
  37.     unsigned char c1, c2;  
  38.   
  39.     if (!len)  
  40.         return 0;  
  41.   
  42.     do {  
  43.         c1 = *s1++;  
  44.         c2 = *s2++;  
  45.         if (!c1 || !c2)  
  46.             break;  
  47.         if (c1 == c2)  
  48.             continue;  
  49.         c1 = tolower(c1);  
  50.         c2 = tolower(c2);  
  51.         if (c1 != c2)  
  52.             break;  
  53.     } while (--len);  
  54.     return (int)c1 - (int)c2;  
  55. }  
  56. EXPORT_SYMBOL(strnicmp);  
  57. #endif   
  58.   
  59. #ifndef __HAVE_ARCH_STRCASECMP   
  60. int strcasecmp(const char *s1, const char *s2)  
  61. {  
  62.     int c1, c2;  
  63.   
  64.     do {  
  65.         c1 = tolower(*s1++);  
  66.         c2 = tolower(*s2++);  
  67.     } while (c1 == c2 && c1 != 0);  
  68.     return c1 - c2;  
  69. }  
  70. EXPORT_SYMBOL(strcasecmp);  
  71. #endif   
  72.   
  73. #ifndef __HAVE_ARCH_STRNCASECMP   
  74. int strncasecmp(const char *s1, const char *s2, size_t n)  
  75. {  
  76.     int c1, c2;  
  77.   
  78.     do {  
  79.         c1 = tolower(*s1++);  
  80.         c2 = tolower(*s2++);  
  81.     } while ((--n > 0) && c1 == c2 && c1 != 0);  
  82.     return c1 - c2;  
  83. }  
  84. EXPORT_SYMBOL(strncasecmp);  
  85. #endif   
  86.   
  87. #ifndef __HAVE_ARCH_STRCPY   
  88. /** 
  89.  * strcpy - Copy a %NUL terminated string 
  90.  * @dest: Where to copy the string to 
  91.  * @src: Where to copy the string from 
  92.  */  
  93. #undef strcpy   
  94. char *strcpy(char *dest, const char *src)  
  95. {  
  96.     char *tmp = dest;  
  97.   
  98.     while ((*dest++ = *src++) != '\0')  
  99.         /* nothing */;  
  100.     return tmp;  
  101. }  
  102. EXPORT_SYMBOL(strcpy);  
  103. #endif   
  104.   
  105. #ifndef __HAVE_ARCH_STRNCPY   
  106. /** 
  107.  * strncpy - Copy a length-limited, %NUL-terminated string 
  108.  * @dest: Where to copy the string to 
  109.  * @src: Where to copy the string from 
  110.  * @count: The maximum number of bytes to copy 
  111.  * 
  112.  * The result is not %NUL-terminated if the source exceeds 
  113.  * @count bytes. 
  114.  * 
  115.  * In the case where the length of @src is less than  that  of 
  116.  * count, the remainder of @dest will be padded with %NUL. 
  117.  * 
  118.  */  
  119. char *strncpy(char *dest, const char *src, size_t count)  
  120. {  
  121.     char *tmp = dest;  
  122.   
  123.     while (count) {  
  124.         if ((*tmp = *src) != 0)  
  125.             src++;  
  126.         tmp++;  
  127.         count--;  
  128.     }  
  129.     return dest;  
  130. }  
  131. EXPORT_SYMBOL(strncpy);  
  132. #endif   
  133.   
  134. #ifndef __HAVE_ARCH_STRLCPY   
  135. /** 
  136.  * strlcpy - Copy a %NUL terminated string into a sized buffer 
  137.  * @dest: Where to copy the string to 
  138.  * @src: Where to copy the string from 
  139.  * @size: size of destination buffer 
  140.  * 
  141.  * Compatible with *BSD: the result is always a valid 
  142.  * NUL-terminated string that fits in the buffer (unless, 
  143.  * of course, the buffer size is zero). It does not pad 
  144.  * out the result like strncpy() does. 
  145.  */  
  146. size_t strlcpy(char *dest, const char *src, size_t size)  
  147. {  
  148.     size_t ret = strlen(src);  
  149.   
  150.     if (size) {  
  151.         size_t len = (ret >= size) ? size - 1 : ret;  
  152.         memcpy(dest, src, len);  
  153.         dest[len] = '\0';  
  154.     }  
  155.     return ret;  
  156. }  
  157. EXPORT_SYMBOL(strlcpy);  
  158. #endif   
  159.   
  160. #ifndef __HAVE_ARCH_STRCAT   
  161. /** 
  162.  * strcat - Append one %NUL-terminated string to another 
  163.  * @dest: The string to be appended to 
  164.  * @src: The string to append to it 
  165.  */  
  166. #undef strcat   
  167. char *strcat(char *dest, const char *src)  
  168. {  
  169.     char *tmp = dest;  
  170.   
  171.     while (*dest)  
  172.         dest++;  
  173.     while ((*dest++ = *src++) != '\0')  
  174.         ;  
  175.     return tmp;  
  176. }  
  177. EXPORT_SYMBOL(strcat);  
  178. #endif   
  179.   
  180. #ifndef __HAVE_ARCH_STRNCAT   
  181. /** 
  182.  * strncat - Append a length-limited, %NUL-terminated string to another 
  183.  * @dest: The string to be appended to 
  184.  * @src: The string to append to it 
  185.  * @count: The maximum numbers of bytes to copy 
  186.  * 
  187.  * Note that in contrast to strncpy(), strncat() ensures the result is 
  188.  * terminated. 
  189.  */  
  190. char *strncat(char *dest, const char *src, size_t count)  
  191. {  
  192.     char *tmp = dest;  
  193.   
  194.     if (count) {  
  195.         while (*dest)  
  196.             dest++;  
  197.         while ((*dest++ = *src++) != 0) {  
  198.             if (--count == 0) {  
  199.                 *dest = '\0';  
  200.                 break;  
  201.             }  
  202.         }  
  203.     }  
  204.     return tmp;  
  205. }  
  206. EXPORT_SYMBOL(strncat);  
  207. #endif   
  208.   
  209. #ifndef __HAVE_ARCH_STRLCAT   
  210. /** 
  211.  * strlcat - Append a length-limited, %NUL-terminated string to another 
  212.  * @dest: The string to be appended to 
  213.  * @src: The string to append to it 
  214.  * @count: The size of the destination buffer. 
  215.  */  
  216. size_t strlcat(char *dest, const char *src, size_t count)  
  217. {  
  218.     size_t dsize = strlen(dest);  
  219.     size_t len = strlen(src);  
  220.     size_t res = dsize + len;  
  221.   
  222.     /* This would be a bug */  
  223.     BUG_ON(dsize >= count);  
  224.   
  225.     dest += dsize;  
  226.     count -= dsize;  
  227.     if (len >= count)  
  228.         len = count-1;  
  229.     memcpy(dest, src, len);  
  230.     dest[len] = 0;  
  231.     return res;  
  232. }  
  233. EXPORT_SYMBOL(strlcat);  
  234. #endif   
  235.   
  236. #ifndef __HAVE_ARCH_STRCMP   
  237. /** 
  238.  * strcmp - Compare two strings 
  239.  * @cs: One string 
  240.  * @ct: Another string 
  241.  */  
  242. #undef strcmp   
  243. int strcmp(const char *cs, const char *ct)  
  244. {  
  245.     unsigned char c1, c2;  
  246.   
  247.     while (1) {  
  248.         c1 = *cs++;  
  249.         c2 = *ct++;  
  250.         if (c1 != c2)  
  251.             return c1 < c2 ? -1 : 1;  
  252.         if (!c1)  
  253.             break;  
  254.     }  
  255.     return 0;  
  256. }  
  257. EXPORT_SYMBOL(strcmp);  
  258. #endif   
  259.   
  260. #ifndef __HAVE_ARCH_STRNCMP   
  261. /** 
  262.  * strncmp - Compare two length-limited strings 
  263.  * @cs: One string 
  264.  * @ct: Another string 
  265.  * @count: The maximum number of bytes to compare 
  266.  */  
  267. int strncmp(const char *cs, const char *ct, size_t count)  
  268. {  
  269.     unsigned char c1, c2;  
  270.   
  271.     while (count) {  
  272.         c1 = *cs++;  
  273.         c2 = *ct++;  
  274.         if (c1 != c2)  
  275.             return c1 < c2 ? -1 : 1;  
  276.         if (!c1)  
  277.             break;  
  278.         count--;  
  279.     }  
  280.     return 0;  
  281. }  
  282. EXPORT_SYMBOL(strncmp);  
  283. #endif   
  284.   
  285. #ifndef __HAVE_ARCH_STRCHR   
  286. /** 
  287.  * strchr - Find the first occurrence of a character in a string 
  288.  * @s: The string to be searched 
  289.  * @c: The character to search for 
  290.  */  
  291. char *strchr(const char *s, int c)  
  292. {  
  293.     for (; *s != (char)c; ++s)  
  294.         if (*s == '\0')  
  295.             return NULL;  
  296.     return (char *)s;  
  297. }  
  298. EXPORT_SYMBOL(strchr);  
  299. #endif   
  300.   
  301. #ifndef __HAVE_ARCH_STRRCHR   
  302. /** 
  303.  * strrchr - Find the last occurrence of a character in a string 
  304.  * @s: The string to be searched 
  305.  * @c: The character to search for 
  306.  */  
  307. char *strrchr(const char *s, int c)  
  308. {  
  309.        const char *p = s + strlen(s);  
  310.        do {  
  311.            if (*p == (char)c)  
  312.                return (char *)p;  
  313.        } while (--p >= s);  
  314.        return NULL;  
  315. }  
  316. EXPORT_SYMBOL(strrchr);  
  317. #endif   
  318.   
  319. #ifndef __HAVE_ARCH_STRNCHR   
  320. /** 
  321.  * strnchr - Find a character in a length limited string 
  322.  * @s: The string to be searched 
  323.  * @count: The number of characters to be searched 
  324.  * @c: The character to search for 
  325.  */  
  326. char *strnchr(const char *s, size_t count, int c)  
  327. {  
  328.     for (; count-- && *s != '\0'; ++s)  
  329.         if (*s == (char)c)  
  330.             return (char *)s;  
  331.     return NULL;  
  332. }  
  333. EXPORT_SYMBOL(strnchr);  
  334. #endif   
  335.   
  336. /** 
  337.  * skip_spaces - Removes leading whitespace from @str. 
  338.  * @str: The string to be stripped. 
  339.  * 
  340.  * Returns a pointer to the first non-whitespace character in @str. 
  341.  */  
  342. char *skip_spaces(const char *str)  
  343. {  
  344.     while (isspace(*str))  
  345.         ++str;  
  346.     return (char *)str;  
  347. }  
  348. EXPORT_SYMBOL(skip_spaces);  
  349.   
  350. /** 
  351.  * strim - Removes leading and trailing whitespace from @s. 
  352.  * @s: The string to be stripped. 
  353.  * 
  354.  * Note that the first trailing whitespace is replaced with a %NUL-terminator 
  355.  * in the given string @s. Returns a pointer to the first non-whitespace 
  356.  * character in @s. 
  357.  */  
  358. char *strim(char *s)  
  359. {  
  360.     size_t size;  
  361.     char *end;  
  362.   
  363.     s = skip_spaces(s);  
  364.     size = strlen(s);  
  365.     if (!size)  
  366.         return s;  
  367.   
  368.     end = s + size - 1;  
  369.     while (end >= s && isspace(*end))  
  370.         end--;  
  371.     *(end + 1) = '\0';  
  372.   
  373.     return s;  
  374. }  
  375. EXPORT_SYMBOL(strim);  
  376.   
  377. #ifndef __HAVE_ARCH_STRLEN   
  378. /** 
  379.  * strlen - Find the length of a string 
  380.  * @s: The string to be sized 
  381.  */  
  382. size_t strlen(const char *s)  
  383. {  
  384.     const char *sc;  
  385.   
  386.     for (sc = s; *sc != '\0'; ++sc)  
  387.         /* nothing */;  
  388.     return sc - s;  
  389. }  
  390. EXPORT_SYMBOL(strlen);  
  391. #endif   
  392.   
  393. #ifndef __HAVE_ARCH_STRNLEN   
  394. /** 
  395.  * strnlen - Find the length of a length-limited string 
  396.  * @s: The string to be sized 
  397.  * @count: The maximum number of bytes to search 
  398.  */  
  399. size_t strnlen(const char *s, size_t count)  
  400. {  
  401.     const char *sc;  
  402.   
  403.     for (sc = s; count-- && *sc != '\0'; ++sc)  
  404.         /* nothing */;  
  405.     return sc - s;  
  406. }  
  407. EXPORT_SYMBOL(strnlen);  
  408. #endif   
  409.   
  410. #ifndef __HAVE_ARCH_STRSPN   
  411. /** 
  412.  * strspn - Calculate the length of the initial substring of @s which only contain letters in @accept 
  413.  * @s: The string to be searched 
  414.  * @accept: The string to search for 
  415.  */  
  416. size_t strspn(const char *s, const char *accept)  
  417. {  
  418.     const char *p;  
  419.     const char *a;  
  420.     size_t count = 0;  
  421.   
  422.     for (p = s; *p != '\0'; ++p) {  
  423.         for (a = accept; *a != '\0'; ++a) {  
  424.             if (*p == *a)  
  425.                 break;  
  426.         }  
  427.         if (*a == '\0')  
  428.             return count;  
  429.         ++count;  
  430.     }  
  431.     return count;  
  432. }  
  433.   
  434. EXPORT_SYMBOL(strspn);  
  435. #endif   
  436.   
  437. #ifndef __HAVE_ARCH_STRCSPN   
  438. /** 
  439.  * strcspn - Calculate the length of the initial substring of @s which does not contain letters in @reject 
  440.  * @s: The string to be searched 
  441.  * @reject: The string to avoid 
  442.  */  
  443. size_t strcspn(const char *s, const char *reject)  
  444. {  
  445.     const char *p;  
  446.     const char *r;  
  447.     size_t count = 0;  
  448.   
  449.     for (p = s; *p != '\0'; ++p) {  
  450.         for (r = reject; *r != '\0'; ++r) {  
  451.             if (*p == *r)  
  452.                 return count;  
  453.         }  
  454.         ++count;  
  455.     }  
  456.     return count;  
  457. }  
  458. EXPORT_SYMBOL(strcspn);  
  459. #endif   
  460.   
  461. #ifndef __HAVE_ARCH_STRPBRK   
  462. /** 
  463.  * strpbrk - Find the first occurrence of a set of characters 
  464.  * @cs: The string to be searched 
  465.  * @ct: The characters to search for 
  466.  */  
  467. char *strpbrk(const char *cs, const char *ct)  
  468. {  
  469.     const char *sc1, *sc2;  
  470.   
  471.     for (sc1 = cs; *sc1 != '\0'; ++sc1) {  
  472.         for (sc2 = ct; *sc2 != '\0'; ++sc2) {  
  473.             if (*sc1 == *sc2)  
  474.                 return (char *)sc1;  
  475.         }  
  476.     }  
  477.     return NULL;  
  478. }  
  479. EXPORT_SYMBOL(strpbrk);  
  480. #endif   
  481.   
  482. #ifndef __HAVE_ARCH_STRSEP   
  483. /** 
  484.  * strsep - Split a string into tokens 
  485.  * @s: The string to be searched 
  486.  * @ct: The characters to search for 
  487.  * 
  488.  * strsep() updates @s to point after the token, ready for the next call. 
  489.  * 
  490.  * It returns empty tokens, too, behaving exactly like the libc function 
  491.  * of that name. In fact, it was stolen from glibc2 and de-fancy-fied. 
  492.  * Same semantics, slimmer shape. ;) 
  493.  */  
  494. char *strsep(char **s, const char *ct)  
  495. {  
  496.     char *sbegin = *s;  
  497.     char *end;  
  498.   
  499.     if (sbegin == NULL)  
  500.         return NULL;  
  501.   
  502.     end = strpbrk(sbegin, ct);  
  503.     if (end)  
  504.         *end++ = '\0';  
  505.     *s = end;  
  506.     return sbegin;  
  507. }  
  508. EXPORT_SYMBOL(strsep);  
  509. #endif   
  510.   
  511. /** 
  512.  * sysfs_streq - return true if strings are equal, modulo trailing newline 
  513.  * @s1: one string 
  514.  * @s2: another string 
  515.  * 
  516.  * This routine returns true iff two strings are equal, treating both 
  517.  * NUL and newline-then-NUL as equivalent string terminations.  It's 
  518.  * geared for use with sysfs input strings, which generally terminate 
  519.  * with newlines but are compared against values without newlines. 
  520.  */  
  521. bool sysfs_streq(const char *s1, const char *s2)  
  522. {  
  523.     while (*s1 && *s1 == *s2) {  
  524.         s1++;  
  525.         s2++;  
  526.     }  
  527.   
  528.     if (*s1 == *s2)  
  529.         return true;  
  530.     if (!*s1 && *s2 == '\n' && !s2[1])  
  531.         return true;  
  532.     if (*s1 == '\n' && !s1[1] && !*s2)  
  533.         return true;  
  534.     return false;  
  535. }  
  536. EXPORT_SYMBOL(sysfs_streq);  
  537.   
  538. #ifndef __HAVE_ARCH_MEMSET   
  539. /** 
  540.  * memset - Fill a region of memory with the given value 
  541.  * @s: Pointer to the start of the area. 
  542.  * @c: The byte to fill the area with 
  543.  * @count: The size of the area. 
  544.  * 
  545.  * Do not use memset() to access IO space, use memset_io() instead. 
  546.  */  
  547. void *memset(void *s, int c, size_t count)  
  548. {  
  549.     char *xs = s;  
  550.   
  551.     while (count--)  
  552.         *xs++ = c;  
  553.     return s;  
  554. }  
  555. EXPORT_SYMBOL(memset);  
  556. #endif   
  557.   
  558. #ifndef __HAVE_ARCH_MEMCPY   
  559. /** 
  560.  * memcpy - Copy one area of memory to another 
  561.  * @dest: Where to copy to 
  562.  * @src: Where to copy from 
  563.  * @count: The size of the area. 
  564.  * 
  565.  * You should not use this function to access IO space, use memcpy_toio() 
  566.  * or memcpy_fromio() instead. 
  567.  */  
  568. void *memcpy(void *dest, const void *src, size_t count)  
  569. {  
  570.     char *tmp = dest;  
  571.     const char *s = src;  
  572.   
  573.     while (count--)  
  574.         *tmp++ = *s++;  
  575.     return dest;  
  576. }  
  577. EXPORT_SYMBOL(memcpy);  
  578. #endif   
  579.   
  580. #ifndef __HAVE_ARCH_MEMMOVE   
  581. /** 
  582.  * memmove - Copy one area of memory to another 
  583.  * @dest: Where to copy to 
  584.  * @src: Where to copy from 
  585.  * @count: The size of the area. 
  586.  * 
  587.  * Unlike memcpy(), memmove() copes with overlapping areas. 
  588.  */  
  589. void *memmove(void *dest, const void *src, size_t count)  
  590. {  
  591.     char *tmp;  
  592.     const char *s;  
  593.   
  594.     if (dest <= src) {  
  595.         tmp = dest;  
  596.         s = src;  
  597.         while (count--)  
  598.             *tmp++ = *s++;  
  599.     } else {  
  600.         tmp = dest;  
  601.         tmp += count;  
  602.         s = src;  
  603.         s += count;  
  604.         while (count--)  
  605.             *--tmp = *--s;  
  606.     }  
  607.     return dest;  
  608. }  
  609. EXPORT_SYMBOL(memmove);  
  610. #endif   
  611.   
  612. #ifndef __HAVE_ARCH_MEMCMP   
  613. /** 
  614.  * memcmp - Compare two areas of memory 
  615.  * @cs: One area of memory 
  616.  * @ct: Another area of memory 
  617.  * @count: The size of the area. 
  618.  */  
  619. #undef memcmp   
  620. int memcmp(const void *cs, const void *ct, size_t count)  
  621. {  
  622.     const unsigned char *su1, *su2;  
  623.     int res = 0;  
  624.   
  625.     for (su1 = cs, su2 = ct; 0 < count; ++su1, ++su2, count--)  
  626.         if ((res = *su1 - *su2) != 0)  
  627.             break;  
  628.     return res;  
  629. }  
  630. EXPORT_SYMBOL(memcmp);  
  631. #endif   
  632.   
  633. #ifndef __HAVE_ARCH_MEMSCAN   
  634. /** 
  635.  * memscan - Find a character in an area of memory. 
  636.  * @addr: The memory area 
  637.  * @c: The byte to search for 
  638.  * @size: The size of the area. 
  639.  * 
  640.  * returns the address of the first occurrence of @c, or 1 byte past 
  641.  * the area if @c is not found 
  642.  */  
  643. void *memscan(void *addr, int c, size_t size)  
  644. {  
  645.     unsigned char *p = addr;  
  646.   
  647.     while (size) {  
  648.         if (*p == c)  
  649.             return (void *)p;  
  650.         p++;  
  651.         size--;  
  652.     }  
  653.     return (void *)p;  
  654. }  
  655. EXPORT_SYMBOL(memscan);  
  656. #endif   
  657.   
  658. #ifndef __HAVE_ARCH_STRSTR   
  659. /** 
  660.  * strstr - Find the first substring in a %NUL terminated string 
  661.  * @s1: The string to be searched 
  662.  * @s2: The string to search for 
  663.  */  
  664. char *strstr(const char *s1, const char *s2)  
  665. {  
  666.     size_t l1, l2;  
  667.   
  668.     l2 = strlen(s2);  
  669.     if (!l2)  
  670.         return (char *)s1;  
  671.     l1 = strlen(s1);  
  672.     while (l1 >= l2) {  
  673.         l1--;  
  674.         if (!memcmp(s1, s2, l2))  
  675.             return (char *)s1;  
  676.         s1++;  
  677.     }  
  678.     return NULL;  
  679. }  
  680. EXPORT_SYMBOL(strstr);  
  681. #endif   
  682.   
  683. #ifndef __HAVE_ARCH_STRNSTR   
  684. /** 
  685.  * strnstr - Find the first substring in a length-limited string 
  686.  * @s1: The string to be searched 
  687.  * @s2: The string to search for 
  688.  * @len: the maximum number of characters to search 
  689.  */  
  690. char *strnstr(const char *s1, const char *s2, size_t len)  
  691. {  
  692.     size_t l2;  
  693.   
  694.     l2 = strlen(s2);  
  695.     if (!l2)  
  696.         return (char *)s1;  
  697.     while (len >= l2) {  
  698.         len--;  
  699.         if (!memcmp(s1, s2, l2))  
  700.             return (char *)s1;  
  701.         s1++;  
  702.     }  
  703.     return NULL;  
  704. }  
  705. EXPORT_SYMBOL(strnstr);  
  706. #endif   
  707.   
  708. #ifndef __HAVE_ARCH_MEMCHR   
  709. /** 
  710.  * memchr - Find a character in an area of memory. 
  711.  * @s: The memory area 
  712.  * @c: The byte to search for 
  713.  * @n: The size of the area. 
  714.  * 
  715.  * returns the address of the first occurrence of @c, or %NULL 
  716.  * if @c is not found 
  717.  */  
  718. void *memchr(const void *s, int c, size_t n)  
  719. {  
  720.     const unsigned char *p = s;  
  721.     while (n-- != 0) {  
  722.             if ((unsigned char)c == *p++) {  
  723.             return (void *)(p - 1);  
  724.         }  
  725.     }  
  726.     return NULL;  
  727. }  
  728. EXPORT_SYMBOL(memchr);  
  729. #endif  

相关内容