2 Unix SMB/Netbios implementation.
4 Samba utility functions
5 Copyright (C) Andrew Tridgell 1992-1998
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24 #if (defined(HAVE_NETGROUP) && defined (WITH_AUTOMOUNT))
25 #ifdef WITH_NISPLUS_HOME
26 #ifdef BROKEN_NISPLUS_INCLUDE_FILES
28 * The following lines are needed due to buggy include files
29 * in Solaris 2.6 which define GROUP in both /usr/include/sys/acl.h and
30 * also in /usr/include/rpcsvc/nis.h. The definitions conflict. JRA.
31 * Also GROUP_OBJ is defined as 0x4 in /usr/include/sys/acl.h and as
32 * an enum in /usr/include/rpcsvc/nis.h.
39 #if defined(GROUP_OBJ)
43 #endif /* BROKEN_NISPLUS_INCLUDE_FILES */
45 #include <rpcsvc/nis.h>
47 #else /* !WITH_NISPLUS_HOME */
49 #include "rpcsvc/ypclnt.h"
51 #endif /* WITH_NISPLUS_HOME */
52 #endif /* HAVE_NETGROUP && WITH_AUTOMOUNT */
56 #undef Realloc /* SSLeay defines this and samba has a function of this name */
61 extern int DEBUGLEVEL;
63 int Protocol = PROTOCOL_COREPLUS;
65 /* a default finfo structure to ensure all fields are sensible */
66 file_info def_finfo = {-1,0,0,0,0,0,0,""};
68 /* the client file descriptor */
71 /* this is used by the chaining code */
77 case handling on filenames
79 int case_default = CASE_LOWER;
81 /* the following control case operations - they are put here so the
82 client can link easily */
85 BOOL use_mangled_map = False;
86 BOOL short_case_preserve;
89 fstring remote_machine="";
90 fstring local_machine="";
91 fstring remote_arch="UNKNOWN";
92 static enum remote_arch_types ra_type = RA_UNKNOWN;
93 fstring remote_proto="UNKNOWN";
94 pstring user_socket_options=DEFAULT_SOCKET_OPTIONS;
96 pstring sesssetup_user="";
97 pstring samlogon_user="";
99 BOOL sam_logon_in_ssb = False;
101 pstring global_myname = "";
102 fstring global_myworkgroup = "";
103 char **my_netbios_names;
105 static char *filename_dos(char *path,char *buf);
109 /****************************************************************************
110 find a suitable temporary directory. The result should be copied immediately
111 as it may be overwritten by a subsequent call
112 ****************************************************************************/
116 if ((p = getenv("TMPDIR"))) {
122 /****************************************************************************
123 determine whether we are in the specified group
124 ****************************************************************************/
126 BOOL in_group(gid_t group, gid_t current_gid, int ngroups, gid_t *groups)
130 if (group == current_gid) return(True);
132 for (i=0;i<ngroups;i++)
133 if (group == groups[i])
140 /****************************************************************************
141 like atoi but gets the value up to the separater character
142 ****************************************************************************/
143 char *Atoic(char *p, int *n, char *c)
145 if (!isdigit((int)*p))
147 DEBUG(5, ("Atoic: malformed number\n"));
153 while ((*p) && isdigit((int)*p))
158 if (strchr(c, *p) == NULL)
160 DEBUG(5, ("Atoic: no separator characters (%s) not found\n", c));
167 /*************************************************************************
168 reads a list of numbers
169 *************************************************************************/
170 char *get_numlist(char *p, uint32 **num, int *count)
174 if (num == NULL || count == NULL)
182 while ((p = Atoic(p, &val, ":,")) != NULL && (*p) != ':')
184 (*num) = Realloc((*num), ((*count)+1) * sizeof(uint32));
189 (*num)[(*count)] = val;
197 #define TRUNCATE_NETBIOS_NAME 1
199 /*******************************************************************
200 convert, possibly using a stupid microsoft-ism which has destroyed
201 the transport independence of netbios (for CIFS vendors that usually
202 use the Win95-type methods, not for NT to NT communication, which uses
203 DCE/RPC and therefore full-length unicode strings...) a dns name into
206 the netbios name (NOT necessarily null-terminated) is truncated to 15
209 ******************************************************************/
210 char *dns_to_netbios_name(char *dns_name)
212 static char netbios_name[16];
214 StrnCpy(netbios_name, dns_name, 15);
215 netbios_name[15] = 0;
217 #ifdef TRUNCATE_NETBIOS_NAME
218 /* ok. this is because of a stupid microsoft-ism. if the called host
219 name contains a '.', microsoft clients expect you to truncate the
220 netbios name up to and including the '.' this even applies, by
221 mistake, to workgroup (domain) names, which is _really_ daft.
223 for (i = 15; i >= 0; i--)
225 if (netbios_name[i] == '.')
231 #endif /* TRUNCATE_NETBIOS_NAME */
237 /****************************************************************************
238 interpret the weird netbios "name". Return the name type
239 ****************************************************************************/
240 static int name_interpret(char *in,char *out)
243 int len = (*in++) / 2;
247 if (len > 30 || len<1) return(0);
251 if (in[0] < 'A' || in[0] > 'P' || in[1] < 'A' || in[1] > 'P') {
255 *out = ((in[0]-'A')<<4) + (in[1]-'A');
263 /* Handle any scope names */
266 *out++ = '.'; /* Scope names are separated by periods */
267 len = *(unsigned char *)in++;
268 StrnCpy(out, in, len);
277 /****************************************************************************
278 mangle a name into netbios format
280 Note: <Out> must be (33 + strlen(scope) + 2) bytes long, at minimum.
281 ****************************************************************************/
282 int name_mangle( char *In, char *Out, char name_type )
289 extern pstring global_scope;
291 /* Safely copy the input string, In, into buf[]. */
292 (void)memset( buf, 0, 20 );
293 if (strcmp(In,"*") == 0)
296 (void)slprintf( buf, sizeof(buf) - 1, "%-15.15s%c", In, name_type );
298 /* Place the length of the first field into the output buffer. */
302 /* Now convert the name to the rfc1001/1002 format. */
303 for( i = 0; i < 16; i++ )
305 c = toupper( buf[i] );
306 p[i*2] = ( (c >> 4) & 0x000F ) + 'A';
307 p[(i*2)+1] = (c & 0x000F) + 'A';
312 /* Add the scope string. */
313 for( i = 0, len = 0; NULL != global_scope; i++, len++ )
315 switch( global_scope[i] )
321 return( name_len(Out) );
328 p[len+1] = global_scope[i];
333 return( name_len(Out) );
336 /*******************************************************************
337 check if a file exists - call vfs_file_exist for samba files
338 ********************************************************************/
339 BOOL file_exist(char *fname,SMB_STRUCT_STAT *sbuf)
342 if (!sbuf) sbuf = &st;
344 if (sys_stat(fname,sbuf) != 0)
347 return(S_ISREG(sbuf->st_mode));
350 /*******************************************************************
352 ********************************************************************/
353 int file_rename(char *from, char *to)
355 int rcode = rename (from, to);
359 /* Rename across filesystems needed. */
360 rcode = copy_reg (from, to);
365 /*******************************************************************
366 check a files mod time
367 ********************************************************************/
368 time_t file_modtime(char *fname)
372 if (sys_stat(fname,&st) != 0)
378 /*******************************************************************
379 check if a directory exists
380 ********************************************************************/
381 BOOL directory_exist(char *dname,SMB_STRUCT_STAT *st)
388 if (sys_stat(dname,st) != 0)
391 ret = S_ISDIR(st->st_mode);
397 /*******************************************************************
398 returns the size in bytes of the named file
399 ********************************************************************/
400 SMB_OFF_T get_file_size(char *file_name)
404 if(sys_stat(file_name,&buf) != 0)
405 return (SMB_OFF_T)-1;
409 /*******************************************************************
410 return a string representing an attribute for a file
411 ********************************************************************/
412 char *attrib_string(uint16 mode)
414 static fstring attrstr;
418 if (mode & aVOLID) fstrcat(attrstr,"V");
419 if (mode & aDIR) fstrcat(attrstr,"D");
420 if (mode & aARCH) fstrcat(attrstr,"A");
421 if (mode & aHIDDEN) fstrcat(attrstr,"H");
422 if (mode & aSYSTEM) fstrcat(attrstr,"S");
423 if (mode & aRONLY) fstrcat(attrstr,"R");
428 /*******************************************************************
429 show a smb message structure
430 ********************************************************************/
431 void show_msg(char *buf)
436 if (DEBUGLEVEL < 5) return;
438 DEBUG(5,("size=%d\nsmb_com=0x%x\nsmb_rcls=%d\nsmb_reh=%d\nsmb_err=%d\nsmb_flg=%d\nsmb_flg2=%d\n",
440 (int)CVAL(buf,smb_com),
441 (int)CVAL(buf,smb_rcls),
442 (int)CVAL(buf,smb_reh),
443 (int)SVAL(buf,smb_err),
444 (int)CVAL(buf,smb_flg),
445 (int)SVAL(buf,smb_flg2)));
446 DEBUG(5,("smb_tid=%d\nsmb_pid=%d\nsmb_uid=%d\nsmb_mid=%d\nsmt_wct=%d\n",
447 (int)SVAL(buf,smb_tid),
448 (int)SVAL(buf,smb_pid),
449 (int)SVAL(buf,smb_uid),
450 (int)SVAL(buf,smb_mid),
451 (int)CVAL(buf,smb_wct)));
453 for (i=0;i<(int)CVAL(buf,smb_wct);i++)
455 DEBUG(5,("smb_vwv[%d]=%d (0x%X)\n",i,
456 SVAL(buf,smb_vwv+2*i),SVAL(buf,smb_vwv+2*i)));
459 bcc = (int)SVAL(buf,smb_vwv+2*(CVAL(buf,smb_wct)));
461 DEBUG(5,("smb_bcc=%d\n",bcc));
463 if (DEBUGLEVEL < 10) return;
470 dump_data(10, smb_buf(buf), bcc);
473 /*******************************************************************
474 set the length and marker of an smb packet
475 ********************************************************************/
476 void smb_setlen(char *buf,int len)
478 _smb_setlen(buf,len);
486 /*******************************************************************
487 setup the word count and byte count for a smb message
488 ********************************************************************/
489 int set_message(char *buf,int num_words,int num_bytes,BOOL zero)
492 memset(buf + smb_size,'\0',num_words*2 + num_bytes);
493 CVAL(buf,smb_wct) = num_words;
494 SSVAL(buf,smb_vwv + num_words*SIZEOFWORD,num_bytes);
495 smb_setlen(buf,smb_size + num_words*2 + num_bytes - 4);
496 return (smb_size + num_words*2 + num_bytes);
499 /*******************************************************************
500 reduce a file name, removing .. elements.
501 ********************************************************************/
502 void dos_clean_name(char *s)
506 DEBUG(3,("dos_clean_name [%s]\n",s));
508 /* remove any double slashes */
509 all_string_sub(s, "\\\\", "\\", 0);
511 while ((p = strstr(s,"\\..\\")) != NULL)
518 if ((p=strrchr(s,'\\')) != NULL)
525 trim_string(s,NULL,"\\..");
527 all_string_sub(s, "\\.\\", "\\", 0);
530 /*******************************************************************
531 reduce a file name, removing .. elements.
532 ********************************************************************/
533 void unix_clean_name(char *s)
537 DEBUG(3,("unix_clean_name [%s]\n",s));
539 /* remove any double slashes */
540 all_string_sub(s, "//","/", 0);
542 /* Remove leading ./ characters */
543 if(strncmp(s, "./", 2) == 0) {
544 trim_string(s, "./", NULL);
549 while ((p = strstr(s,"/../")) != NULL)
556 if ((p=strrchr(s,'/')) != NULL)
563 trim_string(s,NULL,"/..");
566 /*******************************************************************
567 reduce a file name, removing .. elements and checking that
568 it is below dir in the heirachy. This uses dos_GetWd() and so must be run
569 on the system that has the referenced file system.
571 widelinks are allowed if widelinks is true
572 ********************************************************************/
574 BOOL reduce_name(char *s,char *dir,BOOL widelinks)
584 BOOL relative = (*s != '/');
586 *dir2 = *wd = *base_name = *newname = 0;
591 /* can't have a leading .. */
592 if (strncmp(s,"..",2) == 0 && (s[2]==0 || s[2]=='/'))
594 DEBUG(3,("Illegal file name? (%s)\n",s));
604 DEBUG(3,("reduce_name [%s] [%s]\n",s,dir));
606 /* remove any double slashes */
607 all_string_sub(s,"//","/",0);
609 pstrcpy(base_name,s);
610 p = strrchr(base_name,'/');
617 DEBUG(0,("couldn't getwd for %s %s\n",s,dir));
621 if (dos_ChDir(dir) != 0)
623 DEBUG(0,("couldn't chdir to %s\n",dir));
627 if (!dos_GetWd(dir2))
629 DEBUG(0,("couldn't getwd for %s\n",dir));
634 if (p && (p != base_name))
637 if (strcmp(p+1,".")==0)
639 if (strcmp(p+1,"..")==0)
643 if (dos_ChDir(base_name) != 0)
646 DEBUG(3,("couldn't chdir for %s %s basename=%s\n",s,dir,base_name));
650 if (!dos_GetWd(newname))
653 DEBUG(2,("couldn't get wd for %s %s\n",s,dir2));
657 if (p && (p != base_name))
659 pstrcat(newname,"/");
660 pstrcat(newname,p+1);
664 size_t l = strlen(dir2);
665 if (dir2[l-1] == '/')
668 if (strncmp(newname,dir2,l) != 0)
671 DEBUG(2,("Bad access attempt? s=%s dir=%s newname=%s l=%d\n",s,dir2,newname,(int)l));
677 if (newname[l] == '/')
678 pstrcpy(s,newname + l + 1);
680 pstrcpy(s,newname+l);
691 DEBUG(3,("reduced to %s\n",s));
696 /****************************************************************************
698 ****************************************************************************/
699 static void expand_one(char *Mask,int len)
702 while ((p1 = strchr(Mask,'*')) != NULL)
704 int lfill = (len+1) - strlen(Mask);
708 memset(tmp+l1,'?',lfill);
709 pstrcpy(tmp + l1 + lfill,Mask + l1 + 1);
714 /****************************************************************************
715 expand a wildcard expression, replacing *s with ?s
716 ****************************************************************************/
717 void expand_mask(char *Mask,BOOL doext)
724 BOOL absolute = (*Mask == '\\');
726 *mbeg = *mext = *dirpart = *filepart = 0;
728 /* parse the directory and filename */
729 if (strchr(Mask,'\\'))
730 split_at_last_component(Mask,dirpart,'\\',NULL);
732 filename_dos(Mask,filepart);
734 pstrcpy(mbeg,filepart);
735 if ((p1 = strchr(mbeg,'.')) != NULL)
745 if (strlen(mbeg) > 8)
747 pstrcpy(mext,mbeg + 8);
753 pstrcpy(mbeg,"????????");
754 if ((*mext == 0) && doext && !hasdot)
757 if (strequal(mbeg,"*") && *mext==0)
765 pstrcpy(Mask,dirpart);
766 if (*dirpart || absolute) pstrcat(Mask,"\\");
771 DEBUG(6,("Mask expanded to [%s]\n",Mask));
776 /****************************************************************************
778 ****************************************************************************/
779 void make_dir_struct(char *buf,char *mask,char *fname,SMB_OFF_T size,int mode,time_t date)
786 if ((mode & aDIR) != 0)
789 memset(buf+1,' ',11);
790 if ((p = strchr(mask2,'.')) != NULL)
793 memcpy(buf+1,mask2,MIN(strlen(mask2),8));
794 memcpy(buf+9,p+1,MIN(strlen(p+1),3));
798 memcpy(buf+1,mask2,MIN(strlen(mask2),11));
800 memset(buf+21,'\0',DIR_STRUCT_SIZE-21);
802 put_dos_date(buf,22,date);
803 SSVAL(buf,26,size & 0xFFFF);
804 SSVAL(buf,28,(size >> 16)&0xFFFF);
805 StrnCpy(buf+30,fname,12);
808 DEBUG(8,("put name [%s] into dir struct\n",buf+30));
812 /*******************************************************************
813 close the low 3 fd's and open dev/null in their place
814 ********************************************************************/
815 void close_low_fds(void)
819 close(0); close(1); close(2);
820 /* try and use up these file descriptors, so silly
821 library routines writing to stdout etc won't cause havoc */
823 fd = sys_open("/dev/null",O_RDWR,0);
824 if (fd < 0) fd = sys_open("/dev/null",O_WRONLY,0);
826 DEBUG(0,("Can't open /dev/null\n"));
830 DEBUG(0,("Didn't get file descriptor %d\n",i));
836 /****************************************************************************
837 Set a fd into blocking/nonblocking mode. Uses POSIX O_NONBLOCK if available,
841 ****************************************************************************/
842 int set_blocking(int fd, BOOL set)
846 #define FLAG_TO_SET O_NONBLOCK
849 #define FLAG_TO_SET O_NDELAY
851 #define FLAG_TO_SET FNDELAY
855 if((val = fcntl(fd, F_GETFL, 0)) == -1)
857 if(set) /* Turn blocking on - ie. clear nonblock flag */
861 return fcntl( fd, F_SETFL, val);
865 /****************************************************************************
866 transfer some data between two fd's
867 ****************************************************************************/
868 SMB_OFF_T transfer_file(int infd,int outfd,SMB_OFF_T n,char *header,int headlen,int align)
870 static char *buf=NULL;
875 DEBUG(4,("transfer_file n=%.0f (head=%d) called\n",(double)n,headlen));
878 size = lp_readsize();
879 size = MAX(size,1024);
882 while (!buf && size>0) {
883 buf = (char *)Realloc(buf,size+8);
888 DEBUG(0,("Can't allocate transfer buffer!\n"));
892 abuf = buf + (align%8);
899 int s = (int)MIN(n,(SMB_OFF_T)size);
904 if (header && (headlen >= MIN(s,1024))) {
914 if (header && headlen > 0)
916 ret = MIN(headlen,size);
917 memcpy(buf1,header,ret);
920 if (headlen <= 0) header = NULL;
924 ret += read(infd,buf1+ret,s-ret);
928 ret2 = (outfd>=0?write_data(outfd,buf1,ret):ret);
929 if (ret2 > 0) total += ret2;
930 /* if we can't write then dump excess data */
932 transfer_file(infd,-1,n-(ret+headlen),NULL,0,0);
934 if (ret <= 0 || ret2 != ret)
943 /****************************************************************************
944 find a pointer to a netbios name
945 ****************************************************************************/
946 static char *name_ptr(char *buf,int ofs)
948 unsigned char c = *(unsigned char *)(buf+ofs);
950 if ((c & 0xC0) == 0xC0)
952 uint16 l = RSVAL(buf, ofs) & 0x3FFF;
953 DEBUG(5,("name ptr to pos %d from %d is %s\n",l,ofs,buf+l));
960 /****************************************************************************
961 extract a netbios name from a buf
962 ****************************************************************************/
963 int name_extract(char *buf,int ofs,char *name)
965 char *p = name_ptr(buf,ofs);
966 int d = PTR_DIFF(p,buf+ofs);
968 if (d < -50 || d > 50) return(0);
969 return(name_interpret(p,name));
972 /****************************************************************************
973 return the total storage length of a mangled name
974 ****************************************************************************/
975 int name_len(char *s1)
977 /* NOTE: this argument _must_ be unsigned */
978 unsigned char *s = (unsigned char *)s1;
981 /* If the two high bits of the byte are set, return 2. */
982 if (0xC0 == (*s & 0xC0))
985 /* Add up the length bytes. */
986 for (len = 1; (*s); s += (*s) + 1) {
988 SMB_ASSERT(len < 80);
995 /*******************************************************************
996 sleep for a specified number of milliseconds
997 ********************************************************************/
1001 struct timeval tval,t1,t2;
1008 tval.tv_sec = (t-tdiff)/1000;
1009 tval.tv_usec = 1000*((t-tdiff)%1000);
1013 sys_select(0,&fds,&tval);
1016 tdiff = TvalDiff(&t1,&t2);
1021 /*********************************************************
1022 * Recursive routine that is called by unix_mask_match.
1023 * Does the actual matching. This is the 'original code'
1024 * used by the unix matcher.
1025 *********************************************************/
1027 BOOL unix_do_match(char *str, char *regexp, BOOL case_sig)
1032 while(*str && (case_sig ? (*p != *str) : (toupper(*p)!=toupper(*str))))
1035 for( p = regexp; *p && *str; ) {
1043 * Look for a character matching
1044 * the one after the '*'.
1048 return True; /* Automatic match */
1051 * Patch from weidel@multichart.de. In the case of the regexp
1052 * '*XX*' we want to ensure there are at least 2 'X' characters
1053 * in the filename after the '*' for a match to be made.
1060 * Eat all the characters that match, but count how many there were.
1063 while(*str && (case_sig ? (*p == *str) : (toupper(*p)==toupper(*str)))) {
1069 * Now check that if the regexp had n identical characters that
1070 * matchcount had at least that many matches.
1073 while (( *(p+1) && (case_sig ? (*(p+1) == *p) : (toupper(*(p+1))==toupper(*p))))) {
1077 if ( matchcount <= 0 ) {
1081 str--; /* We've eaten the match char after the '*' */
1082 if(unix_do_match(str,p,case_sig))
1096 if(toupper(*str) != toupper(*p))
1107 if (!*p && str[0] == '.' && str[1] == 0)
1110 if (!*str && *p == '?')
1112 while (*p == '?') p++;
1116 if(!*str && (*p == '*' && p[1] == '\0'))
1122 /*********************************************************
1123 * Routine to match a given string with a regexp - uses
1124 * simplified regexp that takes * and ? only. Case can be
1125 * significant or not.
1126 * This is the 'original code' used by the unix matcher.
1127 *********************************************************/
1129 static BOOL unix_mask_match(char *str, char *regexp, BOOL case_sig)
1133 fstring ebase,eext,sbase,sext;
1136 /* Make local copies of str and regexp */
1137 StrnCpy(p1,regexp,sizeof(pstring)-1);
1138 StrnCpy(p2,str,sizeof(pstring)-1);
1140 /* Remove any *? and ** as they are meaningless */
1141 for(p = p1; *p; p++)
1142 while( *p == '*' && (p[1] == '?' ||p[1] == '*'))
1143 (void)pstrcpy( &p[1], &p[2]);
1145 if (strequal(p1,"*")) return(True);
1147 DEBUG(8,("unix_mask_match str=<%s> regexp=<%s>, case_sig = %d\n", p2, p1, case_sig));
1152 matched = unix_do_match(sbase,ebase,case_sig);
1154 DEBUG(8,("unix_mask_match returning %d\n", matched));
1159 /*********************************************************
1160 * Recursive routine that is called by mask_match.
1161 * Does the actual matching. Returns True if matched,
1162 * False if failed. This is the 'new' NT style matcher.
1163 * The win9x_semantics parameter is needed as Win9x matching
1164 * is *actually different*. In Win9x, trailing '?' characters
1165 * will only match the *exact* number of characters. Under
1166 * DOS and NT they match any number. This makes no
1168 *********************************************************/
1170 static BOOL do_match(char *str, char *regexp, int case_sig, BOOL win9x_semantics)
1174 for( p = regexp; *p && *str; ) {
1181 /* Look for a character matching
1182 the one after the '*' */
1185 return True; /* Automatic match */
1187 while(*str && (case_sig ? (*p != *str) : (toupper(*p)!=toupper(*str))))
1191 * Patch from weidel@multichart.de. In the case of the regexp
1192 * '*XX*' we want to ensure there are at least 2 'X' characters
1193 * in the filename after the '*' for a match to be made.
1200 * Eat all the characters that match, but count how many there were.
1203 while(*str && (case_sig ? (*p == *str) : (toupper(*p)==toupper(*str)))) {
1209 * Now check that if the regexp had n identical characters that
1210 * matchcount had at least that many matches.
1213 while (( *(p+1) && (case_sig ? (*(p+1) == *p) : (toupper(*(p+1))==toupper(*p))))) {
1217 if ( matchcount <= 0 ) {
1221 str--; /* We've eaten the match char after the '*' */
1222 if(do_match(str,p,case_sig,win9x_semantics)) {
1239 if(toupper(*str) != toupper(*p)) {
1251 if (!*p && str[0] == '.' && str[1] == 0) {
1255 if (!win9x_semantics) {
1256 if (!*str && *p == '?') {
1263 if(!*str && (*p == '*' && p[1] == '\0')) {
1270 /*********************************************************
1271 * Routine to match a given string with a regexp - uses
1272 * simplified regexp that takes * and ? only. Case can be
1273 * significant or not.
1274 * The 8.3 handling was rewritten by Ums Harald <Harald.Ums@pro-sieben.de>
1275 * This is the new 'NT style' matcher.
1276 *********************************************************/
1278 BOOL mask_match(char *str, char *regexp, BOOL case_sig, BOOL trans2)
1281 pstring t_pattern, t_filename, te_pattern, te_filename;
1282 fstring ebase,eext,sbase,sext;
1283 BOOL matched = False;
1284 BOOL win9x_semantics = (get_remote_arch() == RA_WIN95) && trans2;
1286 /* special case - if it is exactly the same then it always matches! */
1287 if(exact_match(str, regexp, case_sig))
1290 /* Make local copies of str and regexp */
1291 pstrcpy(t_pattern,regexp);
1292 pstrcpy(t_filename,str);
1296 /* a special case for 16 bit apps */
1297 if (strequal(t_pattern,"????????.???"))
1298 pstrcpy(t_pattern,"*");
1302 * Handle broken clients that send us old 8.3 format.
1304 pstring_sub(t_pattern,"????????","*");
1305 pstring_sub(t_pattern,".???",".*");
1311 * Not sure if this is a good idea. JRA.
1313 if(trans2 && is_8_3(t_pattern,False) && is_8_3(t_filename,False))
1318 if (!strchr(t_filename,'.')) {
1319 pstrcat(t_filename,".");
1323 /* Remove any *? and ** as they are meaningless */
1324 for(p = t_pattern; *p; p++)
1325 while( *p == '*' && (p[1] == '?' || p[1] == '*'))
1326 (void)pstrcpy( &p[1], &p[2]);
1328 if (strequal(t_pattern,"*"))
1331 DEBUG(8,("mask_match str=<%s> regexp=<%s>, case_sig = %d\n", t_filename, t_pattern, case_sig));
1335 * Match each component of the regexp, split up by '.'
1338 char *fp, *rp, *cp2, *cp1;
1339 BOOL last_wcard_was_star = False;
1340 int num_path_components, num_regexp_components;
1342 pstrcpy(te_pattern,t_pattern);
1343 pstrcpy(te_filename,t_filename);
1345 * Remove multiple "*." patterns.
1347 pstring_sub(te_pattern, "*.*.", "*.");
1348 num_regexp_components = count_chars(te_pattern, '.');
1349 num_path_components = count_chars(te_filename, '.');
1352 * Check for special 'hack' case of "DIR a*z". - needs to match a.b.c...z
1354 if(num_regexp_components == 0)
1355 matched = do_match( te_filename, te_pattern, case_sig, win9x_semantics);
1357 for( cp1 = te_pattern, cp2 = te_filename; cp1;) {
1358 fp = strchr(cp2, '.');
1361 rp = strchr(cp1, '.');
1365 if(cp1[0] && cp1[strlen(cp1)-1] == '*')
1366 last_wcard_was_star = True;
1368 last_wcard_was_star = False;
1370 if(!do_match(cp2, cp1, case_sig, win9x_semantics))
1374 * Ugly ! Special case for Win9x *only*. If filename is XXXX and pattern extension
1375 * is '*' or all '?' then disallow match.
1378 if (win9x_semantics) {
1379 if (*cp2 == '\0' && str_is_all(cp1, '?'))
1383 cp1 = rp ? rp + 1 : NULL;
1384 cp2 = fp ? fp + 1 : "";
1386 if(last_wcard_was_star || ((cp1 != NULL) && (*cp1 == '*'))) {
1387 /* Eat the extra path components. */
1390 for(i = 0; i < num_path_components - num_regexp_components; i++) {
1391 fp = strchr(cp2, '.');
1395 if((cp1 != NULL) && do_match( cp2, cp1, case_sig, win9x_semantics)) {
1396 cp2 = fp ? fp + 1 : "";
1399 cp2 = fp ? fp + 1 : "";
1401 num_path_components -= i;
1404 if(cp1 == NULL && ((*cp2 == '\0') || last_wcard_was_star))
1409 /* -------------------------------------------------
1410 * Behaviour of Win95
1411 * for 8.3 filenames and 8.3 Wildcards
1412 * -------------------------------------------------
1414 if (strequal (t_filename, ".")) {
1416 * Patterns: *.* *. ?. ? ????????.??? are valid.
1419 if(strequal(t_pattern, "*.*") || strequal(t_pattern, "*.") ||
1420 strequal(t_pattern, "????????.???") ||
1421 strequal(t_pattern, "?.") || strequal(t_pattern, "?"))
1423 } else if (strequal (t_filename, "..")) {
1425 * Patterns: *.* *. ?. ? *.? ????????.??? are valid.
1428 if(strequal(t_pattern, "*.*") || strequal(t_pattern, "*.") ||
1429 strequal(t_pattern, "?.") || strequal(t_pattern, "?") ||
1430 strequal(t_pattern, "????????.???") ||
1431 strequal(t_pattern, "*.?") || strequal(t_pattern, "?.*"))
1435 if ((p = strrchr (t_pattern, '.'))) {
1437 * Wildcard has a suffix.
1440 fstrcpy (ebase, t_pattern);
1442 fstrcpy (eext, p + 1);
1444 /* pattern ends in DOT: treat as if there is no DOT */
1446 if (strequal (ebase, "*"))
1451 * No suffix for wildcard.
1453 fstrcpy (ebase, t_pattern);
1457 p = strrchr (t_filename, '.');
1458 if (p && (p[1] == 0) ) {
1460 * Filename has an extension of '.' only.
1462 *p = 0; /* nuke dot at end of string */
1463 p = 0; /* and treat it as if there is no extension */
1468 * Filename has an extension.
1471 fstrcpy (sbase, t_filename);
1472 fstrcpy (sext, p + 1);
1474 matched = do_match(sbase, ebase, case_sig, False)
1475 && do_match(sext, eext, case_sig, False);
1477 /* pattern has no extension */
1478 /* Really: match complete filename with pattern ??? means exactly 3 chars */
1479 matched = do_match(str, ebase, case_sig, False);
1483 * Filename has no extension.
1485 fstrcpy (sbase, t_filename);
1488 /* pattern has extension */
1489 matched = do_match(sbase, ebase, case_sig, False)
1490 && do_match(sext, eext, case_sig, False);
1493 matched = do_match(sbase, ebase, case_sig, False);
1494 #ifdef EMULATE_WEIRD_W95_MATCHING
1496 * Even Microsoft has some problems
1497 * Behaviour Win95 -> local disk
1498 * is different from Win95 -> smb drive from Nt 4.0
1499 * This branch would reflect the Win95 local disk behaviour
1502 /* a? matches aa and a in w95 */
1503 fstrcat (sbase, ".");
1504 matched = do_match(sbase, ebase, case_sig, False);
1512 DEBUG(8,("mask_match returning %d\n", matched));
1517 /****************************************************************************
1518 become a daemon, discarding the controlling terminal
1519 ****************************************************************************/
1520 void become_daemon(void)
1526 /* detach from the terminal */
1529 #elif defined(TIOCNOTTY)
1531 int i = sys_open("/dev/tty", O_RDWR, 0);
1533 ioctl(i, (int) TIOCNOTTY, (char *)0);
1537 #endif /* HAVE_SETSID */
1539 /* Close fd's 0,1,2. Needed if started by rsh */
1544 /****************************************************************************
1545 put up a yes/no prompt
1546 ****************************************************************************/
1552 if (!fgets(ans,sizeof(ans)-1,stdin))
1555 if (*ans == 'y' || *ans == 'Y')
1561 /****************************************************************************
1562 set the length of a file from a filedescriptor.
1563 Returns 0 on success, -1 on failure.
1564 ****************************************************************************/
1566 /* tpot vfs need to recode this function */
1568 int set_filelen(int fd, SMB_OFF_T len)
1570 /* According to W. R. Stevens advanced UNIX prog. Pure 4.3 BSD cannot
1571 extend a file with ftruncate. Provide alternate implementation
1574 #ifdef HAVE_FTRUNCATE_EXTEND
1575 return sys_ftruncate(fd, len);
1579 SMB_OFF_T currpos = sys_lseek(fd, (SMB_OFF_T)0, SEEK_CUR);
1583 /* Do an fstat to see if the file is longer than
1584 the requested size (call ftruncate),
1585 or shorter, in which case seek to len - 1 and write 1
1587 if(sys_fstat(fd, &st)<0)
1591 if (S_ISFIFO(st.st_mode))
1595 if(st.st_size == len)
1597 if(st.st_size > len)
1598 return sys_ftruncate(fd, len);
1600 if(sys_lseek(fd, len-1, SEEK_SET) != len -1)
1602 if(write(fd, &c, 1)!=1)
1604 /* Seek to where we were */
1605 if(sys_lseek(fd, currpos, SEEK_SET) != currpos)
1613 /****************************************************************************
1614 this is a version of setbuffer() for those machines that only have setvbuf
1615 ****************************************************************************/
1616 void setbuffer(FILE *f,char *buf,int bufsize)
1618 setvbuf(f,buf,_IOFBF,bufsize);
1623 /****************************************************************************
1624 parse out a filename from a path name. Assumes dos style filenames.
1625 ****************************************************************************/
1626 static char *filename_dos(char *path,char *buf)
1628 char *p = strrchr(path,'\\');
1640 /****************************************************************************
1641 expand a pointer to be a particular size
1642 ****************************************************************************/
1643 void *Realloc(void *p,size_t size)
1649 DEBUG(5,("Realloc asked for 0 bytes\n"));
1654 ret = (void *)malloc(size);
1656 ret = (void *)realloc(p,size);
1659 DEBUG(0,("Memory allocation error: failed to expand to %d bytes\n",(int)size));
1665 /****************************************************************************
1666 free memory, checks for NULL
1667 ****************************************************************************/
1668 void safe_free(void *p)
1677 /****************************************************************************
1678 get my own name and IP
1679 ****************************************************************************/
1680 BOOL get_myname(char *my_name)
1686 /* get my host name */
1687 if (gethostname(hostname, sizeof(hostname)) == -1) {
1688 DEBUG(0,("gethostname failed\n"));
1692 /* Ensure null termination. */
1693 hostname[sizeof(hostname)-1] = '\0';
1696 /* split off any parts after an initial . */
1697 char *p = strchr(hostname,'.');
1700 fstrcpy(my_name,hostname);
1706 /****************************************************************************
1707 interpret a protocol description string, with a default
1708 ****************************************************************************/
1709 int interpret_protocol(char *str,int def)
1711 if (strequal(str,"NT1"))
1712 return(PROTOCOL_NT1);
1713 if (strequal(str,"LANMAN2"))
1714 return(PROTOCOL_LANMAN2);
1715 if (strequal(str,"LANMAN1"))
1716 return(PROTOCOL_LANMAN1);
1717 if (strequal(str,"CORE"))
1718 return(PROTOCOL_CORE);
1719 if (strequal(str,"COREPLUS"))
1720 return(PROTOCOL_COREPLUS);
1721 if (strequal(str,"CORE+"))
1722 return(PROTOCOL_COREPLUS);
1724 DEBUG(0,("Unrecognised protocol level %s\n",str));
1729 /****************************************************************************
1730 Return true if a string could be a pure IP address.
1731 ****************************************************************************/
1733 BOOL is_ipaddress(const char *str)
1735 BOOL pure_address = True;
1738 for (i=0; pure_address && str[i]; i++)
1739 if (!(isdigit((int)str[i]) || str[i] == '.'))
1740 pure_address = False;
1742 /* Check that a pure number is not misinterpreted as an IP */
1743 pure_address = pure_address && (strchr(str, '.') != NULL);
1745 return pure_address;
1748 /****************************************************************************
1749 interpret an internet address or name into an IP address in 4 byte form
1750 ****************************************************************************/
1752 uint32 interpret_addr(char *str)
1757 if (strcmp(str,"0.0.0.0") == 0) return(0);
1758 if (strcmp(str,"255.255.255.255") == 0) return(0xFFFFFFFF);
1760 /* if it's in the form of an IP address then get the lib to interpret it */
1761 if (is_ipaddress(str)) {
1762 res = inet_addr(str);
1764 /* otherwise assume it's a network name of some sort and use
1766 if ((hp = Get_Hostbyname(str)) == 0) {
1767 DEBUG(3,("Get_Hostbyname: Unknown host. %s\n",str));
1770 if(hp->h_addr == NULL) {
1771 DEBUG(3,("Get_Hostbyname: host address is invalid for host %s\n",str));
1774 putip((char *)&res,(char *)hp->h_addr);
1777 if (res == (uint32)-1) return(0);
1782 /*******************************************************************
1783 a convenient addition to interpret_addr()
1784 ******************************************************************/
1785 struct in_addr *interpret_addr2(char *str)
1787 static struct in_addr ret;
1788 uint32 a = interpret_addr(str);
1793 /*******************************************************************
1794 check if an IP is the 0.0.0.0
1795 ******************************************************************/
1796 BOOL zero_ip(struct in_addr ip)
1799 putip((char *)&a,(char *)&ip);
1804 /*******************************************************************
1805 matchname - determine if host name matches IP address
1806 ******************************************************************/
1807 BOOL matchname(char *remotehost,struct in_addr addr)
1812 if ((hp = Get_Hostbyname(remotehost)) == 0) {
1813 DEBUG(0,("Get_Hostbyname(%s): lookup failure.\n", remotehost));
1818 * Make sure that gethostbyname() returns the "correct" host name.
1819 * Unfortunately, gethostbyname("localhost") sometimes yields
1820 * "localhost.domain". Since the latter host name comes from the
1821 * local DNS, we just have to trust it (all bets are off if the local
1822 * DNS is perverted). We always check the address list, though.
1825 if (strcasecmp(remotehost, hp->h_name)
1826 && strcasecmp(remotehost, "localhost")) {
1827 DEBUG(0,("host name/name mismatch: %s != %s\n",
1828 remotehost, hp->h_name));
1832 /* Look up the host address in the address list we just got. */
1833 for (i = 0; hp->h_addr_list[i]; i++) {
1834 if (memcmp(hp->h_addr_list[i], (caddr_t) & addr, sizeof(addr)) == 0)
1839 * The host name does not map to the original host address. Perhaps
1840 * someone has compromised a name server. More likely someone botched
1841 * it, but that could be dangerous, too.
1844 DEBUG(0,("host name/address mismatch: %s != %s\n",
1845 inet_ntoa(addr), hp->h_name));
1850 #if (defined(HAVE_NETGROUP) && defined(WITH_AUTOMOUNT))
1851 /******************************************************************
1852 Remove any mount options such as -rsize=2048,wsize=2048 etc.
1853 Based on a fix from <Thomas.Hepper@icem.de>.
1854 *******************************************************************/
1856 static void strip_mount_options( pstring *str)
1861 while(*p && !isspace(*p))
1863 while(*p && isspace(*p))
1868 pstrcpy(tmp_str, p);
1869 pstrcpy(*str, tmp_str);
1874 /*******************************************************************
1875 Patch from jkf@soton.ac.uk
1876 Split Luke's automount_server into YP lookup and string splitter
1877 so can easily implement automount_path().
1878 As we may end up doing both, cache the last YP result.
1879 *******************************************************************/
1881 #ifdef WITH_NISPLUS_HOME
1882 static char *automount_lookup(char *user_name)
1884 static fstring last_key = "";
1885 static pstring last_value = "";
1887 char *nis_map = (char *)lp_nis_home_map_name();
1889 char nis_domain[NIS_MAXNAMELEN + 1];
1890 char buffer[NIS_MAXATTRVAL + 1];
1895 strncpy(nis_domain, (char *)nis_local_directory(), NIS_MAXNAMELEN);
1896 nis_domain[NIS_MAXNAMELEN] = '\0';
1898 DEBUG(5, ("NIS+ Domain: %s\n", nis_domain));
1900 if (strcmp(user_name, last_key))
1902 slprintf(buffer, sizeof(buffer)-1, "[%s=%s]%s.%s", "key", user_name, nis_map, nis_domain);
1903 DEBUG(5, ("NIS+ querystring: %s\n", buffer));
1905 if (result = nis_list(buffer, RETURN_RESULT, NULL, NULL))
1907 if (result->status != NIS_SUCCESS)
1909 DEBUG(3, ("NIS+ query failed: %s\n", nis_sperrno(result->status)));
1910 fstrcpy(last_key, ""); pstrcpy(last_value, "");
1914 object = result->objects.objects_val;
1915 if (object->zo_data.zo_type == ENTRY_OBJ)
1917 entry = &object->zo_data.objdata_u.en_data;
1918 DEBUG(5, ("NIS+ entry type: %s\n", entry->en_type));
1919 DEBUG(3, ("NIS+ result: %s\n", entry->en_cols.en_cols_val[1].ec_value.ec_value_val));
1921 pstrcpy(last_value, entry->en_cols.en_cols_val[1].ec_value.ec_value_val);
1922 pstring_sub(last_value, "&", user_name);
1923 fstrcpy(last_key, user_name);
1927 nis_freeresult(result);
1930 strip_mount_options(&last_value);
1932 DEBUG(4, ("NIS+ Lookup: %s resulted in %s\n", user_name, last_value));
1935 #else /* WITH_NISPLUS_HOME */
1936 static char *automount_lookup(char *user_name)
1938 static fstring last_key = "";
1939 static pstring last_value = "";
1941 int nis_error; /* returned by yp all functions */
1942 char *nis_result; /* yp_match inits this */
1943 int nis_result_len; /* and set this */
1944 char *nis_domain; /* yp_get_default_domain inits this */
1945 char *nis_map = (char *)lp_nis_home_map_name();
1947 if ((nis_error = yp_get_default_domain(&nis_domain)) != 0)
1949 DEBUG(3, ("YP Error: %s\n", yperr_string(nis_error)));
1953 DEBUG(5, ("NIS Domain: %s\n", nis_domain));
1955 if (!strcmp(user_name, last_key))
1957 nis_result = last_value;
1958 nis_result_len = strlen(last_value);
1963 if ((nis_error = yp_match(nis_domain, nis_map,
1964 user_name, strlen(user_name),
1965 &nis_result, &nis_result_len)) != 0)
1967 DEBUG(3, ("YP Error: \"%s\" while looking up \"%s\" in map \"%s\"\n",
1968 yperr_string(nis_error), user_name, nis_map));
1970 if (!nis_error && nis_result_len >= sizeof(pstring))
1972 nis_result_len = sizeof(pstring)-1;
1974 fstrcpy(last_key, user_name);
1975 strncpy(last_value, nis_result, nis_result_len);
1976 last_value[nis_result_len] = '\0';
1979 strip_mount_options(&last_value);
1981 DEBUG(4, ("YP Lookup: %s resulted in %s\n", user_name, last_value));
1984 #endif /* WITH_NISPLUS_HOME */
1987 /*******************************************************************
1988 Patch from jkf@soton.ac.uk
1989 This is Luke's original function with the NIS lookup code
1990 moved out to a separate function.
1991 *******************************************************************/
1992 static char *automount_server(char *user_name)
1994 static pstring server_name;
1996 /* use the local machine name as the default */
1997 /* this will be the default if WITH_AUTOMOUNT is not used or fails */
1998 pstrcpy(server_name, local_machine);
2000 #if (defined(HAVE_NETGROUP) && defined (WITH_AUTOMOUNT))
2002 if (lp_nis_home_map())
2004 int home_server_len;
2005 char *automount_value = automount_lookup(user_name);
2006 home_server_len = strcspn(automount_value,":");
2007 DEBUG(5, ("NIS lookup succeeded. Home server length: %d\n",home_server_len));
2008 if (home_server_len > sizeof(pstring))
2010 home_server_len = sizeof(pstring);
2012 strncpy(server_name, automount_value, home_server_len);
2013 server_name[home_server_len] = '\0';
2017 DEBUG(4,("Home server: %s\n", server_name));
2022 /*******************************************************************
2023 Patch from jkf@soton.ac.uk
2024 Added this to implement %p (NIS auto-map version of %H)
2025 *******************************************************************/
2026 static char *automount_path(char *user_name)
2028 static pstring server_path;
2030 /* use the passwd entry as the default */
2031 /* this will be the default if WITH_AUTOMOUNT is not used or fails */
2032 /* pstrcpy() copes with get_user_home_dir() returning NULL */
2033 pstrcpy(server_path, get_user_home_dir(user_name));
2035 #if (defined(HAVE_NETGROUP) && defined (WITH_AUTOMOUNT))
2037 if (lp_nis_home_map())
2039 char *home_path_start;
2040 char *automount_value = automount_lookup(user_name);
2041 home_path_start = strchr(automount_value,':');
2042 if (home_path_start != NULL)
2044 DEBUG(5, ("NIS lookup succeeded. Home path is: %s\n",
2045 home_path_start?(home_path_start+1):""));
2046 pstrcpy(server_path, home_path_start+1);
2051 DEBUG(4,("Home server path: %s\n", server_path));
2056 /*******************************************************************
2057 Given a pointer to a %$(NAME) expand it as an environment variable.
2058 Return the number of characters by which the pointer should be advanced.
2059 Based on code by Branko Cibej <branko.cibej@hermes.si>
2060 When this is called p points at the '%' character.
2061 ********************************************************************/
2063 static size_t expand_env_var(char *p, int len)
2077 * Look for the terminating ')'.
2080 if ((q = strchr(p,')')) == NULL) {
2081 DEBUG(0,("expand_env_var: Unterminated environment variable [%s]\n", p));
2086 * Extract the name from within the %$(NAME) string.
2090 copylen = MIN((q-r),(sizeof(envname)-1));
2091 strncpy(envname,r,copylen);
2092 envname[copylen] = '\0';
2094 if ((envval = getenv(envname)) == NULL) {
2095 DEBUG(0,("expand_env_var: Environment variable [%s] not set\n", envname));
2100 * Copy the full %$(NAME) into envname so it
2104 copylen = MIN((q+1-p),(sizeof(envname)-1));
2105 strncpy(envname,p,copylen);
2106 envname[copylen] = '\0';
2107 string_sub(p,envname,envval,len);
2108 return 0; /* Allow the environment contents to be parsed. */
2111 /*******************************************************************
2112 Substitute strings with useful parameters.
2113 Rewritten by Stefaan A Eeckels <Stefaan.Eeckels@ecc.lu> and
2114 Paul Rippin <pr3245@nopc.eurostat.cec.be>.
2115 ********************************************************************/
2117 void standard_sub_basic(char *str)
2121 struct passwd *pass;
2122 char *username = sam_logon_in_ssb ? samlogon_user : sesssetup_user;
2124 for (s = str ; s && *s && (p = strchr(s,'%')); s = p )
2126 int l = sizeof(pstring) - (int)(p-str);
2129 DEBUG(0,("ERROR: string overflow by %d in standard_sub_basic(%.50s)\n",
2139 if ((pass = Get_Pwnam(username,False))!=NULL) {
2140 string_sub(p,"%G",gidtoname(pass->pw_gid),l);
2146 case 'N' : string_sub(p,"%N", automount_server(username),l); break;
2147 case 'I' : string_sub(p,"%I", client_addr(Client),l); break;
2148 case 'L' : string_sub(p,"%L", local_machine,l); break;
2149 case 'M' : string_sub(p,"%M", client_name(Client),l); break;
2150 case 'R' : string_sub(p,"%R", remote_proto,l); break;
2151 case 'T' : string_sub(p,"%T", timestring(False),l); break;
2152 case 'U' : string_sub(p,"%U", username,l); break;
2153 case 'a' : string_sub(p,"%a", remote_arch,l); break;
2156 slprintf(pidstr,sizeof(pidstr) - 1, "%d",(int)getpid());
2157 string_sub(p,"%d", pidstr,l);
2160 case 'h' : string_sub(p,"%h", myhostname(),l); break;
2161 case 'm' : string_sub(p,"%m", remote_machine,l); break;
2162 case 'v' : string_sub(p,"%v", VERSION,l); break;
2163 case '$' : p += expand_env_var(p,l); break; /* Expand environment variables */
2164 case '\0': p++; break; /* don't run off end if last character is % */
2165 default : p+=2; break;
2172 /****************************************************************************
2173 Do some standard substitutions in a string.
2174 ****************************************************************************/
2176 void standard_sub(connection_struct *conn,char *str)
2180 for (s=str; (p=strchr(s, '%'));s=p) {
2181 int l = sizeof(pstring) - (int)(p-str);
2185 if ((home = get_user_home_dir(conn->user))) {
2186 string_sub(p,"%H",home,l);
2193 string_sub(p,"%P",conn->connectpath,l);
2198 lp_servicename(SNUM(conn)),l);
2203 gidtoname(conn->gid),l);
2206 string_sub(p,"%u",conn->user,l);
2209 /* Patch from jkf@soton.ac.uk Left the %N (NIS
2210 * server name) in standard_sub_basic as it is
2211 * a feature for logon servers, hence uses the
2212 * username. The %p (NIS server path) code is
2213 * here as it is used instead of the default
2214 * "path =" string in [homes] and so needs the
2215 * service name, not the username. */
2218 automount_path(lp_servicename(SNUM(conn))),l);
2222 break; /* don't run off the end of the string
2230 standard_sub_basic(str);
2235 /*******************************************************************
2236 are two IPs on the same subnet?
2237 ********************************************************************/
2238 BOOL same_net(struct in_addr ip1,struct in_addr ip2,struct in_addr mask)
2240 uint32 net1,net2,nmask;
2242 nmask = ntohl(mask.s_addr);
2243 net1 = ntohl(ip1.s_addr);
2244 net2 = ntohl(ip2.s_addr);
2246 return((net1 & nmask) == (net2 & nmask));
2250 /****************************************************************************
2251 a wrapper for gethostbyname() that tries with all lower and all upper case
2252 if the initial name fails
2253 ****************************************************************************/
2254 struct hostent *Get_Hostbyname(const char *name)
2256 char *name2 = strdup(name);
2257 struct hostent *ret;
2261 DEBUG(0,("Memory allocation error in Get_Hostbyname! panic\n"));
2267 * This next test is redundent and causes some systems (with
2268 * broken isalnum() calls) problems.
2273 if (!isalnum(*name2))
2280 ret = sys_gethostbyname(name2);
2287 /* try with all lowercase */
2289 ret = sys_gethostbyname(name2);
2296 /* try with all uppercase */
2298 ret = sys_gethostbyname(name2);
2305 /* nothing works :-( */
2311 /****************************************************************************
2312 check if a process exists. Does this work on all unixes?
2313 ****************************************************************************/
2315 BOOL process_exists(pid_t pid)
2317 return(kill(pid,0) == 0 || errno != ESRCH);
2321 /*******************************************************************
2322 turn a uid into a user name
2323 ********************************************************************/
2324 char *uidtoname(uid_t uid)
2326 static char name[40];
2327 struct passwd *pass = sys_getpwuid(uid);
2328 if (pass) return(pass->pw_name);
2329 slprintf(name, sizeof(name) - 1, "%d",(int)uid);
2334 /*******************************************************************
2335 turn a gid into a group name
2336 ********************************************************************/
2338 char *gidtoname(gid_t gid)
2340 static char name[40];
2341 struct group *grp = getgrgid(gid);
2342 if (grp) return(grp->gr_name);
2343 slprintf(name,sizeof(name) - 1, "%d",(int)gid);
2347 /*******************************************************************
2348 turn a user name into a uid
2349 ********************************************************************/
2350 uid_t nametouid(const char *name)
2352 struct passwd *pass;
2356 u = strtol(name, &p, 0);
2357 if (p != name) return u;
2359 pass = sys_getpwnam(name);
2360 if (pass) return(pass->pw_uid);
2364 /*******************************************************************
2365 turn a group name into a gid
2366 ********************************************************************/
2367 gid_t nametogid(const char *name)
2373 g = strtol(name, &p, 0);
2374 if (p != name) return g;
2376 grp = getgrnam(name);
2377 if (grp) return(grp->gr_gid);
2381 /*******************************************************************
2382 something really nasty happened - panic!
2383 ********************************************************************/
2384 void smb_panic(char *why)
2386 char *cmd = lp_panic_action();
2390 DEBUG(0,("PANIC: %s\n", why));
2396 /*******************************************************************
2397 a readdir wrapper which just returns the file name
2398 ********************************************************************/
2399 char *readdirname(DIR *p)
2401 SMB_STRUCT_DIRENT *ptr;
2404 if (!p) return(NULL);
2406 ptr = (SMB_STRUCT_DIRENT *)sys_readdir(p);
2407 if (!ptr) return(NULL);
2409 dname = ptr->d_name;
2412 if (telldir(p) < 0) return(NULL);
2415 #ifdef HAVE_BROKEN_READDIR
2416 /* using /usr/ucb/cc is BAD */
2422 memcpy(buf, dname, NAMLEN(ptr)+1);
2429 /*******************************************************************
2430 Utility function used to decide if the last component
2431 of a path matches a (possibly wildcarded) entry in a namelist.
2432 ********************************************************************/
2434 BOOL is_in_path(char *name, name_compare_entry *namelist)
2436 pstring last_component;
2439 DEBUG(8, ("is_in_path: %s\n", name));
2441 /* if we have no list it's obviously not in the path */
2442 if((namelist == NULL ) || ((namelist != NULL) && (namelist[0].name == NULL)))
2444 DEBUG(8,("is_in_path: no name list.\n"));
2448 /* Get the last component of the unix name. */
2449 p = strrchr(name, '/');
2450 strncpy(last_component, p ? ++p : name, sizeof(last_component)-1);
2451 last_component[sizeof(last_component)-1] = '\0';
2453 for(; namelist->name != NULL; namelist++)
2455 if(namelist->is_wild)
2458 * Look for a wildcard match. Use the old
2459 * 'unix style' mask match, rather than the
2462 if (unix_mask_match(last_component, namelist->name, case_sensitive))
2464 DEBUG(8,("is_in_path: mask match succeeded\n"));
2470 if((case_sensitive && (strcmp(last_component, namelist->name) == 0))||
2471 (!case_sensitive && (StrCaseCmp(last_component, namelist->name) == 0)))
2473 DEBUG(8,("is_in_path: match succeeded\n"));
2478 DEBUG(8,("is_in_path: match not found\n"));
2483 /*******************************************************************
2484 Strip a '/' separated list into an array of
2485 name_compare_enties structures suitable for
2486 passing to is_in_path(). We do this for
2487 speed so we can pre-parse all the names in the list
2488 and don't do it for each call to is_in_path().
2489 namelist is modified here and is assumed to be
2490 a copy owned by the caller.
2491 We also check if the entry contains a wildcard to
2492 remove a potentially expensive call to mask_match
2494 ********************************************************************/
2496 void set_namearray(name_compare_entry **ppname_array, char *namelist)
2499 char *nameptr = namelist;
2500 int num_entries = 0;
2503 (*ppname_array) = NULL;
2505 if((nameptr == NULL ) || ((nameptr != NULL) && (*nameptr == '\0')))
2508 /* We need to make two passes over the string. The
2509 first to count the number of elements, the second
2514 if ( *nameptr == '/' )
2516 /* cope with multiple (useless) /s) */
2520 /* find the next / */
2521 name_end = strchr(nameptr, '/');
2523 /* oops - the last check for a / didn't find one. */
2524 if (name_end == NULL)
2527 /* next segment please */
2528 nameptr = name_end + 1;
2532 if(num_entries == 0)
2535 if(( (*ppname_array) = (name_compare_entry *)malloc(
2536 (num_entries + 1) * sizeof(name_compare_entry))) == NULL)
2538 DEBUG(0,("set_namearray: malloc fail\n"));
2542 /* Now copy out the names */
2547 if ( *nameptr == '/' )
2549 /* cope with multiple (useless) /s) */
2553 /* find the next / */
2554 if ((name_end = strchr(nameptr, '/')) != NULL)
2559 /* oops - the last check for a / didn't find one. */
2560 if(name_end == NULL)
2563 (*ppname_array)[i].is_wild = ((strchr( nameptr, '?')!=NULL) ||
2564 (strchr( nameptr, '*')!=NULL));
2565 if(((*ppname_array)[i].name = strdup(nameptr)) == NULL)
2567 DEBUG(0,("set_namearray: malloc fail (1)\n"));
2571 /* next segment please */
2572 nameptr = name_end + 1;
2576 (*ppname_array)[i].name = NULL;
2581 /****************************************************************************
2582 routine to free a namearray.
2583 ****************************************************************************/
2585 void free_namearray(name_compare_entry *name_array)
2590 if(name_array->name != NULL)
2591 free(name_array->name);
2593 free((char *)name_array);
2596 /****************************************************************************
2597 Pathetically try and map a 64 bit lock offset into 31 bits. I hate Windows :-).
2598 ****************************************************************************/
2600 uint32 map_lock_offset(uint32 high, uint32 low)
2604 uint32 highcopy = high;
2607 * Try and find out how many significant bits there are in high.
2610 for(i = 0; highcopy; i++)
2614 * We use 31 bits not 32 here as POSIX
2615 * lock offsets may not be negative.
2618 mask = (~0) << (31 - i);
2621 return 0; /* Fail. */
2628 /****************************************************************************
2629 routine to do file locking
2630 ****************************************************************************/
2632 BOOL fcntl_lock(int fd, int op, SMB_OFF_T offset, SMB_OFF_T count, int type)
2635 SMB_STRUCT_FLOCK lock;
2637 #if defined(LARGE_SMB_OFF_T)
2639 * In the 64 bit locking case we store the original
2640 * values in case we have to map to a 32 bit lock on
2641 * a filesystem that doesn't support 64 bit locks.
2643 SMB_OFF_T orig_offset = offset;
2644 SMB_OFF_T orig_count = count;
2645 #endif /* LARGE_SMB_OFF_T */
2647 if(lp_ole_locking_compat()) {
2648 SMB_OFF_T mask2= ((SMB_OFF_T)0x3) << (SMB_OFF_T_BITS-4);
2649 SMB_OFF_T mask = (mask2<<2);
2651 /* make sure the count is reasonable, we might kill the lockd otherwise */
2654 /* the offset is often strange - remove 2 of its bits if either of
2655 the top two bits are set. Shift the top ones by two bits. This
2656 still allows OLE2 apps to operate, but should stop lockd from
2658 if ((offset & mask) != 0)
2659 offset = (offset & ~mask) | (((offset & mask) >> 2) & mask2);
2661 SMB_OFF_T mask2 = ((SMB_OFF_T)0x4) << (SMB_OFF_T_BITS-4);
2662 SMB_OFF_T mask = (mask2<<1);
2663 SMB_OFF_T neg_mask = ~mask;
2665 /* interpret negative counts as large numbers */
2669 /* no negative offsets */
2673 /* count + offset must be in range */
2674 while ((offset < 0 || (offset + count < 0)) && mask)
2677 mask = ((mask >> 1) & neg_mask);
2681 DEBUG(8,("fcntl_lock %d %d %.0f %.0f %d\n",fd,op,(double)offset,(double)count,type));
2684 lock.l_whence = SEEK_SET;
2685 lock.l_start = offset;
2691 ret = fcntl(fd,op,&lock);
2696 dbgtext("fcntl_lock: WARNING: lock request at offset %.0f, length %.0f returned\n", (double)offset,(double)count);
2697 dbgtext("a 'file too large' error. This can happen when using 64 bit lock offsets\n");
2698 dbgtext("on 32 bit NFS mounted file systems. Retrying with 32 bit truncated length.\n");
2700 /* 32 bit NFS file system, retry with smaller offset */
2702 lock.l_len = count & 0x7fffffff;
2703 ret = fcntl(fd,op,&lock);
2707 DEBUG(3,("fcntl lock gave errno %d (%s)\n",errno,strerror(errno)));
2710 if (op == SMB_F_GETLK)
2713 (lock.l_type != F_UNLCK) &&
2714 (lock.l_pid != 0) &&
2715 (lock.l_pid != getpid()))
2717 DEBUG(3,("fd %d is locked by pid %d\n",fd,(int)lock.l_pid));
2721 /* it must be not locked or locked by me */
2725 /* a lock set or unset */
2728 DEBUG(3,("lock failed at offset %.0f count %.0f op %d type %d (%s)\n",
2729 (double)offset,(double)count,op,type,strerror(errno)));
2731 /* perhaps it doesn't support this sort of locking?? */
2732 if (errno == EINVAL)
2735 #if defined(LARGE_SMB_OFF_T)
2738 * Ok - if we get here then we have a 64 bit lock request
2739 * that has returned EINVAL. Try and map to 31 bits for offset
2740 * and length and try again. This may happen if a filesystem
2741 * doesn't support 64 bit offsets (efs/ufs) although the underlying
2744 uint32 off_low = (orig_offset & 0xFFFFFFFF);
2745 uint32 off_high = ((orig_offset >> 32) & 0xFFFFFFFF);
2747 lock.l_len = (orig_count & 0x7FFFFFFF);
2748 lock.l_start = (SMB_OFF_T)map_lock_offset(off_high, off_low);
2749 ret = fcntl(fd,op,&lock);
2752 if (errno == EINVAL)
2754 DEBUG(3,("locking not supported? returning True\n"));
2759 DEBUG(3,("64 -> 32 bit modified lock call successful\n"));
2762 #else /* LARGE_SMB_OFF_T */
2763 DEBUG(3,("locking not supported? returning True\n"));
2765 #endif /* LARGE_SMB_OFF_T */
2771 /* everything went OK */
2772 DEBUG(8,("Lock call successful\n"));
2780 /*******************************************************************
2781 is the name specified one of my netbios names
2782 returns true is it is equal, false otherwise
2783 ********************************************************************/
2784 BOOL is_myname(char *s)
2789 for (n=0; my_netbios_names[n]; n++) {
2790 if (strequal(my_netbios_names[n], s))
2793 DEBUG(8, ("is_myname(\"%s\") returns %d\n", s, ret));
2797 /*******************************************************************
2798 set the horrid remote_arch string based on an enum.
2799 ********************************************************************/
2800 void set_remote_arch(enum remote_arch_types type)
2806 fstrcpy(remote_arch, "WfWg");
2809 fstrcpy(remote_arch, "OS2");
2812 fstrcpy(remote_arch, "Win95");
2815 fstrcpy(remote_arch, "WinNT");
2818 fstrcpy(remote_arch, "Win2K");
2821 fstrcpy(remote_arch,"Samba");
2824 ra_type = RA_UNKNOWN;
2825 fstrcpy(remote_arch, "UNKNOWN");
2830 /*******************************************************************
2831 Get the remote_arch type.
2832 ********************************************************************/
2833 enum remote_arch_types get_remote_arch(void)
2839 /*******************************************************************
2840 align a pointer to a multiple of 2 bytes
2841 ********************************************************************/
2842 char *align2(char *q, char *base)
2851 void out_ascii(FILE *f, unsigned char *buf,int len)
2856 fprintf(f, "%c", isprint(buf[i])?buf[i]:'.');
2860 void out_data(FILE *f,char *buf1,int len, int per_line)
2862 unsigned char *buf = (unsigned char *)buf1;
2869 fprintf(f, "[%03X] ",i);
2872 fprintf(f, "%02X ",(int)buf[i]);
2874 if (i%(per_line/2) == 0) fprintf(f, " ");
2875 if (i%per_line == 0)
2877 out_ascii(f,&buf[i-per_line ],per_line/2); fprintf(f, " ");
2878 out_ascii(f,&buf[i-per_line/2],per_line/2); fprintf(f, "\n");
2879 if (i<len) fprintf(f, "[%03X] ",i);
2882 if ((i%per_line) != 0)
2886 n = per_line - (i%per_line);
2888 if (n>(per_line/2)) fprintf(f, " ");
2893 n = MIN(per_line/2,i%per_line);
2894 out_ascii(f,&buf[i-(i%per_line)],n); fprintf(f, " ");
2895 n = (i%per_line) - n;
2896 if (n>0) out_ascii(f,&buf[i-n],n);
2901 void print_asc(int level, unsigned char *buf,int len)
2905 DEBUG(level,("%c", isprint(buf[i])?buf[i]:'.'));
2908 void dump_data(int level,char *buf1,int len)
2910 unsigned char *buf = (unsigned char *)buf1;
2914 DEBUG(level,("[%03X] ",i));
2916 DEBUG(level,("%02X ",(int)buf[i]));
2918 if (i%8 == 0) DEBUG(level,(" "));
2920 print_asc(level,&buf[i-16],8); DEBUG(level,(" "));
2921 print_asc(level,&buf[i-8],8); DEBUG(level,("\n"));
2922 if (i<len) DEBUG(level,("[%03X] ",i));
2930 if (n>8) DEBUG(level,(" "));
2931 while (n--) DEBUG(level,(" "));
2934 print_asc(level,&buf[i-(i%16)],n); DEBUG(level,(" "));
2936 if (n>0) print_asc(level,&buf[i-n],n);
2937 DEBUG(level,("\n"));
2941 char *tab_depth(int depth)
2943 static pstring spaces;
2944 memset(spaces, ' ', depth * 4);
2945 spaces[depth * 4] = 0;
2949 /*****************************************************************************
2950 * Provide a checksum on a string
2952 * Input: s - the null-terminated character string for which the checksum
2953 * will be calculated.
2955 * Output: The checksum value calculated for s.
2957 * ****************************************************************************
2959 int str_checksum(const char *s)
2967 res ^= (c << (i % 15)) ^ (c >> (15-(i%15)));
2972 } /* str_checksum */
2976 /*****************************************************************
2977 zero a memory area then free it. Used to catch bugs faster
2978 *****************************************************************/
2979 void zero_free(void *p, size_t size)
2986 /*****************************************************************
2987 set our open file limit to a requested max and return the limit
2988 *****************************************************************/
2989 int set_maxfiles(int requested_max)
2991 #if (defined(HAVE_GETRLIMIT) && defined(RLIMIT_NOFILE))
2993 int saved_current_limit;
2995 if(getrlimit(RLIMIT_NOFILE, &rlp)) {
2996 DEBUG(0,("set_maxfiles: getrlimit (1) for RLIMIT_NOFILE failed with error %s\n",
2999 return requested_max;
3003 * Set the fd limit to be real_max_open_files + MAX_OPEN_FUDGEFACTOR to
3004 * account for the extra fd we need
3005 * as well as the log files and standard
3006 * handles etc. Save the limit we want to set in case
3007 * we are running on an OS that doesn't support this limit (AIX)
3008 * which always returns RLIM_INFINITY for rlp.rlim_max.
3011 saved_current_limit = rlp.rlim_cur = MIN(requested_max,rlp.rlim_max);
3013 if(setrlimit(RLIMIT_NOFILE, &rlp)) {
3014 DEBUG(0,("set_maxfiles: setrlimit for RLIMIT_NOFILE for %d files failed with error %s\n",
3015 (int)rlp.rlim_cur, strerror(errno) ));
3017 return saved_current_limit;
3020 if(getrlimit(RLIMIT_NOFILE, &rlp)) {
3021 DEBUG(0,("set_maxfiles: getrlimit (2) for RLIMIT_NOFILE failed with error %s\n",
3024 return saved_current_limit;
3027 #if defined(RLIM_INFINITY)
3028 if(rlp.rlim_cur == RLIM_INFINITY)
3029 return saved_current_limit;
3032 if((int)rlp.rlim_cur > saved_current_limit)
3033 return saved_current_limit;
3035 return rlp.rlim_cur;
3036 #else /* !defined(HAVE_GETRLIMIT) || !defined(RLIMIT_NOFILE) */
3038 * No way to know - just guess...
3040 return requested_max;
3044 /*****************************************************************
3045 splits out the start of the key (HKLM or HKU) and the rest of the key
3046 *****************************************************************/
3047 BOOL reg_split_key(char *full_keyname, uint32 *reg_type, char *key_name)
3051 if (!next_token(&full_keyname, tmp, "\\", sizeof(tmp)))
3058 DEBUG(10, ("reg_split_key: hive %s\n", tmp));
3060 if (strequal(tmp, "HKLM") || strequal(tmp, "HKEY_LOCAL_MACHINE"))
3062 (*reg_type) = HKEY_LOCAL_MACHINE;
3064 else if (strequal(tmp, "HKU") || strequal(tmp, "HKEY_USERS"))
3066 (*reg_type) = HKEY_USERS;
3070 DEBUG(10,("reg_split_key: unrecognised hive key %s\n", tmp));
3074 if (next_token(NULL, tmp, "\n\r", sizeof(tmp)))
3076 fstrcpy(key_name, tmp);
3083 DEBUG(10, ("reg_split_key: name %s\n", key_name));
3089 /*****************************************************************
3090 like mktemp() but make sure that no % characters are used
3091 % characters are bad for us because of the macro subs
3092 *****************************************************************/
3093 char *smbd_mktemp(char *template)
3095 char *p = mktemp(template);
3099 if (!p) return NULL;
3101 while ((p2=strchr(p,'%'))) {
3103 while (sys_stat(p,&st) == 0 && p2[0] < 'Z') {
3104 /* damn, it exists */
3108 /* oh well ... better return something */
3118 /*****************************************************************
3119 like strdup but for memory
3120 *****************************************************************/
3121 void *memdup(void *p, size_t size)
3125 if (!p2) return NULL;
3126 memcpy(p2, p, size);
3130 /*****************************************************************
3131 get local hostname and cache result
3132 *****************************************************************/
3133 char *myhostname(void)
3143 /*****************************************************************
3144 a useful function for returning a path in the Samba lock directory
3145 *****************************************************************/
3146 char *lock_path(char *name)
3148 static pstring fname;
3150 pstrcpy(fname,lp_lockdir());
3151 trim_string(fname,"","/");
3153 if (!directory_exist(fname,NULL)) {
3158 pstrcat(fname,name);
3163 /*******************************************************************
3164 Given a filename - get its directory name
3165 NB: Returned in static storage. Caveats:
3166 o Not safe in thread environment.
3167 o Caller must not free.
3168 o If caller wishes to preserve, they should copy.
3169 ********************************************************************/
3171 char *parent_dirname(const char *path)
3173 static pstring dirpath;
3179 pstrcpy(dirpath, path);
3180 p = strrchr(dirpath, '/'); /* Find final '/', if any */
3182 pstrcpy(dirpath, "."); /* No final "/", so dir is "." */
3185 ++p; /* For root "/", leave "/" in place */