OLD | NEW |
1 /* | 1 /* |
2 * string.c : an XML string utilities module | 2 * string.c : an XML string utilities module |
3 * | 3 * |
4 * This module provides various utility functions for manipulating | 4 * This module provides various utility functions for manipulating |
5 * the xmlChar* type. All functions named xmlStr* have been moved here | 5 * the xmlChar* type. All functions named xmlStr* have been moved here |
6 * from the parser.c file (their original home). | 6 * from the parser.c file (their original home). |
7 * | 7 * |
8 * See Copyright for the status of this software. | 8 * See Copyright for the status of this software. |
9 * | 9 * |
10 * UTF8 string routines from: | 10 * UTF8 string routines from: |
11 * William Brack <wbrack@mmm.com.hk> | 11 * William Brack <wbrack@mmm.com.hk> |
12 * | 12 * |
13 * daniel@veillard.com | 13 * daniel@veillard.com |
14 */ | 14 */ |
15 | 15 |
16 #define IN_LIBXML | 16 #define IN_LIBXML |
(...skipping 16 matching lines...) Expand all Loading... |
33 * @cur: the input xmlChar * | 33 * @cur: the input xmlChar * |
34 * @len: the len of @cur | 34 * @len: the len of @cur |
35 * | 35 * |
36 * a strndup for array of xmlChar's | 36 * a strndup for array of xmlChar's |
37 * | 37 * |
38 * Returns a new xmlChar * or NULL | 38 * Returns a new xmlChar * or NULL |
39 */ | 39 */ |
40 xmlChar * | 40 xmlChar * |
41 xmlStrndup(const xmlChar *cur, int len) { | 41 xmlStrndup(const xmlChar *cur, int len) { |
42 xmlChar *ret; | 42 xmlChar *ret; |
43 | 43 |
44 if ((cur == NULL) || (len < 0)) return(NULL); | 44 if ((cur == NULL) || (len < 0)) return(NULL); |
45 ret = (xmlChar *) xmlMallocAtomic((len + 1) * sizeof(xmlChar)); | 45 ret = (xmlChar *) xmlMallocAtomic((len + 1) * sizeof(xmlChar)); |
46 if (ret == NULL) { | 46 if (ret == NULL) { |
47 xmlErrMemory(NULL, NULL); | 47 xmlErrMemory(NULL, NULL); |
48 return(NULL); | 48 return(NULL); |
49 } | 49 } |
50 memcpy(ret, cur, len * sizeof(xmlChar)); | 50 memcpy(ret, cur, len * sizeof(xmlChar)); |
51 ret[len] = 0; | 51 ret[len] = 0; |
52 return(ret); | 52 return(ret); |
53 } | 53 } |
(...skipping 24 matching lines...) Expand all Loading... |
78 * | 78 * |
79 * a strndup for char's to xmlChar's | 79 * a strndup for char's to xmlChar's |
80 * | 80 * |
81 * Returns a new xmlChar * or NULL | 81 * Returns a new xmlChar * or NULL |
82 */ | 82 */ |
83 | 83 |
84 xmlChar * | 84 xmlChar * |
85 xmlCharStrndup(const char *cur, int len) { | 85 xmlCharStrndup(const char *cur, int len) { |
86 int i; | 86 int i; |
87 xmlChar *ret; | 87 xmlChar *ret; |
88 | 88 |
89 if ((cur == NULL) || (len < 0)) return(NULL); | 89 if ((cur == NULL) || (len < 0)) return(NULL); |
90 ret = (xmlChar *) xmlMallocAtomic((len + 1) * sizeof(xmlChar)); | 90 ret = (xmlChar *) xmlMallocAtomic((len + 1) * sizeof(xmlChar)); |
91 if (ret == NULL) { | 91 if (ret == NULL) { |
92 xmlErrMemory(NULL, NULL); | 92 xmlErrMemory(NULL, NULL); |
93 return(NULL); | 93 return(NULL); |
94 } | 94 } |
95 for (i = 0;i < len;i++) { | 95 for (i = 0;i < len;i++) { |
96 ret[i] = (xmlChar) cur[i]; | 96 ret[i] = (xmlChar) cur[i]; |
97 if (ret[i] == 0) return(ret); | 97 if (ret[i] == 0) return(ret); |
98 } | 98 } |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
163 } while (*str2++); | 163 } while (*str2++); |
164 return(1); | 164 return(1); |
165 } | 165 } |
166 | 166 |
167 /** | 167 /** |
168 * xmlStrQEqual: | 168 * xmlStrQEqual: |
169 * @pref: the prefix of the QName | 169 * @pref: the prefix of the QName |
170 * @name: the localname of the QName | 170 * @name: the localname of the QName |
171 * @str: the second xmlChar * | 171 * @str: the second xmlChar * |
172 * | 172 * |
173 * Check if a QName is Equal to a given string | 173 * Check if a QName is Equal to a given string |
174 * | 174 * |
175 * Returns 1 if they are equal, 0 if they are different | 175 * Returns 1 if they are equal, 0 if they are different |
176 */ | 176 */ |
177 | 177 |
178 int | 178 int |
179 xmlStrQEqual(const xmlChar *pref, const xmlChar *name, const xmlChar *str) { | 179 xmlStrQEqual(const xmlChar *pref, const xmlChar *name, const xmlChar *str) { |
180 if (pref == NULL) return(xmlStrEqual(name, str)); | 180 if (pref == NULL) return(xmlStrEqual(name, str)); |
181 if (name == NULL) return(0); | 181 if (name == NULL) return(0); |
182 if (str == NULL) return(0); | 182 if (str == NULL) return(0); |
183 | 183 |
(...skipping 149 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
333 * @val: the xmlChar to search (needle) | 333 * @val: the xmlChar to search (needle) |
334 * | 334 * |
335 * a strstr for xmlChar's | 335 * a strstr for xmlChar's |
336 * | 336 * |
337 * Returns the xmlChar * for the first occurrence or NULL. | 337 * Returns the xmlChar * for the first occurrence or NULL. |
338 */ | 338 */ |
339 | 339 |
340 const xmlChar * | 340 const xmlChar * |
341 xmlStrstr(const xmlChar *str, const xmlChar *val) { | 341 xmlStrstr(const xmlChar *str, const xmlChar *val) { |
342 int n; | 342 int n; |
343 | 343 |
344 if (str == NULL) return(NULL); | 344 if (str == NULL) return(NULL); |
345 if (val == NULL) return(NULL); | 345 if (val == NULL) return(NULL); |
346 n = xmlStrlen(val); | 346 n = xmlStrlen(val); |
347 | 347 |
348 if (n == 0) return(str); | 348 if (n == 0) return(str); |
349 while (*str != 0) { /* non input consuming */ | 349 while (*str != 0) { /* non input consuming */ |
350 if (*str == *val) { | 350 if (*str == *val) { |
351 if (!xmlStrncmp(str, val, n)) return((const xmlChar *) str); | 351 if (!xmlStrncmp(str, val, n)) return((const xmlChar *) str); |
352 } | 352 } |
353 str++; | 353 str++; |
354 } | 354 } |
355 return(NULL); | 355 return(NULL); |
356 } | 356 } |
357 | 357 |
358 /** | 358 /** |
359 * xmlStrcasestr: | 359 * xmlStrcasestr: |
360 * @str: the xmlChar * array (haystack) | 360 * @str: the xmlChar * array (haystack) |
361 * @val: the xmlChar to search (needle) | 361 * @val: the xmlChar to search (needle) |
362 * | 362 * |
363 * a case-ignoring strstr for xmlChar's | 363 * a case-ignoring strstr for xmlChar's |
364 * | 364 * |
365 * Returns the xmlChar * for the first occurrence or NULL. | 365 * Returns the xmlChar * for the first occurrence or NULL. |
366 */ | 366 */ |
367 | 367 |
368 const xmlChar * | 368 const xmlChar * |
369 xmlStrcasestr(const xmlChar *str, const xmlChar *val) { | 369 xmlStrcasestr(const xmlChar *str, const xmlChar *val) { |
370 int n; | 370 int n; |
371 | 371 |
372 if (str == NULL) return(NULL); | 372 if (str == NULL) return(NULL); |
373 if (val == NULL) return(NULL); | 373 if (val == NULL) return(NULL); |
374 n = xmlStrlen(val); | 374 n = xmlStrlen(val); |
375 | 375 |
376 if (n == 0) return(str); | 376 if (n == 0) return(str); |
377 while (*str != 0) { /* non input consuming */ | 377 while (*str != 0) { /* non input consuming */ |
378 if (casemap[*str] == casemap[*val]) | 378 if (casemap[*str] == casemap[*val]) |
379 if (!xmlStrncasecmp(str, val, n)) return(str); | 379 if (!xmlStrncasecmp(str, val, n)) return(str); |
380 str++; | 380 str++; |
381 } | 381 } |
382 return(NULL); | 382 return(NULL); |
383 } | 383 } |
384 | 384 |
385 /** | 385 /** |
386 * xmlStrsub: | 386 * xmlStrsub: |
387 * @str: the xmlChar * array (haystack) | 387 * @str: the xmlChar * array (haystack) |
388 * @start: the index of the first char (zero based) | 388 * @start: the index of the first char (zero based) |
389 * @len: the length of the substring | 389 * @len: the length of the substring |
390 * | 390 * |
391 * Extract a substring of a given string | 391 * Extract a substring of a given string |
392 * | 392 * |
393 * Returns the xmlChar * for the first occurrence or NULL. | 393 * Returns the xmlChar * for the first occurrence or NULL. |
394 */ | 394 */ |
395 | 395 |
396 xmlChar * | 396 xmlChar * |
397 xmlStrsub(const xmlChar *str, int start, int len) { | 397 xmlStrsub(const xmlChar *str, int start, int len) { |
398 int i; | 398 int i; |
399 | 399 |
400 if (str == NULL) return(NULL); | 400 if (str == NULL) return(NULL); |
401 if (start < 0) return(NULL); | 401 if (start < 0) return(NULL); |
402 if (len < 0) return(NULL); | 402 if (len < 0) return(NULL); |
403 | 403 |
404 for (i = 0;i < start;i++) { | 404 for (i = 0;i < start;i++) { |
405 if (*str == 0) return(NULL); | 405 if (*str == 0) return(NULL); |
406 str++; | 406 str++; |
407 } | 407 } |
408 if (*str == 0) return(NULL); | 408 if (*str == 0) return(NULL); |
409 return(xmlStrndup(str, len)); | 409 return(xmlStrndup(str, len)); |
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
512 * encoded in UTF-8 or an encoding with 8bit based chars, we assume | 512 * encoded in UTF-8 or an encoding with 8bit based chars, we assume |
513 * a termination mark of '0'. | 513 * a termination mark of '0'. |
514 * | 514 * |
515 * Returns a new xmlChar * containing the concatenated string. | 515 * Returns a new xmlChar * containing the concatenated string. |
516 */ | 516 */ |
517 xmlChar * | 517 xmlChar * |
518 xmlStrcat(xmlChar *cur, const xmlChar *add) { | 518 xmlStrcat(xmlChar *cur, const xmlChar *add) { |
519 const xmlChar *p = add; | 519 const xmlChar *p = add; |
520 | 520 |
521 if (add == NULL) return(cur); | 521 if (add == NULL) return(cur); |
522 if (cur == NULL) | 522 if (cur == NULL) |
523 return(xmlStrdup(add)); | 523 return(xmlStrdup(add)); |
524 | 524 |
525 while (*p != 0) p++; /* non input consuming */ | 525 while (*p != 0) p++; /* non input consuming */ |
526 return(xmlStrncat(cur, add, p - add)); | 526 return(xmlStrncat(cur, add, p - add)); |
527 } | 527 } |
528 | 528 |
529 /** | 529 /** |
530 * xmlStrPrintf: | 530 * xmlStrPrintf: |
531 * @buf: the result buffer. | 531 * @buf: the result buffer. |
532 * @len: the result buffer length. | 532 * @len: the result buffer length. |
533 * @msg: the message with printf formatting. | 533 * @msg: the message with printf formatting. |
534 * @...: extra parameters for the message. | 534 * @...: extra parameters for the message. |
535 * | 535 * |
536 * Formats @msg and places result into @buf. | 536 * Formats @msg and places result into @buf. |
537 * | 537 * |
538 * Returns the number of characters written to @buf or -1 if an error occurs. | 538 * Returns the number of characters written to @buf or -1 if an error occurs. |
539 */ | 539 */ |
540 int XMLCDECL | 540 int XMLCDECL |
541 xmlStrPrintf(xmlChar *buf, int len, const xmlChar *msg, ...) { | 541 xmlStrPrintf(xmlChar *buf, int len, const xmlChar *msg, ...) { |
542 va_list args; | 542 va_list args; |
543 int ret; | 543 int ret; |
544 | 544 |
545 if((buf == NULL) || (msg == NULL)) { | 545 if((buf == NULL) || (msg == NULL)) { |
546 return(-1); | 546 return(-1); |
547 } | 547 } |
548 | 548 |
549 va_start(args, msg); | 549 va_start(args, msg); |
550 ret = vsnprintf((char *) buf, len, (const char *) msg, args); | 550 ret = vsnprintf((char *) buf, len, (const char *) msg, args); |
551 va_end(args); | 551 va_end(args); |
552 buf[len - 1] = 0; /* be safe ! */ | 552 buf[len - 1] = 0; /* be safe ! */ |
553 | 553 |
554 return(ret); | 554 return(ret); |
555 } | 555 } |
556 | 556 |
557 /** | 557 /** |
558 * xmlStrVPrintf: | 558 * xmlStrVPrintf: |
559 * @buf: the result buffer. | 559 * @buf: the result buffer. |
560 * @len: the result buffer length. | 560 * @len: the result buffer length. |
561 * @msg: the message with printf formatting. | 561 * @msg: the message with printf formatting. |
562 * @ap: extra parameters for the message. | 562 * @ap: extra parameters for the message. |
563 * | 563 * |
564 * Formats @msg and places result into @buf. | 564 * Formats @msg and places result into @buf. |
565 * | 565 * |
566 * Returns the number of characters written to @buf or -1 if an error occurs. | 566 * Returns the number of characters written to @buf or -1 if an error occurs. |
567 */ | 567 */ |
568 int | 568 int |
569 xmlStrVPrintf(xmlChar *buf, int len, const xmlChar *msg, va_list ap) { | 569 xmlStrVPrintf(xmlChar *buf, int len, const xmlChar *msg, va_list ap) { |
570 int ret; | 570 int ret; |
571 | 571 |
572 if((buf == NULL) || (msg == NULL)) { | 572 if((buf == NULL) || (msg == NULL)) { |
573 return(-1); | 573 return(-1); |
574 } | 574 } |
575 | 575 |
576 ret = vsnprintf((char *) buf, len, (const char *) msg, ap); | 576 ret = vsnprintf((char *) buf, len, (const char *) msg, ap); |
577 buf[len - 1] = 0; /* be safe ! */ | 577 buf[len - 1] = 0; /* be safe ! */ |
578 | 578 |
579 return(ret); | 579 return(ret); |
580 } | 580 } |
581 | 581 |
582 /************************************************************************ | 582 /************************************************************************ |
583 * * | 583 * * |
584 * Generic UTF8 handling routines * | 584 * Generic UTF8 handling routines * |
585 * * | 585 * * |
586 * From rfc2044: encoding of the Unicode values on UTF-8: * | 586 * From rfc2044: encoding of the Unicode values on UTF-8: * |
587 * * | 587 * * |
588 * UCS-4 range (hex.) UTF-8 octet sequence (binary) * | 588 * UCS-4 range (hex.) UTF-8 octet sequence (binary) * |
(...skipping 262 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
851 * @len: the len of @utf (in chars) | 851 * @len: the len of @utf (in chars) |
852 * | 852 * |
853 * a strndup for array of UTF8's | 853 * a strndup for array of UTF8's |
854 * | 854 * |
855 * Returns a new UTF8 * or NULL | 855 * Returns a new UTF8 * or NULL |
856 */ | 856 */ |
857 xmlChar * | 857 xmlChar * |
858 xmlUTF8Strndup(const xmlChar *utf, int len) { | 858 xmlUTF8Strndup(const xmlChar *utf, int len) { |
859 xmlChar *ret; | 859 xmlChar *ret; |
860 int i; | 860 int i; |
861 | 861 |
862 if ((utf == NULL) || (len < 0)) return(NULL); | 862 if ((utf == NULL) || (len < 0)) return(NULL); |
863 i = xmlUTF8Strsize(utf, len); | 863 i = xmlUTF8Strsize(utf, len); |
864 ret = (xmlChar *) xmlMallocAtomic((i + 1) * sizeof(xmlChar)); | 864 ret = (xmlChar *) xmlMallocAtomic((i + 1) * sizeof(xmlChar)); |
865 if (ret == NULL) { | 865 if (ret == NULL) { |
866 xmlGenericError(xmlGenericErrorContext, | 866 xmlGenericError(xmlGenericErrorContext, |
867 "malloc of %ld byte failed\n", | 867 "malloc of %ld byte failed\n", |
868 (len + 1) * (long)sizeof(xmlChar)); | 868 (len + 1) * (long)sizeof(xmlChar)); |
869 return(NULL); | 869 return(NULL); |
870 } | 870 } |
871 memcpy(ret, utf, i * sizeof(xmlChar)); | 871 memcpy(ret, utf, i * sizeof(xmlChar)); |
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
975 if ( (*utf++ & 0xc0) != 0x80 ) | 975 if ( (*utf++ & 0xc0) != 0x80 ) |
976 return(NULL); | 976 return(NULL); |
977 } | 977 } |
978 } | 978 } |
979 | 979 |
980 return(xmlUTF8Strndup(utf, len)); | 980 return(xmlUTF8Strndup(utf, len)); |
981 } | 981 } |
982 | 982 |
983 #define bottom_xmlstring | 983 #define bottom_xmlstring |
984 #include "elfgcchack.h" | 984 #include "elfgcchack.h" |
OLD | NEW |