2 Unix SMB/CIFS implementation.
3 Samba utility functions
5 Copyright (C) Andrew Tridgell 1992-2001
6 Copyright (C) Simo Sorce 2001-2002
7 Copyright (C) Martin Pool 2003
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
28 * @brief String utilities.
32 * Get the next token from a string, return False if none found.
33 * Handles double-quotes.
35 * Based on a routine by GJC@VILLAGE.COM.
36 * Extensively modified by Andrew.Tridgell@anu.edu.au
38 BOOL next_token(const char **ptr,char *buff, const char *sep, size_t bufsize)
50 /* default to simple separators */
54 /* find the first non sep char */
55 while (*s && strchr_m(sep,*s))
62 /* copy over the token */
64 for (quoted = False; len < bufsize && *s && (quoted || !strchr_m(sep,*s)); s++) {
73 *ptr = (*s) ? s+1 : s;
80 This is like next_token but is not re-entrant and "remembers" the first
81 parameter so you can pass NULL. This is useful for user interface code
82 but beware the fact that it is not re-entrant!
85 static const char *last_ptr=NULL;
87 BOOL next_token_nr(const char **ptr,char *buff, const char *sep, size_t bufsize)
91 ptr = (const char **)&last_ptr;
93 ret = next_token(ptr, buff, sep, bufsize);
98 static uint16 tmpbuf[sizeof(pstring)];
100 void set_first_token(char *ptr)
106 Convert list of tokens to array; dependent on above routine.
107 Uses last_ptr from above - bit of a hack.
110 char **toktocliplist(int *ctok, const char *sep)
119 while(*s && strchr_m(sep,*s))
128 while(*s && (!strchr_m(sep,*s)))
130 while(*s && strchr_m(sep,*s))
137 if (!(ret=iret=malloc(ictok*sizeof(char *))))
152 * Case insensitive string compararison.
154 * iconv does not directly give us a way to compare strings in
155 * arbitrary unix character sets -- all we can is convert and then
156 * compare. This is expensive.
158 * As an optimization, we do a first pass that considers only the
159 * prefix of the strings that is entirely 7-bit. Within this, we
160 * check whether they have the same value.
162 * Hopefully this will often give the answer without needing to copy.
163 * In particular it should speed comparisons to literal ascii strings
164 * or comparisons of strings that are "obviously" different.
166 * If we find a non-ascii character we fall back to converting via
169 * This should never be slower than convering the whole thing, and
172 * A different optimization would be to compare for bitwise equality
173 * in the binary encoding. (It would be possible thought hairy to do
174 * both simultaneously.) But in that case if they turn out to be
175 * different, we'd need to restart the whole thing.
177 * Even better is to implement strcasecmp for each encoding and use a
180 int StrCaseCmp(const char *s, const char *t)
183 const char * ps, * pt;
186 for (ps = s, pt = t; ; ps++, pt++) {
190 return 0; /* both ended */
192 return -1; /* s is a prefix */
194 return +1; /* t is a prefix */
195 else if ((*ps & 0x80) || (*pt & 0x80))
196 /* not ascii anymore, do it the hard way from here on in */
209 /* TODO: Don't do this with a fixed-length buffer. This could
210 * still be much more efficient. */
211 /* TODO: Hardcode a char-by-char comparison for UTF-8, which
212 * can be much faster. */
213 /* TODO: Test case for this! */
215 unix_strupper(ps, strlen(ps)+1, buf1, sizeof(buf1));
216 unix_strupper(pt, strlen(pt)+1, buf2, sizeof(buf2));
218 return strcmp(buf1, buf2);
223 Case insensitive string compararison, length limited.
225 int StrnCaseCmp(const char *s, const char *t, size_t n)
228 unix_strupper(s, strlen(s)+1, buf1, sizeof(buf1));
229 unix_strupper(t, strlen(t)+1, buf2, sizeof(buf2));
230 return strncmp(buf1,buf2,n);
236 * @note The comparison is case-insensitive.
238 BOOL strequal(const char *s1, const char *s2)
245 return(StrCaseCmp(s1,s2)==0);
249 * Compare 2 strings up to and including the nth char.
251 * @note The comparison is case-insensitive.
253 BOOL strnequal(const char *s1,const char *s2,size_t n)
257 if (!s1 || !s2 || !n)
260 return(StrnCaseCmp(s1,s2,n)==0);
264 Compare 2 strings (case sensitive).
267 BOOL strcsequal(const char *s1,const char *s2)
274 return(strcmp(s1,s2)==0);
278 Do a case-insensitive, whitespace-ignoring string compare.
281 int strwicmp(const char *psz1, const char *psz2)
283 /* if BOTH strings are NULL, return TRUE, if ONE is NULL return */
284 /* appropriate value. */
287 else if (psz1 == NULL)
289 else if (psz2 == NULL)
292 /* sync the strings on first non-whitespace */
294 while (isspace((int)*psz1))
296 while (isspace((int)*psz2))
298 if (toupper(*psz1) != toupper(*psz2) || *psz1 == '\0'
304 return (*psz1 - *psz2);
309 Convert a string to upper case, but don't modify it.
312 char *strupper_static(const char *s)
323 Convert a string to "normal" form.
326 void strnorm(char *s)
328 extern int case_default;
329 if (case_default == CASE_UPPER)
336 Check if a string is in "normal" case.
339 BOOL strisnormal(const char *s)
341 extern int case_default;
342 if (case_default == CASE_UPPER)
343 return(!strhaslower(s));
345 return(!strhasupper(s));
351 NOTE: oldc and newc must be 7 bit characters
354 void string_replace(char *s,char oldc,char newc)
356 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
357 string_replace_w(tmpbuf, UCS2_CHAR(oldc), UCS2_CHAR(newc));
358 pull_ucs2(NULL, s, tmpbuf, -1, sizeof(tmpbuf), STR_TERMINATE);
362 Skip past some strings in a buffer.
365 char *skip_string(char *buf,size_t n)
368 buf += strlen(buf) + 1;
373 Count the number of characters in a string. Normally this will
374 be the same as the number of bytes in a string for single byte strings,
375 but will be different for multibyte.
378 size_t str_charnum(const char *s)
380 uint16 tmpbuf2[sizeof(pstring)];
381 push_ucs2(NULL, tmpbuf2,s, sizeof(tmpbuf2), STR_TERMINATE);
382 return strlen_w(tmpbuf2);
386 Count the number of characters in a string. Normally this will
387 be the same as the number of bytes in a string for single byte strings,
388 but will be different for multibyte.
391 size_t str_ascii_charnum(const char *s)
394 push_ascii(tmpbuf2, s, sizeof(tmpbuf2), STR_TERMINATE);
395 return strlen(tmpbuf2);
399 Trim the specified elements off the front and back of a string.
402 BOOL trim_string(char *s,const char *front,const char *back)
409 /* Ignore null or empty strings. */
410 if (!s || (s[0] == '\0'))
413 front_len = front? strlen(front) : 0;
414 back_len = back? strlen(back) : 0;
419 while (len && strncmp(s, front, front_len)==0) {
420 memcpy(s, s+front_len, (len-front_len)+1);
427 while ((len >= back_len) && strncmp(s+len-back_len,back,back_len)==0) {
428 s[len-back_len]='\0';
437 Does a string have any uppercase chars in it?
440 BOOL strhasupper(const char *s)
443 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
444 for(ptr=tmpbuf;*ptr;ptr++)
451 Does a string have any lowercase chars in it?
454 BOOL strhaslower(const char *s)
457 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
458 for(ptr=tmpbuf;*ptr;ptr++)
465 Find the number of 'c' chars in a string
468 size_t count_chars(const char *s,char c)
472 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
473 for(count=0,ptr=tmpbuf;*ptr;ptr++)
474 if(*ptr==UCS2_CHAR(c))
480 Safe string copy into a known length string. maxlength does not
481 include the terminating zero.
484 char *safe_strcpy_fn(const char *fn, int line, char *dest,const char *src, size_t maxlength)
489 DEBUG(0,("ERROR: NULL dest in safe_strcpy\n"));
493 clobber_region(fn,line,dest, maxlength+1);
500 len = strnlen(src, maxlength+1);
502 if (len > maxlength) {
503 DEBUG(0,("ERROR: string overflow by %u (%u - %u) in safe_strcpy [%.50s]\n",
504 (unsigned int)(len-maxlength), len, maxlength, src));
508 memmove(dest, src, len);
514 Safe string cat into a string. maxlength does not
515 include the terminating zero.
517 char *safe_strcat_fn(const char *fn, int line, char *dest, const char *src, size_t maxlength)
519 size_t src_len, dest_len;
522 DEBUG(0,("ERROR: NULL dest in safe_strcat\n"));
529 src_len = strnlen(src, maxlength + 1);
530 dest_len = strnlen(dest, maxlength + 1);
532 clobber_region(fn, line, dest + dest_len, maxlength + 1 - dest_len);
534 if (src_len + dest_len > maxlength) {
535 DEBUG(0,("ERROR: string overflow by %d in safe_strcat [%.50s]\n",
536 (int)(src_len + dest_len - maxlength), src));
537 if (maxlength > dest_len) {
538 memcpy(&dest[dest_len], src, maxlength - dest_len);
544 memcpy(&dest[dest_len], src, src_len);
545 dest[dest_len + src_len] = 0;
550 Paranoid strcpy into a buffer of given length (includes terminating
551 zero. Strips out all but 'a-Z0-9' and the character in other_safe_chars
552 and replaces with '_'. Deliberately does *NOT* check for multibyte
553 characters. Don't change it !
555 char *alpha_strcpy_fn(const char *fn, int line, char *dest, const char *src, const char *other_safe_chars, size_t maxlength)
559 clobber_region(fn, line, dest, maxlength);
562 DEBUG(0,("ERROR: NULL dest in alpha_strcpy\n"));
572 if (len >= maxlength)
575 if (!other_safe_chars)
576 other_safe_chars = "";
578 for(i = 0; i < len; i++) {
579 int val = (src[i] & 0xff);
580 if (isupper(val) || islower(val) || isdigit(val) || strchr_m(other_safe_chars, val))
592 Like strncpy but always null terminates. Make sure there is room!
593 The variable n should always be one less than the available size.
595 char *StrnCpy_fn(const char *fn, int line,char *dest,const char *src,size_t n)
599 clobber_region(fn, line, dest, n+1);
609 while (n-- && (*d = *src)) {
620 Like strncpy but copies up to the character marker. always null terminates.
621 returns a pointer to the character marker in the source string (src).
624 static char *strncpyn(char *dest, const char *src, size_t n, char c)
629 clobber_region(dest, n+1);
631 p = strchr_m(src, c);
633 DEBUG(5, ("strncpyn: separator character (%c) not found\n", c));
637 str_len = PTR_DIFF(p, src);
638 strncpy(dest, src, MIN(n, str_len));
639 dest[str_len] = '\0';
646 Routine to get hex characters and turn them into a 16 byte array.
647 the array can be variable length, and any non-hex-numeric
648 characters are skipped. "0xnn" or "0Xnn" is specially catered
651 valid examples: "0A5D15"; "0x15, 0x49, 0xa2"; "59\ta9\te3\n"
655 size_t strhex_to_str(char *p, size_t len, const char *strhex)
658 size_t num_chars = 0;
659 unsigned char lonybble, hinybble;
660 const char *hexchars = "0123456789ABCDEF";
661 char *p1 = NULL, *p2 = NULL;
663 for (i = 0; i < len && strhex[i] != 0; i++) {
664 if (strnequal(hexchars, "0x", 2)) {
665 i++; /* skip two chars */
669 if (!(p1 = strchr_m(hexchars, toupper(strhex[i]))))
672 i++; /* next hex digit */
674 if (!(p2 = strchr_m(hexchars, toupper(strhex[i]))))
677 /* get the two nybbles */
678 hinybble = PTR_DIFF(p1, hexchars);
679 lonybble = PTR_DIFF(p2, hexchars);
681 p[num_chars] = (hinybble << 4) | lonybble;
691 * Routine to print a buffer as HEX digits, into an allocated string.
694 void hex_encode(const unsigned char *buff_in, size_t len, char **out_hex_buffer)
699 *out_hex_buffer = smb_xmalloc((len*2)+1);
700 hex_buffer = *out_hex_buffer;
702 for (i = 0; i < len; i++)
703 slprintf(&hex_buffer[i*2], 3, "%02X", buff_in[i]);
707 Check if a string is part of a list.
710 BOOL in_list(char *s,char *list,BOOL casesensitive)
718 while (next_token(&p,tok,LIST_SEP,sizeof(tok))) {
720 if (strcmp(tok,s) == 0)
723 if (StrCaseCmp(tok,s) == 0)
730 /* this is used to prevent lots of mallocs of size 1 */
731 static char *null_string = NULL;
734 Set a string value, allocing the space for the string
737 static BOOL string_init(char **dest,const char *src)
747 if((null_string = (char *)malloc(1)) == NULL) {
748 DEBUG(0,("string_init: malloc fail for null_string.\n"));
755 (*dest) = strdup(src);
756 if ((*dest) == NULL) {
757 DEBUG(0,("Out of memory in string_init\n"));
768 void string_free(char **s)
772 if (*s == null_string)
778 Set a string value, deallocating any existing space, and allocing the space
782 BOOL string_set(char **dest,const char *src)
785 return(string_init(dest,src));
789 Substitute a string for a pattern in another string. Make sure there is
792 This routine looks for pattern in s and replaces it with
793 insert. It may do multiple replacements.
795 Any of " ; ' $ or ` in the insert string are replaced with _
796 if len==0 then the string cannot be extended. This is different from the old
797 use of len==0 which was for no length checks to be done.
800 void string_sub(char *s,const char *pattern, const char *insert, size_t len)
805 if (!insert || !pattern || !*pattern || !s)
808 ls = (ssize_t)strlen(s);
809 lp = (ssize_t)strlen(pattern);
810 li = (ssize_t)strlen(insert);
813 len = ls + 1; /* len is number of *bytes* */
815 while (lp <= ls && (p = strstr(s,pattern))) {
816 if (ls + (li-lp) >= len) {
817 DEBUG(0,("ERROR: string overflow by %d in string_sub(%.50s, %d)\n",
818 (int)(ls + (li-lp) - len),
823 memmove(p+li,p+lp,strlen(p+lp)+1);
846 void fstring_sub(char *s,const char *pattern,const char *insert)
848 string_sub(s, pattern, insert, sizeof(fstring));
851 void pstring_sub(char *s,const char *pattern,const char *insert)
853 string_sub(s, pattern, insert, sizeof(pstring));
857 Similar to string_sub, but it will accept only allocated strings
858 and may realloc them so pay attention at what you pass on no
859 pointers inside strings, no pstrings or const may be passed
863 char *realloc_string_sub(char *string, const char *pattern, const char *insert)
867 ssize_t ls,lp,li,ld, i;
869 if (!insert || !pattern || !*pattern || !string || !*string)
876 DEBUG(0, ("realloc_string_sub: out of memory!\n"));
879 ls = (ssize_t)strlen(s);
880 lp = (ssize_t)strlen(pattern);
881 li = (ssize_t)strlen(insert);
900 while ((p = strstr(s,pattern))) {
902 char *t = Realloc(string, ls + ld + 1);
904 DEBUG(0, ("realloc_string_sub: out of memory!\n"));
912 memmove(p+li,p+lp,strlen(p+lp)+1);
923 Similar to string_sub() but allows for any character to be substituted.
925 if len==0 then the string cannot be extended. This is different from the old
926 use of len==0 which was for no length checks to be done.
929 void all_string_sub(char *s,const char *pattern,const char *insert, size_t len)
934 if (!insert || !pattern || !s)
937 ls = (ssize_t)strlen(s);
938 lp = (ssize_t)strlen(pattern);
939 li = (ssize_t)strlen(insert);
945 len = ls + 1; /* len is number of *bytes* */
947 while (lp <= ls && (p = strstr(s,pattern))) {
948 if (ls + (li-lp) >= len) {
949 DEBUG(0,("ERROR: string overflow by %d in all_string_sub(%.50s, %d)\n",
950 (int)(ls + (li-lp) - len),
955 memmove(p+li,p+lp,strlen(p+lp)+1);
957 memcpy(p, insert, li);
964 Similar to all_string_sub but for unicode strings.
965 Return a new allocated unicode string.
966 similar to string_sub() but allows for any character to be substituted.
970 static smb_ucs2_t *all_string_sub_w(const smb_ucs2_t *s, const smb_ucs2_t *pattern,
971 const smb_ucs2_t *insert)
974 const smb_ucs2_t *sp;
975 size_t lr, lp, li, lt;
977 if (!insert || !pattern || !*pattern || !s)
980 lt = (size_t)strlen_w(s);
981 lp = (size_t)strlen_w(pattern);
982 li = (size_t)strlen_w(insert);
985 const smb_ucs2_t *st = s;
987 while ((sp = strstr_w(st, pattern))) {
993 r = rp = (smb_ucs2_t *)malloc((lt + 1)*(sizeof(smb_ucs2_t)));
995 DEBUG(0, ("all_string_sub_w: out of memory!\n"));
999 while ((sp = strstr_w(s, pattern))) {
1000 memcpy(rp, s, (sp - s));
1001 rp += ((sp - s) / sizeof(smb_ucs2_t));
1002 memcpy(rp, insert, (li * sizeof(smb_ucs2_t)));
1006 lr = ((rp - r) / sizeof(smb_ucs2_t));
1008 memcpy(rp, s, ((lt - lr) * sizeof(smb_ucs2_t)));
1016 smb_ucs2_t *all_string_sub_wa(smb_ucs2_t *s, const char *pattern,
1021 if (!insert || !pattern || !s)
1023 push_ucs2(NULL, p, pattern, sizeof(wpstring) - 1, STR_TERMINATE);
1024 push_ucs2(NULL, i, insert, sizeof(wpstring) - 1, STR_TERMINATE);
1025 return all_string_sub_w(s, p, i);
1030 Splits out the front and back at a separator.
1033 static void split_at_last_component(char *path, char *front, char sep, char *back)
1035 char *p = strrchr_m(path, sep);
1041 pstrcpy(front, path);
1055 Write an octal as a string.
1058 const char *octal_string(int i)
1060 static char ret[64];
1063 slprintf(ret, sizeof(ret)-1, "0%o", i);
1069 Truncate a string at a specified length.
1072 char *string_truncate(char *s, unsigned int length)
1074 if (s && strlen(s) > length)
1080 Strchr and strrchr_m are very hard to do on general multi-byte strings.
1081 We convert via ucs2 for now.
1084 char *strchr_m(const char *s, char c)
1090 push_ucs2(NULL, ws, s, sizeof(ws), STR_TERMINATE);
1091 p = strchr_w(ws, UCS2_CHAR(c));
1095 pull_ucs2_pstring(s2, ws);
1096 return (char *)(s+strlen(s2));
1099 char *strrchr_m(const char *s, char c)
1105 push_ucs2(NULL, ws, s, sizeof(ws), STR_TERMINATE);
1106 p = strrchr_w(ws, UCS2_CHAR(c));
1110 pull_ucs2_pstring(s2, ws);
1111 return (char *)(s+strlen(s2));
1114 /***********************************************************************
1115 Return the equivalent of doing strrchr 'n' times - always going
1117 ***********************************************************************/
1119 char *strnrchr_m(const char *s, char c, unsigned int n)
1125 push_ucs2(NULL, ws, s, sizeof(ws), STR_TERMINATE);
1126 p = strnrchr_w(ws, UCS2_CHAR(c), n);
1130 pull_ucs2_pstring(s2, ws);
1131 return (char *)(s+strlen(s2));
1135 Convert a string to lower case.
1138 void strlower_m(char *s)
1140 /* this is quite a common operation, so we want it to be
1141 fast. We optimise for the ascii case, knowing that all our
1142 supported multi-byte character sets are ascii-compatible
1143 (ie. they match for the first 128 chars) */
1145 while (*s && !(((unsigned char)s[0]) & 0x7F)) {
1146 *s = tolower((unsigned char)*s);
1153 /* I assume that lowercased string takes the same number of bytes
1154 * as source string even in UTF-8 encoding. (VIV) */
1155 unix_strlower(s,strlen(s)+1,s,strlen(s)+1);
1159 Duplicate convert a string to lower case.
1162 char *strdup_lower(const char *s)
1164 char *t = strdup(s);
1166 DEBUG(0, ("strdup_lower: Out of memory!\n"));
1174 Convert a string to upper case.
1177 void strupper_m(char *s)
1179 /* this is quite a common operation, so we want it to be
1180 fast. We optimise for the ascii case, knowing that all our
1181 supported multi-byte character sets are ascii-compatible
1182 (ie. they match for the first 128 chars) */
1184 while (*s && !(((unsigned char)s[0]) & 0x7F)) {
1185 *s = toupper((unsigned char)*s);
1192 /* I assume that lowercased string takes the same number of bytes
1193 * as source string even in multibyte encoding. (VIV) */
1194 unix_strupper(s,strlen(s)+1,s,strlen(s)+1);
1198 Convert a string to upper case.
1201 char *strdup_upper(const char *s)
1203 char *t = strdup(s);
1205 DEBUG(0, ("strdup_upper: Out of memory!\n"));
1213 Return a RFC2254 binary string representation of a buffer.
1214 Used in LDAP filters.
1218 char *binary_string(char *buf, int len)
1222 const char *hex = "0123456789ABCDEF";
1223 s = malloc(len * 3 + 1);
1226 for (j=i=0;i<len;i++) {
1228 s[j+1] = hex[((unsigned char)buf[i]) >> 4];
1229 s[j+2] = hex[((unsigned char)buf[i]) & 0xF];
1237 Just a typesafety wrapper for snprintf into a pstring.
1240 int pstr_sprintf(pstring s, const char *fmt, ...)
1246 ret = vsnprintf(s, PSTRING_LEN, fmt, ap);
1253 Just a typesafety wrapper for snprintf into a fstring.
1256 int fstr_sprintf(fstring s, const char *fmt, ...)
1262 ret = vsnprintf(s, FSTRING_LEN, fmt, ap);
1268 #ifndef HAVE_STRNDUP
1270 Some platforms don't have strndup.
1273 char *strndup(const char *s, size_t n)
1288 #ifndef HAVE_STRNLEN
1290 Some platforms don't have strnlen
1293 size_t strnlen(const char *s, size_t n)
1296 for (i=0; s[i] && i<n; i++)
1303 List of Strings manipulation functions
1306 #define S_LIST_ABS 16 /* List Allocation Block Size */
1308 char **str_list_make(const char *string, const char *sep)
1310 char **list, **rlist;
1316 if (!string || !*string)
1320 DEBUG(0,("str_list_make: Unable to allocate memory"));
1323 if (!sep) sep = LIST_SEP;
1329 while (next_token(&str, tok, sep, sizeof(tok))) {
1331 lsize += S_LIST_ABS;
1332 rlist = (char **)Realloc(list, ((sizeof(char **)) * (lsize +1)));
1334 DEBUG(0,("str_list_make: Unable to allocate memory"));
1335 str_list_free(&list);
1340 memset (&list[num], 0, ((sizeof(char**)) * (S_LIST_ABS +1)));
1343 list[num] = strdup(tok);
1345 DEBUG(0,("str_list_make: Unable to allocate memory"));
1346 str_list_free(&list);
1358 BOOL str_list_copy(char ***dest, const char **src)
1360 char **list, **rlist;
1372 lsize += S_LIST_ABS;
1373 rlist = (char **)Realloc(list, ((sizeof(char **)) * (lsize +1)));
1375 DEBUG(0,("str_list_copy: Unable to re-allocate memory"));
1376 str_list_free(&list);
1380 memset (&list[num], 0, ((sizeof(char **)) * (S_LIST_ABS +1)));
1383 list[num] = strdup(src[num]);
1385 DEBUG(0,("str_list_copy: Unable to allocate memory"));
1386 str_list_free(&list);
1398 * Return true if all the elements of the list match exactly.
1400 BOOL str_list_compare(char **list1, char **list2)
1404 if (!list1 || !list2)
1405 return (list1 == list2);
1407 for (num = 0; list1[num]; num++) {
1410 if (!strcsequal(list1[num], list2[num]))
1414 return False; /* if list2 has more elements than list1 fail */
1419 void str_list_free(char ***list)
1423 if (!list || !*list)
1426 for(; *tlist; tlist++)
1431 BOOL str_list_substitute(char **list, const char *pattern, const char *insert)
1434 ssize_t ls, lp, li, ld, i, d;
1443 lp = (ssize_t)strlen(pattern);
1444 li = (ssize_t)strlen(insert);
1449 ls = (ssize_t)strlen(s);
1451 while ((p = strstr(s, pattern))) {
1455 t = (char *) malloc(ls +ld +1);
1457 DEBUG(0,("str_list_substitute: Unable to allocate memory"));
1460 memcpy(t, *list, d);
1461 memcpy(t +d +li, p +lp, ls -d -lp +1);
1468 for (i = 0; i < li; i++) {
1469 switch (insert[i]) {
1481 t[d +i] = insert[i];
1493 #define IPSTR_LIST_SEP ","
1494 #define IPSTR_LIST_CHAR ','
1497 * Add ip string representation to ipstr list. Used also
1498 * as part of @function ipstr_list_make
1500 * @param ipstr_list pointer to string containing ip list;
1501 * MUST BE already allocated and IS reallocated if necessary
1502 * @param ipstr_size pointer to current size of ipstr_list (might be changed
1503 * as a result of reallocation)
1504 * @param ip IP address which is to be added to list
1505 * @return pointer to string appended with new ip and possibly
1506 * reallocated to new length
1509 char* ipstr_list_add(char** ipstr_list, const struct ip_service *service)
1511 char* new_ipstr = NULL;
1513 /* arguments checking */
1514 if (!ipstr_list || !service) return NULL;
1516 /* attempt to convert ip to a string and append colon separator to it */
1518 asprintf(&new_ipstr, "%s%s%s:%d", *ipstr_list, IPSTR_LIST_SEP,
1519 inet_ntoa(service->ip), service->port);
1520 SAFE_FREE(*ipstr_list);
1522 asprintf(&new_ipstr, "%s:%d", inet_ntoa(service->ip), service->port);
1524 *ipstr_list = new_ipstr;
1530 * Allocate and initialise an ipstr list using ip adresses
1531 * passed as arguments.
1533 * @param ipstr_list pointer to string meant to be allocated and set
1534 * @param ip_list array of ip addresses to place in the list
1535 * @param ip_count number of addresses stored in ip_list
1536 * @return pointer to allocated ip string
1539 char* ipstr_list_make(char** ipstr_list, const struct ip_service* ip_list, int ip_count)
1543 /* arguments checking */
1544 if (!ip_list && !ipstr_list) return 0;
1548 /* process ip addresses given as arguments */
1549 for (i = 0; i < ip_count; i++)
1550 *ipstr_list = ipstr_list_add(ipstr_list, &ip_list[i]);
1552 return (*ipstr_list);
1557 * Parse given ip string list into array of ip addresses
1558 * (as ip_service structures)
1559 * e.g. 192.168.1.100:389,192.168.1.78, ...
1561 * @param ipstr ip string list to be parsed
1562 * @param ip_list pointer to array of ip addresses which is
1563 * allocated by this function and must be freed by caller
1564 * @return number of succesfully parsed addresses
1567 int ipstr_list_parse(const char* ipstr_list, struct ip_service **ip_list)
1573 if (!ipstr_list || !ip_list)
1576 count = count_chars(ipstr_list, IPSTR_LIST_CHAR) + 1;
1577 if ( (*ip_list = (struct ip_service*)malloc(count * sizeof(struct ip_service))) == NULL ) {
1578 DEBUG(0,("ipstr_list_parse: malloc failed for %d entries\n", count));
1583 next_token(&ipstr_list, token_str, IPSTR_LIST_SEP, FSTRING_LEN) && i<count;
1586 struct in_addr addr;
1588 char *p = strchr(token_str, ':');
1595 /* convert single token to ip address */
1596 if ( (addr.s_addr = inet_addr(token_str)) == INADDR_NONE )
1599 (*ip_list)[i].ip = addr;
1600 (*ip_list)[i].port = port;
1608 * Safely free ip string list
1610 * @param ipstr_list ip string list to be freed
1613 void ipstr_list_free(char* ipstr_list)
1615 SAFE_FREE(ipstr_list);
1620 Unescape a URL encoded string, in place.
1623 void rfc1738_unescape(char *buf)
1627 while ((p=strchr_m(p,'+')))
1632 while (p && *p && (p=strchr_m(p,'%'))) {
1636 if (c1 >= '0' && c1 <= '9')
1638 else if (c1 >= 'A' && c1 <= 'F')
1640 else if (c1 >= 'a' && c1 <= 'f')
1642 else {p++; continue;}
1644 if (c2 >= '0' && c2 <= '9')
1646 else if (c2 >= 'A' && c2 <= 'F')
1648 else if (c2 >= 'a' && c2 <= 'f')
1650 else {p++; continue;}
1654 memmove(p+1, p+3, strlen(p+3)+1);
1659 static const char *b64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
1662 * Decode a base64 string into a DATA_BLOB - simple and slow algorithm
1664 DATA_BLOB base64_decode_data_blob(const char *s)
1666 int bit_offset, byte_offset, idx, i, n;
1667 DATA_BLOB decoded = data_blob(s, strlen(s)+1);
1668 unsigned char *d = decoded.data;
1673 while (*s && (p=strchr_m(b64,*s))) {
1674 idx = (int)(p - b64);
1675 byte_offset = (i*6)/8;
1676 bit_offset = (i*6)%8;
1677 d[byte_offset] &= ~((1<<(8-bit_offset))-1);
1678 if (bit_offset < 3) {
1679 d[byte_offset] |= (idx << (2-bit_offset));
1682 d[byte_offset] |= (idx >> (bit_offset-2));
1683 d[byte_offset+1] = 0;
1684 d[byte_offset+1] |= (idx << (8-(bit_offset-2))) & 0xFF;
1696 * Decode a base64 string in-place - wrapper for the above
1698 void base64_decode_inplace(char *s)
1700 DATA_BLOB decoded = base64_decode_data_blob(s);
1701 memcpy(s, decoded.data, decoded.length);
1702 /* null terminate */
1703 s[decoded.length] = '\0';
1705 data_blob_free(&decoded);
1709 * Encode a base64 string into a malloc()ed string caller to free.
1711 *From SQUID: adopted from http://ftp.sunet.se/pub2/gnu/vm/base64-encode.c with adjustments
1713 char * base64_encode_data_blob(DATA_BLOB data)
1718 size_t len = data.length;
1719 size_t output_len = data.length * 2;
1720 char *result = malloc(output_len); /* get us plenty of space */
1722 while (len-- && out_cnt < (data.length * 2) - 5) {
1723 int c = (unsigned char) *(data.data++);
1726 if (char_count == 3) {
1727 result[out_cnt++] = b64[bits >> 18];
1728 result[out_cnt++] = b64[(bits >> 12) & 0x3f];
1729 result[out_cnt++] = b64[(bits >> 6) & 0x3f];
1730 result[out_cnt++] = b64[bits & 0x3f];
1737 if (char_count != 0) {
1738 bits <<= 16 - (8 * char_count);
1739 result[out_cnt++] = b64[bits >> 18];
1740 result[out_cnt++] = b64[(bits >> 12) & 0x3f];
1741 if (char_count == 1) {
1742 result[out_cnt++] = '=';
1743 result[out_cnt++] = '=';
1745 result[out_cnt++] = b64[(bits >> 6) & 0x3f];
1746 result[out_cnt++] = '=';
1749 result[out_cnt] = '\0'; /* terminate */
1753 /* read a SMB_BIG_UINT from a string */
1754 SMB_BIG_UINT STR_TO_SMB_BIG_UINT(const char *nptr, const char **entptr)
1757 SMB_BIG_UINT val = -1;
1758 const char *p = nptr;
1760 while (p && *p && isspace(*p))
1762 #ifdef LARGE_SMB_OFF_T
1763 sscanf(p,"%llu",&val);
1764 #else /* LARGE_SMB_OFF_T */
1765 sscanf(p,"%lu",&val);
1766 #endif /* LARGE_SMB_OFF_T */
1768 while (p && *p && isdigit(*p))