2 Unix SMB/Netbios implementation.
4 Samba utility functions
5 Copyright (C) Andrew Tridgell 1992-2001
6 Copyright (C) Simo Sorce 2001-2002
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
25 /****************************************************************************
26 Get the next token from a string, return False if none found
27 handles double-quotes.
28 Based on a routine by GJC@VILLAGE.COM.
29 Extensively modified by Andrew.Tridgell@anu.edu.au
30 ****************************************************************************/
31 BOOL next_token(char **ptr,char *buff,char *sep, size_t bufsize)
37 if (!ptr) return(False);
41 /* default to simple separators */
42 if (!sep) sep = " \t\n\r";
44 /* find the first non sep char */
45 while (*s && strchr_m(sep,*s)) s++;
48 if (! *s) return(False);
50 /* copy over the token */
51 for (quoted = False; len < bufsize && *s && (quoted || !strchr_m(sep,*s)); s++) {
60 *ptr = (*s) ? s+1 : s;
68 /****************************************************************************
69 This is like next_token but is not re-entrant and "remembers" the first
70 parameter so you can pass NULL. This is useful for user interface code
71 but beware the fact that it is not re-entrant!
72 ****************************************************************************/
73 static char *last_ptr=NULL;
75 BOOL next_token_nr(char **ptr,char *buff,char *sep, size_t bufsize)
78 if (!ptr) ptr = &last_ptr;
80 ret = next_token(ptr, buff, sep, bufsize);
85 static uint16 tmpbuf[sizeof(pstring)];
87 void set_first_token(char *ptr)
93 /****************************************************************************
94 Convert list of tokens to array; dependent on above routine.
95 Uses last_ptr from above - bit of a hack.
96 ****************************************************************************/
97 char **toktocliplist(int *ctok, char *sep)
103 if (!sep) sep = " \t\n\r";
105 while(*s && strchr_m(sep,*s)) s++;
108 if (!*s) return(NULL);
112 while(*s && (!strchr_m(sep,*s))) s++;
113 while(*s && strchr_m(sep,*s)) *s++=0;
119 if (!(ret=iret=malloc(ictok*sizeof(char *)))) return NULL;
130 /*******************************************************************
131 case insensitive string compararison
132 ********************************************************************/
133 int StrCaseCmp(const char *s, const char *t)
136 unix_strupper(s, strlen(s)+1, buf1, sizeof(buf1));
137 unix_strupper(t, strlen(t)+1, buf2, sizeof(buf2));
138 return strcmp(buf1,buf2);
141 /*******************************************************************
142 case insensitive string compararison, length limited
143 ********************************************************************/
144 int StrnCaseCmp(const char *s, const char *t, size_t n)
147 unix_strupper(s, strlen(s)+1, buf1, sizeof(buf1));
148 unix_strupper(t, strlen(t)+1, buf2, sizeof(buf2));
149 return strncmp(buf1,buf2,n);
152 /*******************************************************************
154 ********************************************************************/
155 BOOL strequal(const char *s1, const char *s2)
157 if (s1 == s2) return(True);
158 if (!s1 || !s2) return(False);
160 return(StrCaseCmp(s1,s2)==0);
163 /*******************************************************************
164 compare 2 strings up to and including the nth char.
165 ******************************************************************/
166 BOOL strnequal(const char *s1,const char *s2,size_t n)
168 if (s1 == s2) return(True);
169 if (!s1 || !s2 || !n) return(False);
171 return(StrnCaseCmp(s1,s2,n)==0);
174 /*******************************************************************
175 compare 2 strings (case sensitive)
176 ********************************************************************/
177 BOOL strcsequal(const char *s1,const char *s2)
179 if (s1 == s2) return(True);
180 if (!s1 || !s2) return(False);
182 return(strcmp(s1,s2)==0);
185 /***************************************************************************
186 Do a case-insensitive, whitespace-ignoring string compare.
187 ***************************************************************************/
188 int strwicmp(const char *psz1, const char *psz2)
190 /* if BOTH strings are NULL, return TRUE, if ONE is NULL return */
191 /* appropriate value. */
194 else if (psz1 == NULL)
196 else if (psz2 == NULL)
199 /* sync the strings on first non-whitespace */
202 while (isspace((int)*psz1))
204 while (isspace((int)*psz2))
206 if (toupper(*psz1) != toupper(*psz2) || *psz1 == '\0'
212 return (*psz1 - *psz2);
216 /*******************************************************************
217 convert a string to "normal" form
218 ********************************************************************/
219 void strnorm(char *s)
221 extern int case_default;
222 if (case_default == CASE_UPPER)
228 /*******************************************************************
229 check if a string is in "normal" case
230 ********************************************************************/
231 BOOL strisnormal(char *s)
233 extern int case_default;
234 if (case_default == CASE_UPPER)
235 return(!strhaslower(s));
237 return(!strhasupper(s));
241 /****************************************************************************
243 NOTE: oldc and newc must be 7 bit characters
244 ****************************************************************************/
245 void string_replace(char *s,char oldc,char newc)
247 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
248 string_replace_w(tmpbuf, UCS2_CHAR(oldc), UCS2_CHAR(newc));
249 pull_ucs2(NULL, s, tmpbuf, -1, sizeof(tmpbuf), STR_TERMINATE);
253 /*******************************************************************
254 skip past some strings in a buffer
255 ********************************************************************/
256 char *skip_string(char *buf,size_t n)
259 buf += strlen(buf) + 1;
263 /*******************************************************************
264 Count the number of characters in a string. Normally this will
265 be the same as the number of bytes in a string for single byte strings,
266 but will be different for multibyte.
267 ********************************************************************/
268 size_t str_charnum(const char *s)
270 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
271 return strlen_w(tmpbuf);
274 /*******************************************************************
275 trim the specified elements off the front and back of a string
276 ********************************************************************/
278 BOOL trim_string(char *s,const char *front,const char *back)
285 /* Ignore null or empty strings. */
286 if (!s || (s[0] == '\0'))
289 front_len = front? strlen(front) : 0;
290 back_len = back? strlen(back) : 0;
295 while (len && strncmp(s, front, front_len)==0) {
296 memcpy(s, s+front_len, (len-front_len)+1);
303 while (strncmp(s+len-back_len,back,back_len)==0) {
304 s[len-back_len]='\0';
313 /****************************************************************************
314 does a string have any uppercase chars in it?
315 ****************************************************************************/
316 BOOL strhasupper(const char *s)
319 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
320 for(ptr=tmpbuf;*ptr;ptr++)
321 if(isupper_w(*ptr)) return True;
325 /****************************************************************************
326 does a string have any lowercase chars in it?
327 ****************************************************************************/
328 BOOL strhaslower(const char *s)
331 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
332 for(ptr=tmpbuf;*ptr;ptr++)
333 if(islower_w(*ptr)) return True;
337 /****************************************************************************
338 find the number of 'c' chars in a string
339 ****************************************************************************/
340 size_t count_chars(const char *s,char c)
344 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
345 for(count=0,ptr=tmpbuf;*ptr;ptr++) if(*ptr==UCS2_CHAR(c)) count++;
349 /*******************************************************************
350 Return True if a string consists only of one particular character.
351 ********************************************************************/
353 BOOL str_is_all(const char *s,char c)
357 if(s == NULL) return False;
358 if(!*s) return False;
360 push_ucs2(NULL, tmpbuf,s, sizeof(tmpbuf), STR_TERMINATE);
361 for(ptr=tmpbuf;*ptr;ptr++) if(*ptr!=UCS2_CHAR(c)) return False;
366 /*******************************************************************
367 safe string copy into a known length string. maxlength does not
368 include the terminating zero.
369 ********************************************************************/
371 char *safe_strcpy(char *dest,const char *src, size_t maxlength)
376 DEBUG(0,("ERROR: NULL dest in safe_strcpy\n"));
387 if (len > maxlength) {
388 DEBUG(0,("ERROR: string overflow by %d in safe_strcpy [%.50s]\n",
389 (int)(len-maxlength), src));
393 memmove(dest, src, len);
398 /*******************************************************************
399 safe string cat into a string. maxlength does not
400 include the terminating zero.
401 ********************************************************************/
403 char *safe_strcat(char *dest, const char *src, size_t maxlength)
405 size_t src_len, dest_len;
408 DEBUG(0,("ERROR: NULL dest in safe_strcat\n"));
416 src_len = strlen(src);
417 dest_len = strlen(dest);
419 if (src_len + dest_len > maxlength) {
420 DEBUG(0,("ERROR: string overflow by %d in safe_strcat [%.50s]\n",
421 (int)(src_len + dest_len - maxlength), src));
422 src_len = maxlength - dest_len;
425 memcpy(&dest[dest_len], src, src_len);
426 dest[dest_len + src_len] = 0;
430 /*******************************************************************
431 Paranoid strcpy into a buffer of given length (includes terminating
432 zero. Strips out all but 'a-Z0-9' and the character in other_safe_chars
433 and replaces with '_'. Deliberately does *NOT* check for multibyte
434 characters. Don't change it !
435 ********************************************************************/
437 char *alpha_strcpy(char *dest, const char *src, const char *other_safe_chars, size_t maxlength)
442 DEBUG(0,("ERROR: NULL dest in alpha_strcpy\n"));
452 if (len >= maxlength)
455 if (!other_safe_chars)
456 other_safe_chars = "";
458 for(i = 0; i < len; i++) {
459 int val = (src[i] & 0xff);
460 if(isupper(val) || islower(val) || isdigit(val) || strchr_m(other_safe_chars, val))
471 /****************************************************************************
472 Like strncpy but always null terminates. Make sure there is room!
473 The variable n should always be one less than the available size.
474 ****************************************************************************/
476 char *StrnCpy(char *dest,const char *src,size_t n)
479 if (!dest) return(NULL);
484 while (n-- && (*d++ = *src++)) ;
489 /****************************************************************************
490 like strncpy but copies up to the character marker. always null terminates.
491 returns a pointer to the character marker in the source string (src).
492 ****************************************************************************/
493 char *strncpyn(char *dest, const char *src,size_t n, char c)
498 p = strchr_m(src, c);
501 DEBUG(5, ("strncpyn: separator character (%c) not found\n", c));
505 str_len = PTR_DIFF(p, src);
506 strncpy(dest, src, MIN(n, str_len));
507 dest[str_len] = '\0';
513 /*************************************************************
514 Routine to get hex characters and turn them into a 16 byte array.
515 the array can be variable length, and any non-hex-numeric
516 characters are skipped. "0xnn" or "0Xnn" is specially catered
519 valid examples: "0A5D15"; "0x15, 0x49, 0xa2"; "59\ta9\te3\n"
521 **************************************************************/
522 size_t strhex_to_str(char *p, size_t len, const char *strhex)
525 size_t num_chars = 0;
526 unsigned char lonybble, hinybble;
527 char *hexchars = "0123456789ABCDEF";
528 char *p1 = NULL, *p2 = NULL;
530 for (i = 0; i < len && strhex[i] != 0; i++)
532 if (strnequal(hexchars, "0x", 2))
534 i++; /* skip two chars */
538 if (!(p1 = strchr_m(hexchars, toupper(strhex[i]))))
543 i++; /* next hex digit */
545 if (!(p2 = strchr_m(hexchars, toupper(strhex[i]))))
550 /* get the two nybbles */
551 hinybble = PTR_DIFF(p1, hexchars);
552 lonybble = PTR_DIFF(p2, hexchars);
554 p[num_chars] = (hinybble << 4) | lonybble;
563 /****************************************************************************
564 check if a string is part of a list
565 ****************************************************************************/
566 BOOL in_list(char *s,char *list,BOOL casesensitive)
571 if (!list) return(False);
573 while (next_token(&p,tok,LIST_SEP,sizeof(tok))) {
575 if (strcmp(tok,s) == 0)
578 if (StrCaseCmp(tok,s) == 0)
585 /* this is used to prevent lots of mallocs of size 1 */
586 static char *null_string = NULL;
588 /****************************************************************************
589 set a string value, allocing the space for the string
590 ****************************************************************************/
591 static BOOL string_init(char **dest,const char *src)
602 if((null_string = (char *)malloc(1)) == NULL) {
603 DEBUG(0,("string_init: malloc fail for null_string.\n"));
612 (*dest) = (char *)malloc(l+1);
613 if ((*dest) == NULL) {
614 DEBUG(0,("Out of memory in string_init\n"));
623 /****************************************************************************
625 ****************************************************************************/
626 void string_free(char **s)
628 if (!s || !(*s)) return;
629 if (*s == null_string)
634 /****************************************************************************
635 set a string value, allocing the space for the string, and deallocating any
637 ****************************************************************************/
638 BOOL string_set(char **dest,const char *src)
642 return(string_init(dest,src));
646 /****************************************************************************
647 substitute a string for a pattern in another string. Make sure there is
650 This routine looks for pattern in s and replaces it with
651 insert. It may do multiple replacements.
653 any of " ; ' $ or ` in the insert string are replaced with _
654 if len==0 then no length check is performed
655 ****************************************************************************/
656 void string_sub(char *s,const char *pattern,const char *insert, size_t len)
661 if (!insert || !pattern || !s) return;
663 ls = (ssize_t)strlen(s);
664 lp = (ssize_t)strlen(pattern);
665 li = (ssize_t)strlen(insert);
667 if (!*pattern) return;
669 while (lp <= ls && (p = strstr(s,pattern))) {
670 if (len && (ls + (li-lp) >= len)) {
671 DEBUG(0,("ERROR: string overflow by %d in string_sub(%.50s, %d)\n",
672 (int)(ls + (li-lp) - len),
677 memmove(p+li,p+lp,strlen(p+lp)+1);
700 void fstring_sub(char *s,const char *pattern,const char *insert)
702 string_sub(s, pattern, insert, sizeof(fstring));
705 void pstring_sub(char *s,const char *pattern,const char *insert)
707 string_sub(s, pattern, insert, sizeof(pstring));
710 /****************************************************************************
711 similar to string_sub() but allows for any character to be substituted.
713 if len==0 then no length check is performed
714 ****************************************************************************/
715 void all_string_sub(char *s,const char *pattern,const char *insert, size_t len)
720 if (!insert || !pattern || !s) return;
722 ls = (ssize_t)strlen(s);
723 lp = (ssize_t)strlen(pattern);
724 li = (ssize_t)strlen(insert);
726 if (!*pattern) return;
728 while (lp <= ls && (p = strstr(s,pattern))) {
729 if (len && (ls + (li-lp) >= len)) {
730 DEBUG(0,("ERROR: string overflow by %d in all_string_sub(%.50s, %d)\n",
731 (int)(ls + (li-lp) - len),
736 memmove(p+li,p+lp,strlen(p+lp)+1);
738 memcpy(p, insert, li);
744 /****************************************************************************
745 similar to all_string_sub but for unicode strings.
746 return a new allocate unicode string.
747 len is the number of bytes, not chars
748 similar to string_sub() but allows for any character to be substituted.
750 if len==0 then no length check is performed
751 ****************************************************************************/
753 smb_ucs2_t *all_string_sub_w(const smb_ucs2_t *s, const smb_ucs2_t *pattern,
754 const smb_ucs2_t *insert)
756 smb_ucs2_t *r, *rp, *sp;
757 size_t lr, lp, li, lt;
759 if (!insert || !pattern || !*pattern || !s) return NULL;
761 lt = (size_t)strlen_w(s);
762 lp = (size_t)strlen_w(pattern);
763 li = (size_t)strlen_w(insert);
768 while ((sp = strstr_w(st, pattern))) {
774 r = rp = (smb_ucs2_t *)malloc((lt + 1)*(sizeof(smb_ucs2_t)));
776 DEBUG(0, ("all_string_sub_w: out of memory!\n"));
780 while ((sp = strstr_w(s, pattern))) {
781 memcpy(rp, s, (sp - s));
782 rp += ((sp - s) / sizeof(smb_ucs2_t));
783 memcpy(rp, insert, (li * sizeof(smb_ucs2_t)));
787 lr = ((rp - r) / sizeof(smb_ucs2_t));
789 memcpy(rp, s, ((lt - lr) * sizeof(smb_ucs2_t)));
797 smb_ucs2_t *all_string_sub_wa(smb_ucs2_t *s, const char *pattern,
802 if (!insert || !pattern || !s) return NULL;
803 push_ucs2(NULL, p, pattern, sizeof(wpstring) - 1, STR_TERMINATE);
804 push_ucs2(NULL, i, insert, sizeof(wpstring) - 1, STR_TERMINATE);
805 return all_string_sub_w(s, p, i);
808 /****************************************************************************
809 splits out the front and back at a separator.
810 ****************************************************************************/
811 void split_at_last_component(char *path, char *front, char sep, char *back)
813 char *p = strrchr_m(path, sep);
821 pstrcpy(front, path);
841 /****************************************************************************
842 write an octal as a string
843 ****************************************************************************/
844 char *octal_string(int i)
850 slprintf(ret, sizeof(ret)-1, "0%o", i);
855 /****************************************************************************
856 truncate a string at a specified length
857 ****************************************************************************/
858 char *string_truncate(char *s, int length)
860 if (s && strlen(s) > length) {
867 /****************************************************************************
868 strchr and strrchr_m are very hard to do on general multi-byte strings.
869 we convert via ucs2 for now
870 ****************************************************************************/
871 char *strchr_m(const char *s, char c)
877 push_ucs2(NULL, ws, s, sizeof(ws), STR_TERMINATE);
878 p = strchr_w(ws, UCS2_CHAR(c));
881 pull_ucs2_pstring(s2, ws);
882 return (char *)(s+strlen(s2));
885 char *strrchr_m(const char *s, char c)
891 push_ucs2(NULL, ws, s, sizeof(ws), STR_TERMINATE);
892 p = strrchr_w(ws, UCS2_CHAR(c));
895 pull_ucs2_pstring(s2, ws);
896 return (char *)(s+strlen(s2));
899 /*******************************************************************
900 convert a string to lower case
901 ********************************************************************/
902 void strlower_m(char *s)
904 /* I assume that lowercased string takes the same number of bytes
905 * as source string even in UTF-8 encoding. (VIV) */
906 unix_strlower(s,strlen(s)+1,s,strlen(s)+1);
909 /*******************************************************************
910 convert a string to upper case
911 ********************************************************************/
912 void strupper_m(char *s)
914 /* I assume that lowercased string takes the same number of bytes
915 * as source string even in multibyte encoding. (VIV) */
916 unix_strupper(s,strlen(s)+1,s,strlen(s)+1);
920 return a RFC2254 binary string representation of a buffer
924 char *binary_string(char *buf, int len)
928 const char *hex = "0123456789ABCDEF";
929 s = malloc(len * 3 + 1);
931 for (j=i=0;i<len;i++) {
933 s[j+1] = hex[((unsigned char)buf[i]) >> 4];
934 s[j+2] = hex[((unsigned char)buf[i]) & 0xF];
942 /* Just a typesafety wrapper for snprintf into a pstring */
943 int pstr_sprintf(pstring s, const char *fmt, ...)
949 ret = vsnprintf(s, PSTRING_LEN, fmt, ap);
955 /* Just a typesafety wrapper for snprintf into a fstring */
956 int fstr_sprintf(fstring s, const char *fmt, ...)
962 ret = vsnprintf(s, FSTRING_LEN, fmt, ap);