|
|
1.1 root 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 <[email protected]>
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 "config.h"
19: #include "libc/string.h"
20: #include "libc/stdlib.h"
21:
22: /**
23: * strnicmp - Case insensitive, length-limited string comparison
24: * @s1: One string
25: * @s2: The other string
26: * @len: the maximum number of characters to compare
27: */
28: int strnicmp(const char *s1, const char *s2, size_t len)
29: {
30: /* Yes, Virginia, it had better be unsigned */
31: unsigned char c1, c2;
32:
33: c1 = 0; c2 = 0;
34: if (len) {
35: do {
36: c1 = *s1; c2 = *s2;
37: s1++; s2++;
38: if (!c1)
39: break;
40: if (!c2)
41: break;
42: if (c1 == c2)
43: continue;
44: c1 = tolower(c1);
45: c2 = tolower(c2);
46: if (c1 != c2)
47: break;
48: } while (--len);
49: }
50: return (int)c1 - (int)c2;
51: }
52:
53: /**
54: * strcpy - Copy a %NUL terminated string
55: * @dest: Where to copy the string to
56: * @src: Where to copy the string from
57: */
58: char * strcpy(char * dest,const char *src)
59: {
60: char *tmp = dest;
61:
62: while ((*dest++ = *src++) != '\0')
63: /* nothing */;
64: return tmp;
65: }
66:
67: /**
68: * strncpy - Copy a length-limited, %NUL-terminated string
69: * @dest: Where to copy the string to
70: * @src: Where to copy the string from
71: * @count: The maximum number of bytes to copy
72: *
73: * Note that unlike userspace strncpy, this does not %NUL-pad the buffer.
74: * However, the result is not %NUL-terminated if the source exceeds
75: * @count bytes.
76: */
77: char * strncpy(char * dest,const char *src,size_t count)
78: {
79: char *tmp = dest;
80:
81: while (count-- && (*dest++ = *src++) != '\0')
82: /* nothing */;
83:
84: return tmp;
85: }
86:
87: /**
88: * strcat - Append one %NUL-terminated string to another
89: * @dest: The string to be appended to
90: * @src: The string to append to it
91: */
92: char * strcat(char * dest, const char * src)
93: {
94: char *tmp = dest;
95:
96: while (*dest)
97: dest++;
98: while ((*dest++ = *src++) != '\0')
99: ;
100:
101: return tmp;
102: }
103:
104: /**
105: * strncat - Append a length-limited, %NUL-terminated string to another
106: * @dest: The string to be appended to
107: * @src: The string to append to it
108: * @count: The maximum numbers of bytes to copy
109: *
110: * Note that in contrast to strncpy, strncat ensures the result is
111: * terminated.
112: */
113: char * strncat(char *dest, const char *src, size_t count)
114: {
115: char *tmp = dest;
116:
117: if (count) {
118: while (*dest)
119: dest++;
120: while ((*dest++ = *src++)) {
121: if (--count == 0) {
122: *dest = '\0';
123: break;
124: }
125: }
126: }
127:
128: return tmp;
129: }
130:
131: /**
132: * strcmp - Compare two strings
133: * @cs: One string
134: * @ct: Another string
135: */
136: int strcmp(const char * cs,const char * ct)
137: {
138: register signed char __res;
139:
140: while (1) {
141: if ((__res = *cs - *ct++) != 0 || !*cs++)
142: break;
143: }
144:
145: return __res;
146: }
147:
148: /**
149: * strncmp - Compare two length-limited strings
150: * @cs: One string
151: * @ct: Another string
152: * @count: The maximum number of bytes to compare
153: */
154: int strncmp(const char * cs,const char * ct,size_t count)
155: {
156: register signed char __res = 0;
157:
158: while (count) {
159: if ((__res = *cs - *ct++) != 0 || !*cs++)
160: break;
161: count--;
162: }
163:
164: return __res;
165: }
166:
167:
168: /**
169: * strchr - Find the first occurrence of a character in a string
170: * @s: The string to be searched
171: * @c: The character to search for
172: */
173: char * strchr(const char * s, int c)
174: {
175: for(; *s != (char) c; ++s)
176: if (*s == '\0')
177: return NULL;
178: return (char *) s;
179: }
180:
181: /**
182: * strrchr - Find the last occurrence of a character in a string
183: * @s: The string to be searched
184: * @c: The character to search for
185: */
186: char * strrchr(const char * s, int c)
187: {
188: const char *p = s + strlen(s);
189: do {
190: if (*p == (char)c)
191: return (char *)p;
192: } while (--p >= s);
193: return NULL;
194: }
195:
196: /**
197: * strlen - Find the length of a string
198: * @s: The string to be sized
199: */
200: size_t strlen(const char * s)
201: {
202: const char *sc;
203:
204: for (sc = s; *sc != '\0'; ++sc)
205: /* nothing */;
206: return sc - s;
207: }
208:
209: /**
210: * strnlen - Find the length of a length-limited string
211: * @s: The string to be sized
212: * @count: The maximum number of bytes to search
213: */
214: size_t strnlen(const char * s, size_t count)
215: {
216: const char *sc;
217:
218: for (sc = s; count-- && *sc != '\0'; ++sc)
219: /* nothing */;
220: return sc - s;
221: }
222:
223: /**
224: * strpbrk - Find the first occurrence of a set of characters
225: * @cs: The string to be searched
226: * @ct: The characters to search for
227: */
228: char * strpbrk(const char * cs,const char * ct)
229: {
230: const char *sc1,*sc2;
231:
232: for( sc1 = cs; *sc1 != '\0'; ++sc1) {
233: for( sc2 = ct; *sc2 != '\0'; ++sc2) {
234: if (*sc1 == *sc2)
235: return (char *) sc1;
236: }
237: }
238: return NULL;
239: }
240:
241: /**
242: * strsep - Split a string into tokens
243: * @s: The string to be searched
244: * @ct: The characters to search for
245: *
246: * strsep() updates @s to point after the token, ready for the next call.
247: *
248: * It returns empty tokens, too, behaving exactly like the libc function
249: * of that name. In fact, it was stolen from glibc2 and de-fancy-fied.
250: * Same semantics, slimmer shape. ;)
251: */
252: char * strsep(char **s, const char *ct)
253: {
254: char *sbegin = *s, *end;
255:
256: if (sbegin == NULL)
257: return NULL;
258:
259: end = strpbrk(sbegin, ct);
260: if (end)
261: *end++ = '\0';
262: *s = end;
263:
264: return sbegin;
265: }
266:
267: /**
268: * memset - Fill a region of memory with the given value
269: * @s: Pointer to the start of the area.
270: * @c: The byte to fill the area with
271: * @count: The size of the area.
272: *
273: * Do not use memset() to access IO space, use memset_io() instead.
274: */
275: void * memset(void * s,int c,size_t count)
276: {
277: char *xs = (char *) s;
278:
279: while (count--)
280: *xs++ = c;
281:
282: return s;
283: }
284:
285: /**
286: * memcpy - Copy one area of memory to another
287: * @dest: Where to copy to
288: * @src: Where to copy from
289: * @count: The size of the area.
290: *
291: * You should not use this function to access IO space, use memcpy_toio()
292: * or memcpy_fromio() instead.
293: */
294: void * memcpy(void * dest,const void *src,size_t count)
295: {
296: char *tmp = (char *) dest, *s = (char *) src;
297:
298: while (count--)
299: *tmp++ = *s++;
300:
301: return dest;
302: }
303:
304: /**
305: * memmove - Copy one area of memory to another
306: * @dest: Where to copy to
307: * @src: Where to copy from
308: * @count: The size of the area.
309: *
310: * Unlike memcpy(), memmove() copes with overlapping areas.
311: */
312: void * memmove(void * dest,const void *src,size_t count)
313: {
314: char *tmp, *s;
315:
316: if (dest <= src) {
317: tmp = (char *) dest;
318: s = (char *) src;
319: while (count--)
320: *tmp++ = *s++;
321: }
322: else {
323: tmp = (char *) dest + count;
324: s = (char *) src + count;
325: while (count--)
326: *--tmp = *--s;
327: }
328:
329: return dest;
330: }
331:
332: /**
333: * memcmp - Compare two areas of memory
334: * @cs: One area of memory
335: * @ct: Another area of memory
336: * @count: The size of the area.
337: */
338: int memcmp(const void * cs,const void * ct,size_t count)
339: {
340: const unsigned char *su1, *su2;
341: int res = 0;
342:
343: for( su1 = cs, su2 = ct; 0 < count; ++su1, ++su2, count--)
344: if ((res = *su1 - *su2) != 0)
345: break;
346: return res;
347: }
348:
349: char *
350: strdup( const char *str )
351: {
352: char *p;
353: if( !str )
354: return NULL;
355: p = malloc( strlen(str) + 1 );
356: strcpy( p, str );
357: return p;
358: }
359:
360: int
361: strcasecmp( const char *cs, const char *ct )
362: {
363: register signed char __res;
364:
365: while (1) {
366: char ch1 = toupper(*cs), ch2 = toupper(*ct);
367: ct++;
368: if ((__res = ch1 - ch2) != 0 || !*cs++)
369: break;
370: }
371: return __res;
372: }
373:
374: int
375: strncasecmp( const char *cs, const char *ct, size_t count )
376: {
377: register signed char __res = 0;
378:
379: while (count--) {
380: char ch1 = toupper(*cs), ch2 = toupper(*ct);
381: ct++;
382: if ((__res = ch1 - ch2) != 0 || !*cs++)
383: break;
384: }
385: return __res;
386: }
387:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.