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)
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)
112 char *s=(char *)last_ptr;
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+1)*sizeof(char *))))
155 * Case insensitive string compararison.
157 * iconv does not directly give us a way to compare strings in
158 * arbitrary unix character sets -- all we can is convert and then
159 * compare. This is expensive.
161 * As an optimization, we do a first pass that considers only the
162 * prefix of the strings that is entirely 7-bit. Within this, we
163 * check whether they have the same value.
165 * Hopefully this will often give the answer without needing to copy.
166 * In particular it should speed comparisons to literal ascii strings
167 * or comparisons of strings that are "obviously" different.
169 * If we find a non-ascii character we fall back to converting via
172 * This should never be slower than convering the whole thing, and
175 * A different optimization would be to compare for bitwise equality
176 * in the binary encoding. (It would be possible thought hairy to do
177 * both simultaneously.) But in that case if they turn out to be
178 * different, we'd need to restart the whole thing.
180 * Even better is to implement strcasecmp for each encoding and use a
183 int StrCaseCmp(const char *s, const char *t)
186 const char * ps, * pt;
188 smb_ucs2_t *buffer_s, *buffer_t;
191 for (ps = s, pt = t; ; ps++, pt++) {
195 return 0; /* both ended */
197 return -1; /* s is a prefix */
199 return +1; /* t is a prefix */
200 else if ((*ps & 0x80) || (*pt & 0x80))
201 /* not ascii anymore, do it the hard way from here on in */
214 size = push_ucs2_allocate(&buffer_s, s);
215 if (size == (size_t)-1) {
217 /* Not quite the right answer, but finding the right one
218 under this failure case is expensive, and it's pretty close */
221 size = push_ucs2_allocate(&buffer_t, t);
222 if (size == (size_t)-1) {
225 /* Not quite the right answer, but finding the right one
226 under this failure case is expensive, and it's pretty close */
229 ret = strcasecmp_w(buffer_s, buffer_t);
237 Case insensitive string compararison, length limited.
239 int StrnCaseCmp(const char *s, const char *t, size_t n)
242 unix_strupper(s, strlen(s)+1, buf1, sizeof(buf1));
243 unix_strupper(t, strlen(t)+1, buf2, sizeof(buf2));
244 return strncmp(buf1,buf2,n);
250 * @note The comparison is case-insensitive.
252 BOOL strequal(const char *s1, const char *s2)
259 return(StrCaseCmp(s1,s2)==0);
263 * Compare 2 strings up to and including the nth char.
265 * @note The comparison is case-insensitive.
267 BOOL strnequal(const char *s1,const char *s2,size_t n)
271 if (!s1 || !s2 || !n)
274 return(StrnCaseCmp(s1,s2,n)==0);
278 Compare 2 strings (case sensitive).
281 BOOL strcsequal(const char *s1,const char *s2)
288 return(strcmp(s1,s2)==0);
292 Do a case-insensitive, whitespace-ignoring string compare.
295 int strwicmp(const char *psz1, const char *psz2)
297 /* if BOTH strings are NULL, return TRUE, if ONE is NULL return */
298 /* appropriate value. */
301 else if (psz1 == NULL)
303 else if (psz2 == NULL)
306 /* sync the strings on first non-whitespace */
308 while (isspace((int)*psz1))
310 while (isspace((int)*psz2))
312 if (toupper(*psz1) != toupper(*psz2) || *psz1 == '\0'
318 return (*psz1 - *psz2);
323 Convert a string to upper case, but don't modify it.
326 char *strupper_static(const char *s)
337 Convert a string to "normal" form.
340 void strnorm(char *s, int case_default)
342 if (case_default == CASE_UPPER)
349 Check if a string is in "normal" case.
352 BOOL strisnormal(const char *s, int case_default)
354 if (case_default == CASE_UPPER)
355 return(!strhaslower(s));
357 return(!strhasupper(s));
363 NOTE: oldc and newc must be 7 bit characters
366 void string_replace(pstring s,char oldc,char newc)
370 /* this is quite a common operation, so we want it to be
371 fast. We optimise for the ascii case, knowing that all our
372 supported multi-byte character sets are ascii-compatible
373 (ie. they match for the first 128 chars) */
375 for (p = (unsigned char *)s; *p; p++) {
376 if (*p & 0x80) /* mb string - slow path. */
385 /* Slow (mb) path. */
386 #ifdef BROKEN_UNICODE_COMPOSE_CHARACTERS
387 /* With compose characters we must restart from the beginning. JRA. */
390 push_ucs2(NULL, tmpbuf, p, sizeof(tmpbuf), STR_TERMINATE);
391 string_replace_w(tmpbuf, UCS2_CHAR(oldc), UCS2_CHAR(newc));
392 pull_ucs2(NULL, p, tmpbuf, -1, sizeof(tmpbuf), STR_TERMINATE);
396 Skip past some strings in a buffer.
399 char *skip_string(char *buf,size_t n)
402 buf += strlen(buf) + 1;
407 Count the number of characters in a string. Normally this will
408 be the same as the number of bytes in a string for single byte strings,
409 but will be different for multibyte.
412 size_t str_charnum(const char *s)
414 uint16 tmpbuf2[sizeof(pstring)];
415 push_ucs2(NULL, tmpbuf2,s, sizeof(tmpbuf2), STR_TERMINATE);
416 return strlen_w(tmpbuf2);
420 Count the number of characters in a string. Normally this will
421 be the same as the number of bytes in a string for single byte strings,
422 but will be different for multibyte.
425 size_t str_ascii_charnum(const char *s)
428 push_ascii(tmpbuf2, s, sizeof(tmpbuf2), STR_TERMINATE);
429 return strlen(tmpbuf2);
432 BOOL trim_char(char *s,char cfront,char cback)
438 /* Ignore null or empty strings. */
439 if (!s || (s[0] == '\0'))
443 while (*fp && *fp == cfront)
446 /* We ate the string. */
454 ep = fp + strlen(fp) - 1;
456 /* Attempt ascii only. Bail for mb strings. */
457 while ((ep >= fp) && (*ep == cback)) {
459 if ((ep > fp) && (((unsigned char)ep[-1]) & 0x80)) {
460 /* Could be mb... bail back to tim_string. */
468 return trim_string(s, cfront ? fs : NULL, bs);
474 /* We ate the string. */
481 memmove(s, fp, ep-fp+2);
486 Trim the specified elements off the front and back of a string.
489 BOOL trim_string(char *s,const char *front,const char *back)
496 /* Ignore null or empty strings. */
497 if (!s || (s[0] == '\0'))
500 front_len = front? strlen(front) : 0;
501 back_len = back? strlen(back) : 0;
506 while (len && strncmp(s, front, front_len)==0) {
507 /* Must use memmove here as src & dest can
508 * easily overlap. Found by valgrind. JRA. */
509 memmove(s, s+front_len, (len-front_len)+1);
516 while ((len >= back_len) && strncmp(s+len-back_len,back,back_len)==0) {
517 s[len-back_len]='\0';
526 Does a string have any uppercase chars in it?
529 BOOL strhasupper(const char *s)
532 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
533 for(ptr=tmpbuf;*ptr;ptr++)
540 Does a string have any lowercase chars in it?
543 BOOL strhaslower(const char *s)
546 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
547 for(ptr=tmpbuf;*ptr;ptr++)
554 Find the number of 'c' chars in a string
557 size_t count_chars(const char *s,char c)
561 smb_ucs2_t *alloc_tmpbuf = NULL;
563 if (push_ucs2_allocate(&alloc_tmpbuf, s) == (size_t)-1) {
567 for(count=0,ptr=alloc_tmpbuf;*ptr;ptr++)
568 if(*ptr==UCS2_CHAR(c))
571 SAFE_FREE(alloc_tmpbuf);
576 Safe string copy into a known length string. maxlength does not
577 include the terminating zero.
580 char *safe_strcpy_fn(const char *fn, int line, char *dest,const char *src, size_t maxlength)
585 DEBUG(0,("ERROR: NULL dest in safe_strcpy, called from [%s][%d]\n", fn, line));
590 clobber_region(fn,line,dest, maxlength+1);
598 len = strnlen(src, maxlength+1);
600 if (len > maxlength) {
601 DEBUG(0,("ERROR: string overflow by %lu (%lu - %lu) in safe_strcpy [%.50s]\n",
602 (unsigned long)(len-maxlength), (unsigned long)len,
603 (unsigned long)maxlength, src));
607 memmove(dest, src, len);
613 Safe string cat into a string. maxlength does not
614 include the terminating zero.
616 char *safe_strcat_fn(const char *fn, int line, char *dest, const char *src, size_t maxlength)
618 size_t src_len, dest_len;
621 DEBUG(0,("ERROR: NULL dest in safe_strcat, called from [%s][%d]\n", fn, line));
628 src_len = strnlen(src, maxlength + 1);
629 dest_len = strnlen(dest, maxlength + 1);
632 clobber_region(fn, line, dest + dest_len, maxlength + 1 - dest_len);
635 if (src_len + dest_len > maxlength) {
636 DEBUG(0,("ERROR: string overflow by %d in safe_strcat [%.50s]\n",
637 (int)(src_len + dest_len - maxlength), src));
638 if (maxlength > dest_len) {
639 memcpy(&dest[dest_len], src, maxlength - dest_len);
645 memcpy(&dest[dest_len], src, src_len);
646 dest[dest_len + src_len] = 0;
651 Paranoid strcpy into a buffer of given length (includes terminating
652 zero. Strips out all but 'a-Z0-9' and the character in other_safe_chars
653 and replaces with '_'. Deliberately does *NOT* check for multibyte
654 characters. Don't change it !
656 char *alpha_strcpy_fn(const char *fn, int line, char *dest, const char *src, const char *other_safe_chars, size_t maxlength)
661 clobber_region(fn, line, dest, maxlength);
665 DEBUG(0,("ERROR: NULL dest in alpha_strcpy, called from [%s][%d]\n", fn, line));
675 if (len >= maxlength)
678 if (!other_safe_chars)
679 other_safe_chars = "";
681 for(i = 0; i < len; i++) {
682 int val = (src[i] & 0xff);
683 if (isupper(val) || islower(val) || isdigit(val) || strchr_m(other_safe_chars, val))
695 Like strncpy but always null terminates. Make sure there is room!
696 The variable n should always be one less than the available size.
698 char *StrnCpy_fn(const char *fn, int line,char *dest,const char *src,size_t n)
703 clobber_region(fn, line, dest, n+1);
707 DEBUG(0,("ERROR: NULL dest in StrnCpy, called from [%s][%d]\n", fn, line));
716 while (n-- && (*d = *src)) {
727 Like strncpy but copies up to the character marker. always null terminates.
728 returns a pointer to the character marker in the source string (src).
731 static char *strncpyn(char *dest, const char *src, size_t n, char c)
737 clobber_region(dest, n+1);
739 p = strchr_m(src, c);
741 DEBUG(5, ("strncpyn: separator character (%c) not found\n", c));
745 str_len = PTR_DIFF(p, src);
746 strncpy(dest, src, MIN(n, str_len));
747 dest[str_len] = '\0';
754 Routine to get hex characters and turn them into a 16 byte array.
755 the array can be variable length, and any non-hex-numeric
756 characters are skipped. "0xnn" or "0Xnn" is specially catered
759 valid examples: "0A5D15"; "0x15, 0x49, 0xa2"; "59\ta9\te3\n"
763 size_t strhex_to_str(char *p, size_t len, const char *strhex)
766 size_t num_chars = 0;
767 unsigned char lonybble, hinybble;
768 const char *hexchars = "0123456789ABCDEF";
769 char *p1 = NULL, *p2 = NULL;
771 for (i = 0; i < len && strhex[i] != 0; i++) {
772 if (strnequal(hexchars, "0x", 2)) {
773 i++; /* skip two chars */
777 if (!(p1 = strchr_m(hexchars, toupper(strhex[i]))))
780 i++; /* next hex digit */
782 if (!(p2 = strchr_m(hexchars, toupper(strhex[i]))))
785 /* get the two nybbles */
786 hinybble = PTR_DIFF(p1, hexchars);
787 lonybble = PTR_DIFF(p2, hexchars);
789 p[num_chars] = (hinybble << 4) | lonybble;
798 DATA_BLOB strhex_to_data_blob(const char *strhex)
800 DATA_BLOB ret_blob = data_blob(NULL, strlen(strhex)/2+1);
802 ret_blob.length = strhex_to_str(ret_blob.data,
810 * Routine to print a buffer as HEX digits, into an allocated string.
813 void hex_encode(const unsigned char *buff_in, size_t len, char **out_hex_buffer)
818 *out_hex_buffer = smb_xmalloc((len*2)+1);
819 hex_buffer = *out_hex_buffer;
821 for (i = 0; i < len; i++)
822 slprintf(&hex_buffer[i*2], 3, "%02X", buff_in[i]);
826 Check if a string is part of a list.
829 BOOL in_list(char *s,char *list,BOOL casesensitive)
837 while (next_token(&p,tok,LIST_SEP,sizeof(tok))) {
839 if (strcmp(tok,s) == 0)
842 if (StrCaseCmp(tok,s) == 0)
849 /* this is used to prevent lots of mallocs of size 1 */
850 static char *null_string = NULL;
853 Set a string value, allocing the space for the string
856 static BOOL string_init(char **dest,const char *src)
866 if((null_string = (char *)malloc(1)) == NULL) {
867 DEBUG(0,("string_init: malloc fail for null_string.\n"));
874 (*dest) = strdup(src);
875 if ((*dest) == NULL) {
876 DEBUG(0,("Out of memory in string_init\n"));
887 void string_free(char **s)
891 if (*s == null_string)
897 Set a string value, deallocating any existing space, and allocing the space
901 BOOL string_set(char **dest,const char *src)
904 return(string_init(dest,src));
908 Substitute a string for a pattern in another string. Make sure there is
911 This routine looks for pattern in s and replaces it with
912 insert. It may do multiple replacements.
914 Any of " ; ' $ or ` in the insert string are replaced with _
915 if len==0 then the string cannot be extended. This is different from the old
916 use of len==0 which was for no length checks to be done.
919 void string_sub(char *s,const char *pattern, const char *insert, size_t len)
924 if (!insert || !pattern || !*pattern || !s)
927 ls = (ssize_t)strlen(s);
928 lp = (ssize_t)strlen(pattern);
929 li = (ssize_t)strlen(insert);
932 len = ls + 1; /* len is number of *bytes* */
934 while (lp <= ls && (p = strstr_m(s,pattern))) {
935 if (ls + (li-lp) >= len) {
936 DEBUG(0,("ERROR: string overflow by %d in string_sub(%.50s, %d)\n",
937 (int)(ls + (li-lp) - len),
942 memmove(p+li,p+lp,strlen(p+lp)+1);
965 void fstring_sub(char *s,const char *pattern,const char *insert)
967 string_sub(s, pattern, insert, sizeof(fstring));
970 void pstring_sub(char *s,const char *pattern,const char *insert)
972 string_sub(s, pattern, insert, sizeof(pstring));
976 Similar to string_sub, but it will accept only allocated strings
977 and may realloc them so pay attention at what you pass on no
978 pointers inside strings, no pstrings or const may be passed
982 char *realloc_string_sub(char *string, const char *pattern, const char *insert)
986 ssize_t ls,lp,li,ld, i;
988 if (!insert || !pattern || !*pattern || !string || !*string)
995 DEBUG(0, ("realloc_string_sub: out of memory!\n"));
998 ls = (ssize_t)strlen(s);
999 lp = (ssize_t)strlen(pattern);
1000 li = (ssize_t)strlen(insert);
1002 for (i=0;i<li;i++) {
1019 while ((p = strstr_m(s,pattern))) {
1021 int offset = PTR_DIFF(s,string);
1022 char *t = Realloc(string, ls + ld + 1);
1024 DEBUG(0, ("realloc_string_sub: out of memory!\n"));
1029 p = t + offset + (p - s);
1032 memmove(p+li,p+lp,strlen(p+lp)+1);
1043 Similar to string_sub() but allows for any character to be substituted.
1045 if len==0 then the string cannot be extended. This is different from the old
1046 use of len==0 which was for no length checks to be done.
1049 void all_string_sub(char *s,const char *pattern,const char *insert, size_t len)
1054 if (!insert || !pattern || !s)
1057 ls = (ssize_t)strlen(s);
1058 lp = (ssize_t)strlen(pattern);
1059 li = (ssize_t)strlen(insert);
1065 len = ls + 1; /* len is number of *bytes* */
1067 while (lp <= ls && (p = strstr_m(s,pattern))) {
1068 if (ls + (li-lp) >= len) {
1069 DEBUG(0,("ERROR: string overflow by %d in all_string_sub(%.50s, %d)\n",
1070 (int)(ls + (li-lp) - len),
1071 pattern, (int)len));
1075 memmove(p+li,p+lp,strlen(p+lp)+1);
1077 memcpy(p, insert, li);
1084 Similar to all_string_sub but for unicode strings.
1085 Return a new allocated unicode string.
1086 similar to string_sub() but allows for any character to be substituted.
1090 static smb_ucs2_t *all_string_sub_w(const smb_ucs2_t *s, const smb_ucs2_t *pattern,
1091 const smb_ucs2_t *insert)
1094 const smb_ucs2_t *sp;
1095 size_t lr, lp, li, lt;
1097 if (!insert || !pattern || !*pattern || !s)
1100 lt = (size_t)strlen_w(s);
1101 lp = (size_t)strlen_w(pattern);
1102 li = (size_t)strlen_w(insert);
1105 const smb_ucs2_t *st = s;
1107 while ((sp = strstr_w(st, pattern))) {
1113 r = rp = (smb_ucs2_t *)malloc((lt + 1)*(sizeof(smb_ucs2_t)));
1115 DEBUG(0, ("all_string_sub_w: out of memory!\n"));
1119 while ((sp = strstr_w(s, pattern))) {
1120 memcpy(rp, s, (sp - s));
1121 rp += ((sp - s) / sizeof(smb_ucs2_t));
1122 memcpy(rp, insert, (li * sizeof(smb_ucs2_t)));
1126 lr = ((rp - r) / sizeof(smb_ucs2_t));
1128 memcpy(rp, s, ((lt - lr) * sizeof(smb_ucs2_t)));
1136 smb_ucs2_t *all_string_sub_wa(smb_ucs2_t *s, const char *pattern,
1141 if (!insert || !pattern || !s)
1143 push_ucs2(NULL, p, pattern, sizeof(wpstring) - 1, STR_TERMINATE);
1144 push_ucs2(NULL, i, insert, sizeof(wpstring) - 1, STR_TERMINATE);
1145 return all_string_sub_w(s, p, i);
1150 Splits out the front and back at a separator.
1153 static void split_at_last_component(char *path, char *front, char sep, char *back)
1155 char *p = strrchr_m(path, sep);
1161 pstrcpy(front, path);
1175 Write an octal as a string.
1178 const char *octal_string(int i)
1180 static char ret[64];
1183 slprintf(ret, sizeof(ret)-1, "0%o", i);
1189 Truncate a string at a specified length.
1192 char *string_truncate(char *s, unsigned int length)
1194 if (s && strlen(s) > length)
1200 Strchr and strrchr_m are very hard to do on general multi-byte strings.
1201 We convert via ucs2 for now.
1204 char *strchr_m(const char *src, char c)
1211 /* this is quite a common operation, so we want it to be
1212 fast. We optimise for the ascii case, knowing that all our
1213 supported multi-byte character sets are ascii-compatible
1214 (ie. they match for the first 128 chars) */
1216 for (s = src; *s && !(((unsigned char)s[0]) & 0x80); s++) {
1224 #ifdef BROKEN_UNICODE_COMPOSE_CHARACTERS
1225 /* With compose characters we must restart from the beginning. JRA. */
1229 push_ucs2(NULL, ws, s, sizeof(ws), STR_TERMINATE);
1230 p = strchr_w(ws, UCS2_CHAR(c));
1234 pull_ucs2_pstring(s2, ws);
1235 return (char *)(s+strlen(s2));
1238 char *strrchr_m(const char *s, char c)
1240 /* this is quite a common operation, so we want it to be
1241 fast. We optimise for the ascii case, knowing that all our
1242 supported multi-byte character sets are ascii-compatible
1243 (ie. they match for the first 128 chars). Also, in Samba
1244 we only search for ascii characters in 'c' and that
1245 in all mb character sets with a compound character
1246 containing c, if 'c' is not a match at position
1247 p, then p[-1] > 0x7f. JRA. */
1250 size_t len = strlen(s);
1252 BOOL got_mb = False;
1259 /* Could be a match. Part of a multibyte ? */
1260 if ((cp > s) && (((unsigned char)cp[-1]) & 0x80)) {
1261 /* Yep - go slow :-( */
1265 /* No - we have a match ! */
1268 } while (cp-- != s);
1273 /* String contained a non-ascii char. Slow path. */
1279 push_ucs2(NULL, ws, s, sizeof(ws), STR_TERMINATE);
1280 p = strrchr_w(ws, UCS2_CHAR(c));
1284 pull_ucs2_pstring(s2, ws);
1285 return (char *)(s+strlen(s2));
1289 /***********************************************************************
1290 Return the equivalent of doing strrchr 'n' times - always going
1292 ***********************************************************************/
1294 char *strnrchr_m(const char *s, char c, unsigned int n)
1300 push_ucs2(NULL, ws, s, sizeof(ws), STR_TERMINATE);
1301 p = strnrchr_w(ws, UCS2_CHAR(c), n);
1305 pull_ucs2_pstring(s2, ws);
1306 return (char *)(s+strlen(s2));
1309 /***********************************************************************
1310 strstr_m - We convert via ucs2 for now.
1311 ***********************************************************************/
1313 char *strstr_m(const char *src, const char *findstr)
1316 smb_ucs2_t *src_w, *find_w;
1321 size_t findstr_len = 0;
1323 /* for correctness */
1328 /* Samba does single character findstr calls a *lot*. */
1329 if (findstr[1] == '\0')
1330 return strchr_m(src, *findstr);
1332 /* We optimise for the ascii case, knowing that all our
1333 supported multi-byte character sets are ascii-compatible
1334 (ie. they match for the first 128 chars) */
1336 for (s = src; *s && !(((unsigned char)s[0]) & 0x80); s++) {
1337 if (*s == *findstr) {
1339 findstr_len = strlen(findstr);
1341 if (strncmp(s, findstr, findstr_len) == 0) {
1350 #if 1 /* def BROKEN_UNICODE_COMPOSE_CHARACTERS */
1351 /* 'make check' fails unless we do this */
1353 /* With compose characters we must restart from the beginning. JRA. */
1357 if (push_ucs2_allocate(&src_w, src) == (size_t)-1) {
1358 DEBUG(0,("strstr_m: src malloc fail\n"));
1362 if (push_ucs2_allocate(&find_w, findstr) == (size_t)-1) {
1364 DEBUG(0,("strstr_m: find malloc fail\n"));
1368 p = strstr_w(src_w, find_w);
1377 if (pull_ucs2_allocate(&s2, src_w) == (size_t)-1) {
1380 DEBUG(0,("strstr_m: dest malloc fail\n"));
1383 retp = (char *)(s+strlen(s2));
1391 Convert a string to lower case.
1394 void strlower_m(char *s)
1399 /* this is quite a common operation, so we want it to be
1400 fast. We optimise for the ascii case, knowing that all our
1401 supported multi-byte character sets are ascii-compatible
1402 (ie. they match for the first 128 chars) */
1404 while (*s && !(((unsigned char)s[0]) & 0x80)) {
1405 *s = tolower((unsigned char)*s);
1412 /* I assume that lowercased string takes the same number of bytes
1413 * as source string even in UTF-8 encoding. (VIV) */
1414 len = strlen(s) + 1;
1417 unix_strlower(s,len,s,len);
1418 /* Catch mb conversion errors that may not terminate. */
1425 Convert a string to upper case.
1428 void strupper_m(char *s)
1433 /* this is quite a common operation, so we want it to be
1434 fast. We optimise for the ascii case, knowing that all our
1435 supported multi-byte character sets are ascii-compatible
1436 (ie. they match for the first 128 chars) */
1438 while (*s && !(((unsigned char)s[0]) & 0x80)) {
1439 *s = toupper((unsigned char)*s);
1446 /* I assume that lowercased string takes the same number of bytes
1447 * as source string even in multibyte encoding. (VIV) */
1448 len = strlen(s) + 1;
1451 unix_strupper(s,len,s,len);
1452 /* Catch mb conversion errors that may not terminate. */
1459 Return a RFC2254 binary string representation of a buffer.
1460 Used in LDAP filters.
1464 char *binary_string(char *buf, int len)
1468 const char *hex = "0123456789ABCDEF";
1469 s = malloc(len * 3 + 1);
1472 for (j=i=0;i<len;i++) {
1474 s[j+1] = hex[((unsigned char)buf[i]) >> 4];
1475 s[j+2] = hex[((unsigned char)buf[i]) & 0xF];
1483 Just a typesafety wrapper for snprintf into a pstring.
1486 int pstr_sprintf(pstring s, const char *fmt, ...)
1492 ret = vsnprintf(s, PSTRING_LEN, fmt, ap);
1499 Just a typesafety wrapper for snprintf into a fstring.
1502 int fstr_sprintf(fstring s, const char *fmt, ...)
1508 ret = vsnprintf(s, FSTRING_LEN, fmt, ap);
1514 #if !defined(HAVE_STRNDUP) || defined(BROKEN_STRNDUP)
1516 Some platforms don't have strndup.
1519 char *strndup(const char *s, size_t n)
1534 #if !defined(HAVE_STRNLEN) || defined(BROKEN_STRNLEN)
1536 Some platforms don't have strnlen
1539 size_t strnlen(const char *s, size_t n)
1542 for (i=0; s[i] && i<n; i++)
1549 List of Strings manipulation functions
1552 #define S_LIST_ABS 16 /* List Allocation Block Size */
1554 char **str_list_make(const char *string, const char *sep)
1556 char **list, **rlist;
1562 if (!string || !*string)
1566 DEBUG(0,("str_list_make: Unable to allocate memory"));
1569 if (!sep) sep = LIST_SEP;
1575 while (next_token(&str, tok, sep, sizeof(tok))) {
1577 lsize += S_LIST_ABS;
1578 rlist = (char **)Realloc(list, ((sizeof(char **)) * (lsize +1)));
1580 DEBUG(0,("str_list_make: Unable to allocate memory"));
1581 str_list_free(&list);
1586 memset (&list[num], 0, ((sizeof(char**)) * (S_LIST_ABS +1)));
1589 list[num] = strdup(tok);
1591 DEBUG(0,("str_list_make: Unable to allocate memory"));
1592 str_list_free(&list);
1604 BOOL str_list_copy(char ***dest, const char **src)
1606 char **list, **rlist;
1618 lsize += S_LIST_ABS;
1619 rlist = (char **)Realloc(list, ((sizeof(char **)) * (lsize +1)));
1621 DEBUG(0,("str_list_copy: Unable to re-allocate memory"));
1622 str_list_free(&list);
1626 memset (&list[num], 0, ((sizeof(char **)) * (S_LIST_ABS +1)));
1629 list[num] = strdup(src[num]);
1631 DEBUG(0,("str_list_copy: Unable to allocate memory"));
1632 str_list_free(&list);
1644 * Return true if all the elements of the list match exactly.
1646 BOOL str_list_compare(char **list1, char **list2)
1650 if (!list1 || !list2)
1651 return (list1 == list2);
1653 for (num = 0; list1[num]; num++) {
1656 if (!strcsequal(list1[num], list2[num]))
1660 return False; /* if list2 has more elements than list1 fail */
1665 void str_list_free(char ***list)
1669 if (!list || !*list)
1672 for(; *tlist; tlist++)
1677 /******************************************************************************
1678 version of standard_sub_basic() for string lists; uses alloc_sub_basic()
1680 *****************************************************************************/
1682 BOOL str_list_sub_basic( char **list, const char *smb_name )
1688 tmpstr = alloc_sub_basic(smb_name, s);
1690 DEBUG(0,("str_list_sub_basic: alloc_sub_basic() return NULL!\n"));
1703 /******************************************************************************
1704 substritute a specific pattern in a string list
1705 *****************************************************************************/
1707 BOOL str_list_substitute(char **list, const char *pattern, const char *insert)
1710 ssize_t ls, lp, li, ld, i, d;
1719 lp = (ssize_t)strlen(pattern);
1720 li = (ssize_t)strlen(insert);
1725 ls = (ssize_t)strlen(s);
1727 while ((p = strstr_m(s, pattern))) {
1731 t = (char *) malloc(ls +ld +1);
1733 DEBUG(0,("str_list_substitute: Unable to allocate memory"));
1736 memcpy(t, *list, d);
1737 memcpy(t +d +li, p +lp, ls -d -lp +1);
1744 for (i = 0; i < li; i++) {
1745 switch (insert[i]) {
1757 t[d +i] = insert[i];
1770 #define IPSTR_LIST_SEP ","
1771 #define IPSTR_LIST_CHAR ','
1774 * Add ip string representation to ipstr list. Used also
1775 * as part of @function ipstr_list_make
1777 * @param ipstr_list pointer to string containing ip list;
1778 * MUST BE already allocated and IS reallocated if necessary
1779 * @param ipstr_size pointer to current size of ipstr_list (might be changed
1780 * as a result of reallocation)
1781 * @param ip IP address which is to be added to list
1782 * @return pointer to string appended with new ip and possibly
1783 * reallocated to new length
1786 char* ipstr_list_add(char** ipstr_list, const struct ip_service *service)
1788 char* new_ipstr = NULL;
1790 /* arguments checking */
1791 if (!ipstr_list || !service) return NULL;
1793 /* attempt to convert ip to a string and append colon separator to it */
1795 asprintf(&new_ipstr, "%s%s%s:%d", *ipstr_list, IPSTR_LIST_SEP,
1796 inet_ntoa(service->ip), service->port);
1797 SAFE_FREE(*ipstr_list);
1799 asprintf(&new_ipstr, "%s:%d", inet_ntoa(service->ip), service->port);
1801 *ipstr_list = new_ipstr;
1807 * Allocate and initialise an ipstr list using ip adresses
1808 * passed as arguments.
1810 * @param ipstr_list pointer to string meant to be allocated and set
1811 * @param ip_list array of ip addresses to place in the list
1812 * @param ip_count number of addresses stored in ip_list
1813 * @return pointer to allocated ip string
1816 char* ipstr_list_make(char** ipstr_list, const struct ip_service* ip_list, int ip_count)
1820 /* arguments checking */
1821 if (!ip_list && !ipstr_list) return 0;
1825 /* process ip addresses given as arguments */
1826 for (i = 0; i < ip_count; i++)
1827 *ipstr_list = ipstr_list_add(ipstr_list, &ip_list[i]);
1829 return (*ipstr_list);
1834 * Parse given ip string list into array of ip addresses
1835 * (as ip_service structures)
1836 * e.g. 192.168.1.100:389,192.168.1.78, ...
1838 * @param ipstr ip string list to be parsed
1839 * @param ip_list pointer to array of ip addresses which is
1840 * allocated by this function and must be freed by caller
1841 * @return number of succesfully parsed addresses
1844 int ipstr_list_parse(const char* ipstr_list, struct ip_service **ip_list)
1850 if (!ipstr_list || !ip_list)
1853 count = count_chars(ipstr_list, IPSTR_LIST_CHAR) + 1;
1854 if ( (*ip_list = (struct ip_service*)malloc(count * sizeof(struct ip_service))) == NULL ) {
1855 DEBUG(0,("ipstr_list_parse: malloc failed for %lu entries\n", (unsigned long)count));
1860 next_token(&ipstr_list, token_str, IPSTR_LIST_SEP, FSTRING_LEN) && i<count;
1863 struct in_addr addr;
1865 char *p = strchr(token_str, ':');
1872 /* convert single token to ip address */
1873 if ( (addr.s_addr = inet_addr(token_str)) == INADDR_NONE )
1876 (*ip_list)[i].ip = addr;
1877 (*ip_list)[i].port = port;
1885 * Safely free ip string list
1887 * @param ipstr_list ip string list to be freed
1890 void ipstr_list_free(char* ipstr_list)
1892 SAFE_FREE(ipstr_list);
1897 Unescape a URL encoded string, in place.
1900 void rfc1738_unescape(char *buf)
1904 while (p && *p && (p=strchr_m(p,'%'))) {
1908 if (c1 >= '0' && c1 <= '9')
1910 else if (c1 >= 'A' && c1 <= 'F')
1912 else if (c1 >= 'a' && c1 <= 'f')
1914 else {p++; continue;}
1916 if (c2 >= '0' && c2 <= '9')
1918 else if (c2 >= 'A' && c2 <= 'F')
1920 else if (c2 >= 'a' && c2 <= 'f')
1922 else {p++; continue;}
1926 memmove(p+1, p+3, strlen(p+3)+1);
1931 static const char *b64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
1934 * Decode a base64 string into a DATA_BLOB - simple and slow algorithm
1936 DATA_BLOB base64_decode_data_blob(const char *s)
1938 int bit_offset, byte_offset, idx, i, n;
1939 DATA_BLOB decoded = data_blob(s, strlen(s)+1);
1940 unsigned char *d = decoded.data;
1945 while (*s && (p=strchr_m(b64,*s))) {
1946 idx = (int)(p - b64);
1947 byte_offset = (i*6)/8;
1948 bit_offset = (i*6)%8;
1949 d[byte_offset] &= ~((1<<(8-bit_offset))-1);
1950 if (bit_offset < 3) {
1951 d[byte_offset] |= (idx << (2-bit_offset));
1954 d[byte_offset] |= (idx >> (bit_offset-2));
1955 d[byte_offset+1] = 0;
1956 d[byte_offset+1] |= (idx << (8-(bit_offset-2))) & 0xFF;
1962 if ((n > 0) && (*s == '=')) {
1972 * Decode a base64 string in-place - wrapper for the above
1974 void base64_decode_inplace(char *s)
1976 DATA_BLOB decoded = base64_decode_data_blob(s);
1978 if ( decoded.length != 0 ) {
1979 memcpy(s, decoded.data, decoded.length);
1981 /* null terminate */
1982 s[decoded.length] = '\0';
1987 data_blob_free(&decoded);
1991 * Encode a base64 string into a malloc()ed string caller to free.
1993 *From SQUID: adopted from http://ftp.sunet.se/pub2/gnu/vm/base64-encode.c with adjustments
1995 char * base64_encode_data_blob(DATA_BLOB data)
2000 size_t len = data.length;
2001 size_t output_len = data.length * 2;
2002 char *result = malloc(output_len); /* get us plenty of space */
2004 while (len-- && out_cnt < (data.length * 2) - 5) {
2005 int c = (unsigned char) *(data.data++);
2008 if (char_count == 3) {
2009 result[out_cnt++] = b64[bits >> 18];
2010 result[out_cnt++] = b64[(bits >> 12) & 0x3f];
2011 result[out_cnt++] = b64[(bits >> 6) & 0x3f];
2012 result[out_cnt++] = b64[bits & 0x3f];
2019 if (char_count != 0) {
2020 bits <<= 16 - (8 * char_count);
2021 result[out_cnt++] = b64[bits >> 18];
2022 result[out_cnt++] = b64[(bits >> 12) & 0x3f];
2023 if (char_count == 1) {
2024 result[out_cnt++] = '=';
2025 result[out_cnt++] = '=';
2027 result[out_cnt++] = b64[(bits >> 6) & 0x3f];
2028 result[out_cnt++] = '=';
2031 result[out_cnt] = '\0'; /* terminate */
2035 /* read a SMB_BIG_UINT from a string */
2036 SMB_BIG_UINT STR_TO_SMB_BIG_UINT(const char *nptr, const char **entptr)
2039 SMB_BIG_UINT val = -1;
2040 const char *p = nptr;
2042 while (p && *p && isspace(*p))
2044 #ifdef LARGE_SMB_OFF_T
2045 sscanf(p,"%llu",&val);
2046 #else /* LARGE_SMB_OFF_T */
2047 sscanf(p,"%lu",&val);
2048 #endif /* LARGE_SMB_OFF_T */
2050 while (p && *p && isdigit(*p))
2058 void string_append(char **left, const char *right)
2060 int new_len = strlen(right) + 1;
2062 if (*left == NULL) {
2063 *left = malloc(new_len);
2066 new_len += strlen(*left);
2067 *left = Realloc(*left, new_len);
2073 safe_strcat(*left, right, new_len-1);