s3-time: fix build warnings after we moved to shared time functions.
[ira/wip.git] / source3 / lib / util.c
1 /* 
2    Unix SMB/CIFS implementation.
3    Samba utility functions
4    Copyright (C) Andrew Tridgell 1992-1998
5    Copyright (C) Jeremy Allison 2001-2007
6    Copyright (C) Simo Sorce 2001
7    Copyright (C) Jim McDonough <jmcd@us.ibm.com> 2003
8    Copyright (C) James Peach 2006
9
10    This program is free software; you can redistribute it and/or modify
11    it under the terms of the GNU General Public License as published by
12    the Free Software Foundation; either version 3 of the License, or
13    (at your option) any later version.
14
15    This program is distributed in the hope that it will be useful,
16    but WITHOUT ANY WARRANTY; without even the implied warranty of
17    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18    GNU General Public License for more details.
19
20    You should have received a copy of the GNU General Public License
21    along with this program.  If not, see <http://www.gnu.org/licenses/>.
22 */
23
24 #include "includes.h"
25
26 extern char *global_clobber_region_function;
27 extern unsigned int global_clobber_region_line;
28
29 /* Max allowable allococation - 256mb - 0x10000000 */
30 #define MAX_ALLOC_SIZE (1024*1024*256)
31
32 #if (defined(HAVE_NETGROUP) && defined (WITH_AUTOMOUNT))
33 #ifdef WITH_NISPLUS_HOME
34 #ifdef BROKEN_NISPLUS_INCLUDE_FILES
35 /*
36  * The following lines are needed due to buggy include files
37  * in Solaris 2.6 which define GROUP in both /usr/include/sys/acl.h and
38  * also in /usr/include/rpcsvc/nis.h. The definitions conflict. JRA.
39  * Also GROUP_OBJ is defined as 0x4 in /usr/include/sys/acl.h and as
40  * an enum in /usr/include/rpcsvc/nis.h.
41  */
42
43 #if defined(GROUP)
44 #undef GROUP
45 #endif
46
47 #if defined(GROUP_OBJ)
48 #undef GROUP_OBJ
49 #endif
50
51 #endif /* BROKEN_NISPLUS_INCLUDE_FILES */
52
53 #include <rpcsvc/nis.h>
54
55 #endif /* WITH_NISPLUS_HOME */
56 #endif /* HAVE_NETGROUP && WITH_AUTOMOUNT */
57
58 static enum protocol_types Protocol = PROTOCOL_COREPLUS;
59
60 enum protocol_types get_Protocol(void)
61 {
62         return Protocol;
63 }
64
65 void set_Protocol(enum protocol_types  p)
66 {
67         Protocol = p;
68 }
69
70 static enum remote_arch_types ra_type = RA_UNKNOWN;
71
72 /***********************************************************************
73  Definitions for all names.
74 ***********************************************************************/
75
76 static char *smb_myname;
77 static char *smb_myworkgroup;
78 static char *smb_scope;
79 static int smb_num_netbios_names;
80 static char **smb_my_netbios_names;
81
82 /***********************************************************************
83  Allocate and set myname. Ensure upper case.
84 ***********************************************************************/
85
86 bool set_global_myname(const char *myname)
87 {
88         SAFE_FREE(smb_myname);
89         smb_myname = SMB_STRDUP(myname);
90         if (!smb_myname)
91                 return False;
92         strupper_m(smb_myname);
93         return True;
94 }
95
96 const char *global_myname(void)
97 {
98         return smb_myname;
99 }
100
101 /***********************************************************************
102  Allocate and set myworkgroup. Ensure upper case.
103 ***********************************************************************/
104
105 bool set_global_myworkgroup(const char *myworkgroup)
106 {
107         SAFE_FREE(smb_myworkgroup);
108         smb_myworkgroup = SMB_STRDUP(myworkgroup);
109         if (!smb_myworkgroup)
110                 return False;
111         strupper_m(smb_myworkgroup);
112         return True;
113 }
114
115 const char *lp_workgroup(void)
116 {
117         return smb_myworkgroup;
118 }
119
120 /***********************************************************************
121  Allocate and set scope. Ensure upper case.
122 ***********************************************************************/
123
124 bool set_global_scope(const char *scope)
125 {
126         SAFE_FREE(smb_scope);
127         smb_scope = SMB_STRDUP(scope);
128         if (!smb_scope)
129                 return False;
130         strupper_m(smb_scope);
131         return True;
132 }
133
134 /*********************************************************************
135  Ensure scope is never null string.
136 *********************************************************************/
137
138 const char *global_scope(void)
139 {
140         if (!smb_scope)
141                 set_global_scope("");
142         return smb_scope;
143 }
144
145 static void free_netbios_names_array(void)
146 {
147         int i;
148
149         for (i = 0; i < smb_num_netbios_names; i++)
150                 SAFE_FREE(smb_my_netbios_names[i]);
151
152         SAFE_FREE(smb_my_netbios_names);
153         smb_num_netbios_names = 0;
154 }
155
156 static bool allocate_my_netbios_names_array(size_t number)
157 {
158         free_netbios_names_array();
159
160         smb_num_netbios_names = number + 1;
161         smb_my_netbios_names = SMB_MALLOC_ARRAY( char *, smb_num_netbios_names );
162
163         if (!smb_my_netbios_names)
164                 return False;
165
166         memset(smb_my_netbios_names, '\0', sizeof(char *) * smb_num_netbios_names);
167         return True;
168 }
169
170 static bool set_my_netbios_names(const char *name, int i)
171 {
172         SAFE_FREE(smb_my_netbios_names[i]);
173
174         smb_my_netbios_names[i] = SMB_STRDUP(name);
175         if (!smb_my_netbios_names[i])
176                 return False;
177         strupper_m(smb_my_netbios_names[i]);
178         return True;
179 }
180
181 /***********************************************************************
182  Free memory allocated to global objects
183 ***********************************************************************/
184
185 void gfree_names(void)
186 {
187         SAFE_FREE( smb_myname );
188         SAFE_FREE( smb_myworkgroup );
189         SAFE_FREE( smb_scope );
190         free_netbios_names_array();
191         free_local_machine_name();
192 }
193
194 void gfree_all( void )
195 {
196         gfree_names();
197         gfree_loadparm();
198         gfree_case_tables();
199         gfree_charcnv();
200         gfree_interfaces();
201         gfree_debugsyms();
202 }
203
204 const char *my_netbios_names(int i)
205 {
206         return smb_my_netbios_names[i];
207 }
208
209 bool set_netbios_aliases(const char **str_array)
210 {
211         size_t namecount;
212
213         /* Work out the max number of netbios aliases that we have */
214         for( namecount=0; str_array && (str_array[namecount] != NULL); namecount++ )
215                 ;
216
217         if ( global_myname() && *global_myname())
218                 namecount++;
219
220         /* Allocate space for the netbios aliases */
221         if (!allocate_my_netbios_names_array(namecount))
222                 return False;
223
224         /* Use the global_myname string first */
225         namecount=0;
226         if ( global_myname() && *global_myname()) {
227                 set_my_netbios_names( global_myname(), namecount );
228                 namecount++;
229         }
230
231         if (str_array) {
232                 size_t i;
233                 for ( i = 0; str_array[i] != NULL; i++) {
234                         size_t n;
235                         bool duplicate = False;
236
237                         /* Look for duplicates */
238                         for( n=0; n<namecount; n++ ) {
239                                 if( strequal( str_array[i], my_netbios_names(n) ) ) {
240                                         duplicate = True;
241                                         break;
242                                 }
243                         }
244                         if (!duplicate) {
245                                 if (!set_my_netbios_names(str_array[i], namecount))
246                                         return False;
247                                 namecount++;
248                         }
249                 }
250         }
251         return True;
252 }
253
254 /****************************************************************************
255   Common name initialization code.
256 ****************************************************************************/
257
258 bool init_names(void)
259 {
260         int n;
261
262         if (global_myname() == NULL || *global_myname() == '\0') {
263                 if (!set_global_myname(myhostname())) {
264                         DEBUG( 0, ( "init_structs: malloc fail.\n" ) );
265                         return False;
266                 }
267         }
268
269         if (!set_netbios_aliases(lp_netbios_aliases())) {
270                 DEBUG( 0, ( "init_structs: malloc fail.\n" ) );
271                 return False;
272         }
273
274         set_local_machine_name(global_myname(),false);
275
276         DEBUG( 5, ("Netbios name list:-\n") );
277         for( n=0; my_netbios_names(n); n++ ) {
278                 DEBUGADD( 5, ("my_netbios_names[%d]=\"%s\"\n",
279                                         n, my_netbios_names(n) ) );
280         }
281
282         return( True );
283 }
284
285 /**************************************************************************n
286   Code to cope with username/password auth options from the commandline.
287   Used mainly in client tools.
288 ****************************************************************************/
289
290 struct user_auth_info *user_auth_info_init(TALLOC_CTX *mem_ctx)
291 {
292         struct user_auth_info *result;
293
294         result = TALLOC_ZERO_P(mem_ctx, struct user_auth_info);
295         if (result == NULL) {
296                 return NULL;
297         }
298
299         result->signing_state = Undefined;
300         return result;
301 }
302
303 const char *get_cmdline_auth_info_username(const struct user_auth_info *auth_info)
304 {
305         if (!auth_info->username) {
306                 return "";
307         }
308         return auth_info->username;
309 }
310
311 void set_cmdline_auth_info_username(struct user_auth_info *auth_info,
312                                     const char *username)
313 {
314         TALLOC_FREE(auth_info->username);
315         auth_info->username = talloc_strdup(auth_info, username);
316         if (!auth_info->username) {
317                 exit(ENOMEM);
318         }
319 }
320
321 const char *get_cmdline_auth_info_domain(const struct user_auth_info *auth_info)
322 {
323         if (!auth_info->domain) {
324                 return "";
325         }
326         return auth_info->domain;
327 }
328
329 void set_cmdline_auth_info_domain(struct user_auth_info *auth_info,
330                                   const char *domain)
331 {
332         TALLOC_FREE(auth_info->domain);
333         auth_info->domain = talloc_strdup(auth_info, domain);
334         if (!auth_info->domain) {
335                 exit(ENOMEM);
336         }
337 }
338
339 const char *get_cmdline_auth_info_password(const struct user_auth_info *auth_info)
340 {
341         if (!auth_info->password) {
342                 return "";
343         }
344         return auth_info->password;
345 }
346
347 void set_cmdline_auth_info_password(struct user_auth_info *auth_info,
348                                     const char *password)
349 {
350         TALLOC_FREE(auth_info->password);
351         if (password == NULL) {
352                 password = "";
353         }
354         auth_info->password = talloc_strdup(auth_info, password);
355         if (!auth_info->password) {
356                 exit(ENOMEM);
357         }
358         auth_info->got_pass = true;
359 }
360
361 bool set_cmdline_auth_info_signing_state(struct user_auth_info *auth_info,
362                                          const char *arg)
363 {
364         auth_info->signing_state = -1;
365         if (strequal(arg, "off") || strequal(arg, "no") ||
366                         strequal(arg, "false")) {
367                 auth_info->signing_state = false;
368         } else if (strequal(arg, "on") || strequal(arg, "yes") ||
369                         strequal(arg, "true") || strequal(arg, "auto")) {
370                 auth_info->signing_state = true;
371         } else if (strequal(arg, "force") || strequal(arg, "required") ||
372                         strequal(arg, "forced")) {
373                 auth_info->signing_state = Required;
374         } else {
375                 return false;
376         }
377         return true;
378 }
379
380 int get_cmdline_auth_info_signing_state(const struct user_auth_info *auth_info)
381 {
382         return auth_info->signing_state;
383 }
384
385 void set_cmdline_auth_info_use_kerberos(struct user_auth_info *auth_info,
386                                         bool b)
387 {
388         auth_info->use_kerberos = b;
389 }
390
391 bool get_cmdline_auth_info_use_kerberos(const struct user_auth_info *auth_info)
392 {
393         return auth_info->use_kerberos;
394 }
395
396 void set_cmdline_auth_info_fallback_after_kerberos(struct user_auth_info *auth_info,
397                                         bool b)
398 {
399         auth_info->fallback_after_kerberos = b;
400 }
401
402 bool get_cmdline_auth_info_fallback_after_kerberos(const struct user_auth_info *auth_info)
403 {
404         return auth_info->fallback_after_kerberos;
405 }
406
407 /* This should only be used by lib/popt_common.c JRA */
408 void set_cmdline_auth_info_use_krb5_ticket(struct user_auth_info *auth_info)
409 {
410         auth_info->use_kerberos = true;
411         auth_info->got_pass = true;
412 }
413
414 /* This should only be used by lib/popt_common.c JRA */
415 void set_cmdline_auth_info_smb_encrypt(struct user_auth_info *auth_info)
416 {
417         auth_info->smb_encrypt = true;
418 }
419
420 void set_cmdline_auth_info_use_machine_account(struct user_auth_info *auth_info)
421 {
422         auth_info->use_machine_account = true;
423 }
424
425 bool get_cmdline_auth_info_got_pass(const struct user_auth_info *auth_info)
426 {
427         return auth_info->got_pass;
428 }
429
430 bool get_cmdline_auth_info_smb_encrypt(const struct user_auth_info *auth_info)
431 {
432         return auth_info->smb_encrypt;
433 }
434
435 bool get_cmdline_auth_info_use_machine_account(const struct user_auth_info *auth_info)
436 {
437         return auth_info->use_machine_account;
438 }
439
440 struct user_auth_info *get_cmdline_auth_info_copy(TALLOC_CTX *mem_ctx,
441                                                   const struct user_auth_info *src)
442 {
443         struct user_auth_info *result;
444
445         result = user_auth_info_init(mem_ctx);
446         if (result == NULL) {
447                 return NULL;
448         }
449
450         *result = *src;
451
452         result->username = talloc_strdup(
453                 result, get_cmdline_auth_info_username(src));
454         result->password = talloc_strdup(
455                 result, get_cmdline_auth_info_password(src));
456         if ((result->username == NULL) || (result->password == NULL)) {
457                 TALLOC_FREE(result);
458                 return NULL;
459         }
460
461         return result;
462 }
463
464 bool set_cmdline_auth_info_machine_account_creds(struct user_auth_info *auth_info)
465 {
466         char *pass = NULL;
467         char *account = NULL;
468
469         if (!get_cmdline_auth_info_use_machine_account(auth_info)) {
470                 return false;
471         }
472
473         if (!secrets_init()) {
474                 d_printf("ERROR: Unable to open secrets database\n");
475                 return false;
476         }
477
478         if (asprintf(&account, "%s$@%s", global_myname(), lp_realm()) < 0) {
479                 return false;
480         }
481
482         pass = secrets_fetch_machine_password(lp_workgroup(), NULL, NULL);
483         if (!pass) {
484                 d_printf("ERROR: Unable to fetch machine password for "
485                         "%s in domain %s\n",
486                         account, lp_workgroup());
487                 SAFE_FREE(account);
488                 return false;
489         }
490
491         set_cmdline_auth_info_username(auth_info, account);
492         set_cmdline_auth_info_password(auth_info, pass);
493
494         SAFE_FREE(account);
495         SAFE_FREE(pass);
496
497         return true;
498 }
499
500 /****************************************************************************
501  Ensure we have a password if one not given.
502 ****************************************************************************/
503
504 void set_cmdline_auth_info_getpass(struct user_auth_info *auth_info)
505 {
506         char *label = NULL;
507         char *pass;
508         TALLOC_CTX *frame;
509
510         if (get_cmdline_auth_info_got_pass(auth_info) ||
511                         get_cmdline_auth_info_use_kerberos(auth_info)) {
512                 /* Already got one... */
513                 return;
514         }
515
516         frame = talloc_stackframe();
517         label = talloc_asprintf(frame, "Enter %s's password: ",
518                         get_cmdline_auth_info_username(auth_info));
519         pass = getpass(label);
520         if (pass) {
521                 set_cmdline_auth_info_password(auth_info, pass);
522         }
523         TALLOC_FREE(frame);
524 }
525
526 /*******************************************************************
527  Check if a file exists - call vfs_file_exist for samba files.
528 ********************************************************************/
529
530 bool file_exist_stat(const char *fname,SMB_STRUCT_STAT *sbuf,
531                      bool fake_dir_create_times)
532 {
533         SMB_STRUCT_STAT st;
534         if (!sbuf)
535                 sbuf = &st;
536
537         if (sys_stat(fname, sbuf, fake_dir_create_times) != 0)
538                 return(False);
539
540         return((S_ISREG(sbuf->st_ex_mode)) || (S_ISFIFO(sbuf->st_ex_mode)));
541 }
542
543 /*******************************************************************
544  Check if a unix domain socket exists - call vfs_file_exist for samba files.
545 ********************************************************************/
546
547 bool socket_exist(const char *fname)
548 {
549         SMB_STRUCT_STAT st;
550         if (sys_stat(fname, &st, false) != 0)
551                 return(False);
552
553         return S_ISSOCK(st.st_ex_mode);
554 }
555
556 /*******************************************************************
557  Returns the size in bytes of the named given the stat struct.
558 ********************************************************************/
559
560 uint64_t get_file_size_stat(const SMB_STRUCT_STAT *sbuf)
561 {
562         return sbuf->st_ex_size;
563 }
564
565 /*******************************************************************
566  Returns the size in bytes of the named file.
567 ********************************************************************/
568
569 SMB_OFF_T get_file_size(char *file_name)
570 {
571         SMB_STRUCT_STAT buf;
572         buf.st_ex_size = 0;
573         if (sys_stat(file_name, &buf, false) != 0)
574                 return (SMB_OFF_T)-1;
575         return get_file_size_stat(&buf);
576 }
577
578 /*******************************************************************
579  Return a string representing an attribute for a file.
580 ********************************************************************/
581
582 char *attrib_string(uint16 mode)
583 {
584         fstring attrstr;
585
586         attrstr[0] = 0;
587
588         if (mode & aVOLID) fstrcat(attrstr,"V");
589         if (mode & aDIR) fstrcat(attrstr,"D");
590         if (mode & aARCH) fstrcat(attrstr,"A");
591         if (mode & aHIDDEN) fstrcat(attrstr,"H");
592         if (mode & aSYSTEM) fstrcat(attrstr,"S");
593         if (mode & aRONLY) fstrcat(attrstr,"R");          
594
595         return talloc_strdup(talloc_tos(), attrstr);
596 }
597
598 /*******************************************************************
599  Show a smb message structure.
600 ********************************************************************/
601
602 void show_msg(char *buf)
603 {
604         int i;
605         int bcc=0;
606
607         if (!DEBUGLVL(5))
608                 return;
609
610         DEBUG(5,("size=%d\nsmb_com=0x%x\nsmb_rcls=%d\nsmb_reh=%d\nsmb_err=%d\nsmb_flg=%d\nsmb_flg2=%d\n",
611                         smb_len(buf),
612                         (int)CVAL(buf,smb_com),
613                         (int)CVAL(buf,smb_rcls),
614                         (int)CVAL(buf,smb_reh),
615                         (int)SVAL(buf,smb_err),
616                         (int)CVAL(buf,smb_flg),
617                         (int)SVAL(buf,smb_flg2)));
618         DEBUGADD(5,("smb_tid=%d\nsmb_pid=%d\nsmb_uid=%d\nsmb_mid=%d\n",
619                         (int)SVAL(buf,smb_tid),
620                         (int)SVAL(buf,smb_pid),
621                         (int)SVAL(buf,smb_uid),
622                         (int)SVAL(buf,smb_mid)));
623         DEBUGADD(5,("smt_wct=%d\n",(int)CVAL(buf,smb_wct)));
624
625         for (i=0;i<(int)CVAL(buf,smb_wct);i++)
626                 DEBUGADD(5,("smb_vwv[%2d]=%5d (0x%X)\n",i,
627                         SVAL(buf,smb_vwv+2*i),SVAL(buf,smb_vwv+2*i)));
628
629         bcc = (int)SVAL(buf,smb_vwv+2*(CVAL(buf,smb_wct)));
630
631         DEBUGADD(5,("smb_bcc=%d\n",bcc));
632
633         if (DEBUGLEVEL < 10)
634                 return;
635
636         if (DEBUGLEVEL < 50)
637                 bcc = MIN(bcc, 512);
638
639         dump_data(10, (uint8 *)smb_buf(buf), bcc);      
640 }
641
642 /*******************************************************************
643  Set the length and marker of an encrypted smb packet.
644 ********************************************************************/
645
646 void smb_set_enclen(char *buf,int len,uint16 enc_ctx_num)
647 {
648         _smb_setlen(buf,len);
649
650         SCVAL(buf,4,0xFF);
651         SCVAL(buf,5,'E');
652         SSVAL(buf,6,enc_ctx_num);
653 }
654
655 /*******************************************************************
656  Set the length and marker of an smb packet.
657 ********************************************************************/
658
659 void smb_setlen(char *buf,int len)
660 {
661         _smb_setlen(buf,len);
662
663         SCVAL(buf,4,0xFF);
664         SCVAL(buf,5,'S');
665         SCVAL(buf,6,'M');
666         SCVAL(buf,7,'B');
667 }
668
669 /*******************************************************************
670  Setup only the byte count for a smb message.
671 ********************************************************************/
672
673 int set_message_bcc(char *buf,int num_bytes)
674 {
675         int num_words = CVAL(buf,smb_wct);
676         SSVAL(buf,smb_vwv + num_words*SIZEOFWORD,num_bytes);
677         _smb_setlen(buf,smb_size + num_words*2 + num_bytes - 4);
678         return (smb_size + num_words*2 + num_bytes);
679 }
680
681 /*******************************************************************
682  Add a data blob to the end of a smb_buf, adjusting bcc and smb_len.
683  Return the bytes added
684 ********************************************************************/
685
686 ssize_t message_push_blob(uint8 **outbuf, DATA_BLOB blob)
687 {
688         size_t newlen = smb_len(*outbuf) + 4 + blob.length;
689         uint8 *tmp;
690
691         if (!(tmp = TALLOC_REALLOC_ARRAY(NULL, *outbuf, uint8, newlen))) {
692                 DEBUG(0, ("talloc failed\n"));
693                 return -1;
694         }
695         *outbuf = tmp;
696
697         memcpy(tmp + smb_len(tmp) + 4, blob.data, blob.length);
698         set_message_bcc((char *)tmp, smb_buflen(tmp) + blob.length);
699         return blob.length;
700 }
701
702 /*******************************************************************
703  Reduce a file name, removing .. elements.
704 ********************************************************************/
705
706 static char *dos_clean_name(TALLOC_CTX *ctx, const char *s)
707 {
708         char *p = NULL;
709         char *str = NULL;
710
711         DEBUG(3,("dos_clean_name [%s]\n",s));
712
713         /* remove any double slashes */
714         str = talloc_all_string_sub(ctx, s, "\\\\", "\\");
715         if (!str) {
716                 return NULL;
717         }
718
719         /* Remove leading .\\ characters */
720         if(strncmp(str, ".\\", 2) == 0) {
721                 trim_string(str, ".\\", NULL);
722                 if(*str == 0) {
723                         str = talloc_strdup(ctx, ".\\");
724                         if (!str) {
725                                 return NULL;
726                         }
727                 }
728         }
729
730         while ((p = strstr_m(str,"\\..\\")) != NULL) {
731                 char *s1;
732
733                 *p = 0;
734                 s1 = p+3;
735
736                 if ((p=strrchr_m(str,'\\')) != NULL) {
737                         *p = 0;
738                 } else {
739                         *str = 0;
740                 }
741                 str = talloc_asprintf(ctx,
742                                 "%s%s",
743                                 str,
744                                 s1);
745                 if (!str) {
746                         return NULL;
747                 }
748         }
749
750         trim_string(str,NULL,"\\..");
751         return talloc_all_string_sub(ctx, str, "\\.\\", "\\");
752 }
753
754 /*******************************************************************
755  Reduce a file name, removing .. elements.
756 ********************************************************************/
757
758 char *unix_clean_name(TALLOC_CTX *ctx, const char *s)
759 {
760         char *p = NULL;
761         char *str = NULL;
762
763         DEBUG(3,("unix_clean_name [%s]\n",s));
764
765         /* remove any double slashes */
766         str = talloc_all_string_sub(ctx, s, "//","/");
767         if (!str) {
768                 return NULL;
769         }
770
771         /* Remove leading ./ characters */
772         if(strncmp(str, "./", 2) == 0) {
773                 trim_string(str, "./", NULL);
774                 if(*str == 0) {
775                         str = talloc_strdup(ctx, "./");
776                         if (!str) {
777                                 return NULL;
778                         }
779                 }
780         }
781
782         while ((p = strstr_m(str,"/../")) != NULL) {
783                 char *s1;
784
785                 *p = 0;
786                 s1 = p+3;
787
788                 if ((p=strrchr_m(str,'/')) != NULL) {
789                         *p = 0;
790                 } else {
791                         *str = 0;
792                 }
793                 str = talloc_asprintf(ctx,
794                                 "%s%s",
795                                 str,
796                                 s1);
797                 if (!str) {
798                         return NULL;
799                 }
800         }
801
802         trim_string(str,NULL,"/..");
803         return talloc_all_string_sub(ctx, str, "/./", "/");
804 }
805
806 char *clean_name(TALLOC_CTX *ctx, const char *s)
807 {
808         char *str = dos_clean_name(ctx, s);
809         if (!str) {
810                 return NULL;
811         }
812         return unix_clean_name(ctx, str);
813 }
814
815 /*******************************************************************
816  Write data into an fd at a given offset. Ignore seek errors.
817 ********************************************************************/
818
819 ssize_t write_data_at_offset(int fd, const char *buffer, size_t N, SMB_OFF_T pos)
820 {
821         size_t total=0;
822         ssize_t ret;
823
824         if (pos == (SMB_OFF_T)-1) {
825                 return write_data(fd, buffer, N);
826         }
827 #if defined(HAVE_PWRITE) || defined(HAVE_PRWITE64)
828         while (total < N) {
829                 ret = sys_pwrite(fd,buffer + total,N - total, pos);
830                 if (ret == -1 && errno == ESPIPE) {
831                         return write_data(fd, buffer + total,N - total);
832                 }
833                 if (ret == -1) {
834                         DEBUG(0,("write_data_at_offset: write failure. Error = %s\n", strerror(errno) ));
835                         return -1;
836                 }
837                 if (ret == 0) {
838                         return total;
839                 }
840                 total += ret;
841                 pos += ret;
842         }
843         return (ssize_t)total;
844 #else
845         /* Use lseek and write_data. */
846         if (sys_lseek(fd, pos, SEEK_SET) == -1) {
847                 if (errno != ESPIPE) {
848                         return -1;
849                 }
850         }
851         return write_data(fd, buffer, N);
852 #endif
853 }
854
855 /*******************************************************************
856  Sleep for a specified number of milliseconds.
857 ********************************************************************/
858
859 void smb_msleep(unsigned int t)
860 {
861 #if defined(HAVE_NANOSLEEP)
862         struct timespec tval;
863         int ret;
864
865         tval.tv_sec = t/1000;
866         tval.tv_nsec = 1000000*(t%1000);
867
868         do {
869                 errno = 0;
870                 ret = nanosleep(&tval, &tval);
871         } while (ret < 0 && errno == EINTR && (tval.tv_sec > 0 || tval.tv_nsec > 0));
872 #else
873         unsigned int tdiff=0;
874         struct timeval tval,t1,t2;  
875         fd_set fds;
876
877         GetTimeOfDay(&t1);
878         t2 = t1;
879
880         while (tdiff < t) {
881                 tval.tv_sec = (t-tdiff)/1000;
882                 tval.tv_usec = 1000*((t-tdiff)%1000);
883
884                 /* Never wait for more than 1 sec. */
885                 if (tval.tv_sec > 1) {
886                         tval.tv_sec = 1; 
887                         tval.tv_usec = 0;
888                 }
889
890                 FD_ZERO(&fds);
891                 errno = 0;
892                 sys_select_intr(0,&fds,NULL,NULL,&tval);
893
894                 GetTimeOfDay(&t2);
895                 if (t2.tv_sec < t1.tv_sec) {
896                         /* Someone adjusted time... */
897                         t1 = t2;
898                 }
899
900                 tdiff = TvalDiff(&t1,&t2);
901         }
902 #endif
903 }
904
905 NTSTATUS reinit_after_fork(struct messaging_context *msg_ctx,
906                        struct event_context *ev_ctx,
907                        bool parent_longlived)
908 {
909         NTSTATUS status = NT_STATUS_OK;
910
911         /* Reset the state of the random
912          * number generation system, so
913          * children do not get the same random
914          * numbers as each other */
915         set_need_random_reseed();
916
917         /* tdb needs special fork handling */
918         if (tdb_reopen_all(parent_longlived ? 1 : 0) == -1) {
919                 DEBUG(0,("tdb_reopen_all failed.\n"));
920                 status = NT_STATUS_OPEN_FAILED;
921                 goto done;
922         }
923
924         if (ev_ctx) {
925                 event_context_reinit(ev_ctx);
926         }
927
928         if (msg_ctx) {
929                 /*
930                  * For clustering, we need to re-init our ctdbd connection after the
931                  * fork
932                  */
933                 status = messaging_reinit(msg_ctx);
934                 if (!NT_STATUS_IS_OK(status)) {
935                         DEBUG(0,("messaging_reinit() failed: %s\n",
936                                  nt_errstr(status)));
937                 }
938         }
939  done:
940         return status;
941 }
942
943 /****************************************************************************
944  Put up a yes/no prompt.
945 ****************************************************************************/
946
947 bool yesno(const char *p)
948 {
949         char ans[20];
950         printf("%s",p);
951
952         if (!fgets(ans,sizeof(ans)-1,stdin))
953                 return(False);
954
955         if (*ans == 'y' || *ans == 'Y')
956                 return(True);
957
958         return(False);
959 }
960
961 #if defined(PARANOID_MALLOC_CHECKER)
962
963 /****************************************************************************
964  Internal malloc wrapper. Externally visible.
965 ****************************************************************************/
966
967 void *malloc_(size_t size)
968 {
969         if (size == 0) {
970                 return NULL;
971         }
972 #undef malloc
973         return malloc(size);
974 #define malloc(s) __ERROR_DONT_USE_MALLOC_DIRECTLY
975 }
976
977 /****************************************************************************
978  Internal calloc wrapper. Not externally visible.
979 ****************************************************************************/
980
981 static void *calloc_(size_t count, size_t size)
982 {
983         if (size == 0 || count == 0) {
984                 return NULL;
985         }
986 #undef calloc
987         return calloc(count, size);
988 #define calloc(n,s) __ERROR_DONT_USE_CALLOC_DIRECTLY
989 }
990
991 /****************************************************************************
992  Internal realloc wrapper. Not externally visible.
993 ****************************************************************************/
994
995 static void *realloc_(void *ptr, size_t size)
996 {
997 #undef realloc
998         return realloc(ptr, size);
999 #define realloc(p,s) __ERROR_DONT_USE_RELLOC_DIRECTLY
1000 }
1001
1002 #endif /* PARANOID_MALLOC_CHECKER */
1003
1004 /****************************************************************************
1005  Type-safe memalign
1006 ****************************************************************************/
1007
1008 void *memalign_array(size_t el_size, size_t align, unsigned int count)
1009 {
1010         if (count >= MAX_ALLOC_SIZE/el_size) {
1011                 return NULL;
1012         }
1013
1014         return sys_memalign(align, el_size*count);
1015 }
1016
1017 /****************************************************************************
1018  Type-safe calloc.
1019 ****************************************************************************/
1020
1021 void *calloc_array(size_t size, size_t nmemb)
1022 {
1023         if (nmemb >= MAX_ALLOC_SIZE/size) {
1024                 return NULL;
1025         }
1026         if (size == 0 || nmemb == 0) {
1027                 return NULL;
1028         }
1029 #if defined(PARANOID_MALLOC_CHECKER)
1030         return calloc_(nmemb, size);
1031 #else
1032         return calloc(nmemb, size);
1033 #endif
1034 }
1035
1036 /****************************************************************************
1037  Expand a pointer to be a particular size.
1038  Note that this version of Realloc has an extra parameter that decides
1039  whether to free the passed in storage on allocation failure or if the
1040  new size is zero.
1041
1042  This is designed for use in the typical idiom of :
1043
1044  p = SMB_REALLOC(p, size)
1045  if (!p) {
1046     return error;
1047  }
1048
1049  and not to have to keep track of the old 'p' contents to free later, nor
1050  to worry if the size parameter was zero. In the case where NULL is returned
1051  we guarentee that p has been freed.
1052
1053  If free later semantics are desired, then pass 'free_old_on_error' as False which
1054  guarentees that the old contents are not freed on error, even if size == 0. To use
1055  this idiom use :
1056
1057  tmp = SMB_REALLOC_KEEP_OLD_ON_ERROR(p, size);
1058  if (!tmp) {
1059     SAFE_FREE(p);
1060     return error;
1061  } else {
1062     p = tmp;
1063  }
1064
1065  Changes were instigated by Coverity error checking. JRA.
1066 ****************************************************************************/
1067
1068 void *Realloc(void *p, size_t size, bool free_old_on_error)
1069 {
1070         void *ret=NULL;
1071
1072         if (size == 0) {
1073                 if (free_old_on_error) {
1074                         SAFE_FREE(p);
1075                 }
1076                 DEBUG(2,("Realloc asked for 0 bytes\n"));
1077                 return NULL;
1078         }
1079
1080 #if defined(PARANOID_MALLOC_CHECKER)
1081         if (!p) {
1082                 ret = (void *)malloc_(size);
1083         } else {
1084                 ret = (void *)realloc_(p,size);
1085         }
1086 #else
1087         if (!p) {
1088                 ret = (void *)malloc(size);
1089         } else {
1090                 ret = (void *)realloc(p,size);
1091         }
1092 #endif
1093
1094         if (!ret) {
1095                 if (free_old_on_error && p) {
1096                         SAFE_FREE(p);
1097                 }
1098                 DEBUG(0,("Memory allocation error: failed to expand to %d bytes\n",(int)size));
1099         }
1100
1101         return(ret);
1102 }
1103
1104 /****************************************************************************
1105  (Hopefully) efficient array append.
1106 ****************************************************************************/
1107
1108 void add_to_large_array(TALLOC_CTX *mem_ctx, size_t element_size,
1109                         void *element, void *_array, uint32 *num_elements,
1110                         ssize_t *array_size)
1111 {
1112         void **array = (void **)_array;
1113
1114         if (*array_size < 0) {
1115                 return;
1116         }
1117
1118         if (*array == NULL) {
1119                 if (*array_size == 0) {
1120                         *array_size = 128;
1121                 }
1122
1123                 if (*array_size >= MAX_ALLOC_SIZE/element_size) {
1124                         goto error;
1125                 }
1126
1127                 *array = TALLOC(mem_ctx, element_size * (*array_size));
1128                 if (*array == NULL) {
1129                         goto error;
1130                 }
1131         }
1132
1133         if (*num_elements == *array_size) {
1134                 *array_size *= 2;
1135
1136                 if (*array_size >= MAX_ALLOC_SIZE/element_size) {
1137                         goto error;
1138                 }
1139
1140                 *array = TALLOC_REALLOC(mem_ctx, *array,
1141                                         element_size * (*array_size));
1142
1143                 if (*array == NULL) {
1144                         goto error;
1145                 }
1146         }
1147
1148         memcpy((char *)(*array) + element_size*(*num_elements),
1149                element, element_size);
1150         *num_elements += 1;
1151
1152         return;
1153
1154  error:
1155         *num_elements = 0;
1156         *array_size = -1;
1157 }
1158
1159 /****************************************************************************
1160  Get my own domain name, or "" if we have none.
1161 ****************************************************************************/
1162
1163 char *get_mydnsdomname(TALLOC_CTX *ctx)
1164 {
1165         const char *domname;
1166         char *p;
1167
1168         domname = get_mydnsfullname();
1169         if (!domname) {
1170                 return NULL;
1171         }
1172
1173         p = strchr_m(domname, '.');
1174         if (p) {
1175                 p++;
1176                 return talloc_strdup(ctx, p);
1177         } else {
1178                 return talloc_strdup(ctx, "");
1179         }
1180 }
1181
1182 /****************************************************************************
1183  Interpret a protocol description string, with a default.
1184 ****************************************************************************/
1185
1186 int interpret_protocol(const char *str,int def)
1187 {
1188         if (strequal(str,"NT1"))
1189                 return(PROTOCOL_NT1);
1190         if (strequal(str,"LANMAN2"))
1191                 return(PROTOCOL_LANMAN2);
1192         if (strequal(str,"LANMAN1"))
1193                 return(PROTOCOL_LANMAN1);
1194         if (strequal(str,"CORE"))
1195                 return(PROTOCOL_CORE);
1196         if (strequal(str,"COREPLUS"))
1197                 return(PROTOCOL_COREPLUS);
1198         if (strequal(str,"CORE+"))
1199                 return(PROTOCOL_COREPLUS);
1200
1201         DEBUG(0,("Unrecognised protocol level %s\n",str));
1202
1203         return(def);
1204 }
1205
1206
1207 #if (defined(HAVE_NETGROUP) && defined(WITH_AUTOMOUNT))
1208 /******************************************************************
1209  Remove any mount options such as -rsize=2048,wsize=2048 etc.
1210  Based on a fix from <Thomas.Hepper@icem.de>.
1211  Returns a malloc'ed string.
1212 *******************************************************************/
1213
1214 static char *strip_mount_options(TALLOC_CTX *ctx, const char *str)
1215 {
1216         if (*str == '-') {
1217                 const char *p = str;
1218                 while(*p && !isspace(*p))
1219                         p++;
1220                 while(*p && isspace(*p))
1221                         p++;
1222                 if(*p) {
1223                         return talloc_strdup(ctx, p);
1224                 }
1225         }
1226         return NULL;
1227 }
1228
1229 /*******************************************************************
1230  Patch from jkf@soton.ac.uk
1231  Split Luke's automount_server into YP lookup and string splitter
1232  so can easily implement automount_path().
1233  Returns a malloc'ed string.
1234 *******************************************************************/
1235
1236 #ifdef WITH_NISPLUS_HOME
1237 char *automount_lookup(TALLOC_CTX *ctx, const char *user_name)
1238 {
1239         char *value = NULL;
1240
1241         char *nis_map = (char *)lp_nis_home_map_name();
1242
1243         char buffer[NIS_MAXATTRVAL + 1];
1244         nis_result *result;
1245         nis_object *object;
1246         entry_obj  *entry;
1247
1248         snprintf(buffer, sizeof(buffer), "[key=%s],%s", user_name, nis_map);
1249         DEBUG(5, ("NIS+ querystring: %s\n", buffer));
1250
1251         if (result = nis_list(buffer, FOLLOW_PATH|EXPAND_NAME|HARD_LOOKUP, NULL, NULL)) {
1252                 if (result->status != NIS_SUCCESS) {
1253                         DEBUG(3, ("NIS+ query failed: %s\n", nis_sperrno(result->status)));
1254                 } else {
1255                         object = result->objects.objects_val;
1256                         if (object->zo_data.zo_type == ENTRY_OBJ) {
1257                                 entry = &object->zo_data.objdata_u.en_data;
1258                                 DEBUG(5, ("NIS+ entry type: %s\n", entry->en_type));
1259                                 DEBUG(3, ("NIS+ result: %s\n", entry->en_cols.en_cols_val[1].ec_value.ec_value_val));
1260
1261                                 value = talloc_strdup(ctx,
1262                                                 entry->en_cols.en_cols_val[1].ec_value.ec_value_val);
1263                                 if (!value) {
1264                                         nis_freeresult(result);
1265                                         return NULL;
1266                                 }
1267                                 value = talloc_string_sub(ctx,
1268                                                 value,
1269                                                 "&",
1270                                                 user_name);
1271                         }
1272                 }
1273         }
1274         nis_freeresult(result);
1275
1276         if (value) {
1277                 value = strip_mount_options(ctx, value);
1278                 DEBUG(4, ("NIS+ Lookup: %s resulted in %s\n",
1279                                         user_name, value));
1280         }
1281         return value;
1282 }
1283 #else /* WITH_NISPLUS_HOME */
1284
1285 char *automount_lookup(TALLOC_CTX *ctx, const char *user_name)
1286 {
1287         char *value = NULL;
1288
1289         int nis_error;        /* returned by yp all functions */
1290         char *nis_result;     /* yp_match inits this */
1291         int nis_result_len;  /* and set this */
1292         char *nis_domain;     /* yp_get_default_domain inits this */
1293         char *nis_map = (char *)lp_nis_home_map_name();
1294
1295         if ((nis_error = yp_get_default_domain(&nis_domain)) != 0) {
1296                 DEBUG(3, ("YP Error: %s\n", yperr_string(nis_error)));
1297                 return NULL;
1298         }
1299
1300         DEBUG(5, ("NIS Domain: %s\n", nis_domain));
1301
1302         if ((nis_error = yp_match(nis_domain, nis_map, user_name,
1303                                         strlen(user_name), &nis_result,
1304                                         &nis_result_len)) == 0) {
1305                 value = talloc_strdup(ctx, nis_result);
1306                 if (!value) {
1307                         return NULL;
1308                 }
1309                 value = strip_mount_options(ctx, value);
1310         } else if(nis_error == YPERR_KEY) {
1311                 DEBUG(3, ("YP Key not found:  while looking up \"%s\" in map \"%s\"\n", 
1312                                 user_name, nis_map));
1313                 DEBUG(3, ("using defaults for server and home directory\n"));
1314         } else {
1315                 DEBUG(3, ("YP Error: \"%s\" while looking up \"%s\" in map \"%s\"\n", 
1316                                 yperr_string(nis_error), user_name, nis_map));
1317         }
1318
1319         if (value) {
1320                 DEBUG(4, ("YP Lookup: %s resulted in %s\n", user_name, value));
1321         }
1322         return value;
1323 }
1324 #endif /* WITH_NISPLUS_HOME */
1325 #endif
1326
1327 /****************************************************************************
1328  Check if a process exists. Does this work on all unixes?
1329 ****************************************************************************/
1330
1331 bool process_exists(const struct server_id pid)
1332 {
1333         if (procid_is_me(&pid)) {
1334                 return True;
1335         }
1336
1337         if (procid_is_local(&pid)) {
1338                 return (kill(pid.pid,0) == 0 || errno != ESRCH);
1339         }
1340
1341 #ifdef CLUSTER_SUPPORT
1342         return ctdbd_process_exists(messaging_ctdbd_connection(), pid.vnn,
1343                                     pid.pid);
1344 #else
1345         return False;
1346 #endif
1347 }
1348
1349 /*******************************************************************
1350  Convert a uid into a user name.
1351 ********************************************************************/
1352
1353 const char *uidtoname(uid_t uid)
1354 {
1355         TALLOC_CTX *ctx = talloc_tos();
1356         char *name = NULL;
1357         struct passwd *pass = NULL;
1358
1359         pass = getpwuid_alloc(ctx,uid);
1360         if (pass) {
1361                 name = talloc_strdup(ctx,pass->pw_name);
1362                 TALLOC_FREE(pass);
1363         } else {
1364                 name = talloc_asprintf(ctx,
1365                                 "%ld",
1366                                 (long int)uid);
1367         }
1368         return name;
1369 }
1370
1371 /*******************************************************************
1372  Convert a gid into a group name.
1373 ********************************************************************/
1374
1375 char *gidtoname(gid_t gid)
1376 {
1377         struct group *grp;
1378
1379         grp = getgrgid(gid);
1380         if (grp) {
1381                 return talloc_strdup(talloc_tos(), grp->gr_name);
1382         }
1383         else {
1384                 return talloc_asprintf(talloc_tos(),
1385                                         "%d",
1386                                         (int)gid);
1387         }
1388 }
1389
1390 /*******************************************************************
1391  Convert a user name into a uid.
1392 ********************************************************************/
1393
1394 uid_t nametouid(const char *name)
1395 {
1396         struct passwd *pass;
1397         char *p;
1398         uid_t u;
1399
1400         pass = getpwnam_alloc(talloc_autofree_context(), name);
1401         if (pass) {
1402                 u = pass->pw_uid;
1403                 TALLOC_FREE(pass);
1404                 return u;
1405         }
1406
1407         u = (uid_t)strtol(name, &p, 0);
1408         if ((p != name) && (*p == '\0'))
1409                 return u;
1410
1411         return (uid_t)-1;
1412 }
1413
1414 /*******************************************************************
1415  Convert a name to a gid_t if possible. Return -1 if not a group. 
1416 ********************************************************************/
1417
1418 gid_t nametogid(const char *name)
1419 {
1420         struct group *grp;
1421         char *p;
1422         gid_t g;
1423
1424         g = (gid_t)strtol(name, &p, 0);
1425         if ((p != name) && (*p == '\0'))
1426                 return g;
1427
1428         grp = sys_getgrnam(name);
1429         if (grp)
1430                 return(grp->gr_gid);
1431         return (gid_t)-1;
1432 }
1433
1434 /*******************************************************************
1435  Something really nasty happened - panic !
1436 ********************************************************************/
1437
1438 void smb_panic(const char *const why)
1439 {
1440         char *cmd;
1441         int result;
1442
1443 #ifdef DEVELOPER
1444         {
1445
1446                 if (global_clobber_region_function) {
1447                         DEBUG(0,("smb_panic: clobber_region() last called from [%s(%u)]\n",
1448                                          global_clobber_region_function,
1449                                          global_clobber_region_line));
1450                 } 
1451         }
1452 #endif
1453
1454         DEBUG(0,("PANIC (pid %llu): %s\n",
1455                     (unsigned long long)sys_getpid(), why));
1456         log_stack_trace();
1457
1458         cmd = lp_panic_action();
1459         if (cmd && *cmd) {
1460                 DEBUG(0, ("smb_panic(): calling panic action [%s]\n", cmd));
1461                 result = system(cmd);
1462
1463                 if (result == -1)
1464                         DEBUG(0, ("smb_panic(): fork failed in panic action: %s\n",
1465                                           strerror(errno)));
1466                 else
1467                         DEBUG(0, ("smb_panic(): action returned status %d\n",
1468                                           WEXITSTATUS(result)));
1469         }
1470
1471         dump_core();
1472 }
1473
1474 /*******************************************************************
1475  Print a backtrace of the stack to the debug log. This function
1476  DELIBERATELY LEAKS MEMORY. The expectation is that you should
1477  exit shortly after calling it.
1478 ********************************************************************/
1479
1480 #ifdef HAVE_LIBUNWIND_H
1481 #include <libunwind.h>
1482 #endif
1483
1484 #ifdef HAVE_EXECINFO_H
1485 #include <execinfo.h>
1486 #endif
1487
1488 #ifdef HAVE_LIBEXC_H
1489 #include <libexc.h>
1490 #endif
1491
1492 void log_stack_trace(void)
1493 {
1494 #ifdef HAVE_LIBUNWIND
1495         /* Try to use libunwind before any other technique since on ia64
1496          * libunwind correctly walks the stack in more circumstances than
1497          * backtrace.
1498          */ 
1499         unw_cursor_t cursor;
1500         unw_context_t uc;
1501         unsigned i = 0;
1502
1503         char procname[256];
1504         unw_word_t ip, sp, off;
1505
1506         procname[sizeof(procname) - 1] = '\0';
1507
1508         if (unw_getcontext(&uc) != 0) {
1509                 goto libunwind_failed;
1510         }
1511
1512         if (unw_init_local(&cursor, &uc) != 0) {
1513                 goto libunwind_failed;
1514         }
1515
1516         DEBUG(0, ("BACKTRACE:\n"));
1517
1518         do {
1519             ip = sp = 0;
1520             unw_get_reg(&cursor, UNW_REG_IP, &ip);
1521             unw_get_reg(&cursor, UNW_REG_SP, &sp);
1522
1523             switch (unw_get_proc_name(&cursor,
1524                         procname, sizeof(procname) - 1, &off) ) {
1525             case 0:
1526                     /* Name found. */
1527             case -UNW_ENOMEM:
1528                     /* Name truncated. */
1529                     DEBUGADD(0, (" #%u %s + %#llx [ip=%#llx] [sp=%#llx]\n",
1530                             i, procname, (long long)off,
1531                             (long long)ip, (long long) sp));
1532                     break;
1533             default:
1534             /* case -UNW_ENOINFO: */
1535             /* case -UNW_EUNSPEC: */
1536                     /* No symbol name found. */
1537                     DEBUGADD(0, (" #%u %s [ip=%#llx] [sp=%#llx]\n",
1538                             i, "<unknown symbol>",
1539                             (long long)ip, (long long) sp));
1540             }
1541             ++i;
1542         } while (unw_step(&cursor) > 0);
1543
1544         return;
1545
1546 libunwind_failed:
1547         DEBUG(0, ("unable to produce a stack trace with libunwind\n"));
1548
1549 #elif HAVE_BACKTRACE_SYMBOLS
1550         void *backtrace_stack[BACKTRACE_STACK_SIZE];
1551         size_t backtrace_size;
1552         char **backtrace_strings;
1553
1554         /* get the backtrace (stack frames) */
1555         backtrace_size = backtrace(backtrace_stack,BACKTRACE_STACK_SIZE);
1556         backtrace_strings = backtrace_symbols(backtrace_stack, backtrace_size);
1557
1558         DEBUG(0, ("BACKTRACE: %lu stack frames:\n", 
1559                   (unsigned long)backtrace_size));
1560
1561         if (backtrace_strings) {
1562                 int i;
1563
1564                 for (i = 0; i < backtrace_size; i++)
1565                         DEBUGADD(0, (" #%u %s\n", i, backtrace_strings[i]));
1566
1567                 /* Leak the backtrace_strings, rather than risk what free() might do */
1568         }
1569
1570 #elif HAVE_LIBEXC
1571
1572         /* The IRIX libexc library provides an API for unwinding the stack. See
1573          * libexc(3) for details. Apparantly trace_back_stack leaks memory, but
1574          * since we are about to abort anyway, it hardly matters.
1575          */
1576
1577 #define NAMESIZE 32 /* Arbitrary */
1578
1579         __uint64_t      addrs[BACKTRACE_STACK_SIZE];
1580         char *          names[BACKTRACE_STACK_SIZE];
1581         char            namebuf[BACKTRACE_STACK_SIZE * NAMESIZE];
1582
1583         int             i;
1584         int             levels;
1585
1586         ZERO_ARRAY(addrs);
1587         ZERO_ARRAY(names);
1588         ZERO_ARRAY(namebuf);
1589
1590         /* We need to be root so we can open our /proc entry to walk
1591          * our stack. It also helps when we want to dump core.
1592          */
1593         become_root();
1594
1595         for (i = 0; i < BACKTRACE_STACK_SIZE; i++) {
1596                 names[i] = namebuf + (i * NAMESIZE);
1597         }
1598
1599         levels = trace_back_stack(0, addrs, names,
1600                         BACKTRACE_STACK_SIZE, NAMESIZE - 1);
1601
1602         DEBUG(0, ("BACKTRACE: %d stack frames:\n", levels));
1603         for (i = 0; i < levels; i++) {
1604                 DEBUGADD(0, (" #%d 0x%llx %s\n", i, addrs[i], names[i]));
1605         }
1606 #undef NAMESIZE
1607
1608 #else
1609         DEBUG(0, ("unable to produce a stack trace on this platform\n"));
1610 #endif
1611 }
1612
1613 /*******************************************************************
1614   A readdir wrapper which just returns the file name.
1615  ********************************************************************/
1616
1617 const char *readdirname(SMB_STRUCT_DIR *p)
1618 {
1619         SMB_STRUCT_DIRENT *ptr;
1620         char *dname;
1621
1622         if (!p)
1623                 return(NULL);
1624
1625         ptr = (SMB_STRUCT_DIRENT *)sys_readdir(p);
1626         if (!ptr)
1627                 return(NULL);
1628
1629         dname = ptr->d_name;
1630
1631 #ifdef NEXT2
1632         if (telldir(p) < 0)
1633                 return(NULL);
1634 #endif
1635
1636 #ifdef HAVE_BROKEN_READDIR_NAME
1637         /* using /usr/ucb/cc is BAD */
1638         dname = dname - 2;
1639 #endif
1640
1641         return talloc_strdup(talloc_tos(), dname);
1642 }
1643
1644 /*******************************************************************
1645  Utility function used to decide if the last component 
1646  of a path matches a (possibly wildcarded) entry in a namelist.
1647 ********************************************************************/
1648
1649 bool is_in_path(const char *name, name_compare_entry *namelist, bool case_sensitive)
1650 {
1651         const char *last_component;
1652
1653         /* if we have no list it's obviously not in the path */
1654         if((namelist == NULL ) || ((namelist != NULL) && (namelist[0].name == NULL))) {
1655                 return False;
1656         }
1657
1658         DEBUG(8, ("is_in_path: %s\n", name));
1659
1660         /* Get the last component of the unix name. */
1661         last_component = strrchr_m(name, '/');
1662         if (!last_component) {
1663                 last_component = name;
1664         } else {
1665                 last_component++; /* Go past '/' */
1666         }
1667
1668         for(; namelist->name != NULL; namelist++) {
1669                 if(namelist->is_wild) {
1670                         if (mask_match(last_component, namelist->name, case_sensitive)) {
1671                                 DEBUG(8,("is_in_path: mask match succeeded\n"));
1672                                 return True;
1673                         }
1674                 } else {
1675                         if((case_sensitive && (strcmp(last_component, namelist->name) == 0))||
1676                                                 (!case_sensitive && (StrCaseCmp(last_component, namelist->name) == 0))) {
1677                                 DEBUG(8,("is_in_path: match succeeded\n"));
1678                                 return True;
1679                         }
1680                 }
1681         }
1682         DEBUG(8,("is_in_path: match not found\n"));
1683         return False;
1684 }
1685
1686 /*******************************************************************
1687  Strip a '/' separated list into an array of 
1688  name_compare_enties structures suitable for 
1689  passing to is_in_path(). We do this for
1690  speed so we can pre-parse all the names in the list 
1691  and don't do it for each call to is_in_path().
1692  namelist is modified here and is assumed to be 
1693  a copy owned by the caller.
1694  We also check if the entry contains a wildcard to
1695  remove a potentially expensive call to mask_match
1696  if possible.
1697 ********************************************************************/
1698
1699 void set_namearray(name_compare_entry **ppname_array, const char *namelist)
1700 {
1701         char *name_end;
1702         char *nameptr = (char *)namelist;
1703         int num_entries = 0;
1704         int i;
1705
1706         (*ppname_array) = NULL;
1707
1708         if((nameptr == NULL ) || ((nameptr != NULL) && (*nameptr == '\0'))) 
1709                 return;
1710
1711         /* We need to make two passes over the string. The
1712                 first to count the number of elements, the second
1713                 to split it.
1714         */
1715
1716         while(*nameptr) {
1717                 if ( *nameptr == '/' ) {
1718                         /* cope with multiple (useless) /s) */
1719                         nameptr++;
1720                         continue;
1721                 }
1722                 /* anything left? */
1723                 if ( *nameptr == '\0' )
1724                         break;
1725
1726                 /* find the next '/' or consume remaining */
1727                 name_end = strchr_m(nameptr, '/');
1728                 if (name_end == NULL)
1729                         name_end = (char *)nameptr + strlen(nameptr);
1730
1731                 /* next segment please */
1732                 nameptr = name_end + 1;
1733                 num_entries++;
1734         }
1735
1736         if(num_entries == 0)
1737                 return;
1738
1739         if(( (*ppname_array) = SMB_MALLOC_ARRAY(name_compare_entry, num_entries + 1)) == NULL) {
1740                 DEBUG(0,("set_namearray: malloc fail\n"));
1741                 return;
1742         }
1743
1744         /* Now copy out the names */
1745         nameptr = (char *)namelist;
1746         i = 0;
1747         while(*nameptr) {
1748                 if ( *nameptr == '/' ) {
1749                         /* cope with multiple (useless) /s) */
1750                         nameptr++;
1751                         continue;
1752                 }
1753                 /* anything left? */
1754                 if ( *nameptr == '\0' )
1755                         break;
1756
1757                 /* find the next '/' or consume remaining */
1758                 name_end = strchr_m(nameptr, '/');
1759                 if (name_end)
1760                         *name_end = '\0';
1761                 else
1762                         name_end = nameptr + strlen(nameptr);
1763
1764                 (*ppname_array)[i].is_wild = ms_has_wild(nameptr);
1765                 if(((*ppname_array)[i].name = SMB_STRDUP(nameptr)) == NULL) {
1766                         DEBUG(0,("set_namearray: malloc fail (1)\n"));
1767                         return;
1768                 }
1769
1770                 /* next segment please */
1771                 nameptr = name_end + 1;
1772                 i++;
1773         }
1774
1775         (*ppname_array)[i].name = NULL;
1776
1777         return;
1778 }
1779
1780 /****************************************************************************
1781  Routine to free a namearray.
1782 ****************************************************************************/
1783
1784 void free_namearray(name_compare_entry *name_array)
1785 {
1786         int i;
1787
1788         if(name_array == NULL)
1789                 return;
1790
1791         for(i=0; name_array[i].name!=NULL; i++)
1792                 SAFE_FREE(name_array[i].name);
1793         SAFE_FREE(name_array);
1794 }
1795
1796 #undef DBGC_CLASS
1797 #define DBGC_CLASS DBGC_LOCKING
1798
1799 /****************************************************************************
1800  Simple routine to query existing file locks. Cruft in NFS and 64->32 bit mapping
1801  is dealt with in posix.c
1802  Returns True if we have information regarding this lock region (and returns
1803  F_UNLCK in *ptype if the region is unlocked). False if the call failed.
1804 ****************************************************************************/
1805
1806 bool fcntl_getlock(int fd, SMB_OFF_T *poffset, SMB_OFF_T *pcount, int *ptype, pid_t *ppid)
1807 {
1808         SMB_STRUCT_FLOCK lock;
1809         int ret;
1810
1811         DEBUG(8,("fcntl_getlock fd=%d offset=%.0f count=%.0f type=%d\n",
1812                     fd,(double)*poffset,(double)*pcount,*ptype));
1813
1814         lock.l_type = *ptype;
1815         lock.l_whence = SEEK_SET;
1816         lock.l_start = *poffset;
1817         lock.l_len = *pcount;
1818         lock.l_pid = 0;
1819
1820         ret = sys_fcntl_ptr(fd,SMB_F_GETLK,&lock);
1821
1822         if (ret == -1) {
1823                 int sav = errno;
1824                 DEBUG(3,("fcntl_getlock: lock request failed at offset %.0f count %.0f type %d (%s)\n",
1825                         (double)*poffset,(double)*pcount,*ptype,strerror(errno)));
1826                 errno = sav;
1827                 return False;
1828         }
1829
1830         *ptype = lock.l_type;
1831         *poffset = lock.l_start;
1832         *pcount = lock.l_len;
1833         *ppid = lock.l_pid;
1834
1835         DEBUG(3,("fcntl_getlock: fd %d is returned info %d pid %u\n",
1836                         fd, (int)lock.l_type, (unsigned int)lock.l_pid));
1837         return True;
1838 }
1839
1840 #undef DBGC_CLASS
1841 #define DBGC_CLASS DBGC_ALL
1842
1843 /*******************************************************************
1844  Is the name specified one of my netbios names.
1845  Returns true if it is equal, false otherwise.
1846 ********************************************************************/
1847
1848 bool is_myname(const char *s)
1849 {
1850         int n;
1851         bool ret = False;
1852
1853         for (n=0; my_netbios_names(n); n++) {
1854                 if (strequal(my_netbios_names(n), s)) {
1855                         ret=True;
1856                         break;
1857                 }
1858         }
1859         DEBUG(8, ("is_myname(\"%s\") returns %d\n", s, ret));
1860         return(ret);
1861 }
1862
1863 /*******************************************************************
1864  Is the name specified our workgroup/domain.
1865  Returns true if it is equal, false otherwise.
1866 ********************************************************************/
1867
1868 bool is_myworkgroup(const char *s)
1869 {
1870         bool ret = False;
1871
1872         if (strequal(s, lp_workgroup())) {
1873                 ret=True;
1874         }
1875
1876         DEBUG(8, ("is_myworkgroup(\"%s\") returns %d\n", s, ret));
1877         return(ret);
1878 }
1879
1880 /*******************************************************************
1881  we distinguish between 2K and XP by the "Native Lan Manager" string
1882    WinXP => "Windows 2002 5.1"
1883    WinXP 64bit => "Windows XP 5.2"
1884    Win2k => "Windows 2000 5.0"
1885    NT4   => "Windows NT 4.0"
1886    Win9x => "Windows 4.0"
1887  Windows 2003 doesn't set the native lan manager string but
1888  they do set the domain to "Windows 2003 5.2" (probably a bug).
1889 ********************************************************************/
1890
1891 void ra_lanman_string( const char *native_lanman )
1892 {
1893         if ( strcmp( native_lanman, "Windows 2002 5.1" ) == 0 )
1894                 set_remote_arch( RA_WINXP );
1895         else if ( strcmp( native_lanman, "Windows XP 5.2" ) == 0 )
1896                 set_remote_arch( RA_WINXP64 );
1897         else if ( strcmp( native_lanman, "Windows Server 2003 5.2" ) == 0 )
1898                 set_remote_arch( RA_WIN2K3 );
1899 }
1900
1901 static const char *remote_arch_str;
1902
1903 const char *get_remote_arch_str(void)
1904 {
1905         if (!remote_arch_str) {
1906                 return "UNKNOWN";
1907         }
1908         return remote_arch_str;
1909 }
1910
1911 /*******************************************************************
1912  Set the horrid remote_arch string based on an enum.
1913 ********************************************************************/
1914
1915 void set_remote_arch(enum remote_arch_types type)
1916 {
1917         ra_type = type;
1918         switch( type ) {
1919         case RA_WFWG:
1920                 remote_arch_str = "WfWg";
1921                 break;
1922         case RA_OS2:
1923                 remote_arch_str = "OS2";
1924                 break;
1925         case RA_WIN95:
1926                 remote_arch_str = "Win95";
1927                 break;
1928         case RA_WINNT:
1929                 remote_arch_str = "WinNT";
1930                 break;
1931         case RA_WIN2K:
1932                 remote_arch_str = "Win2K";
1933                 break;
1934         case RA_WINXP:
1935                 remote_arch_str = "WinXP";
1936                 break;
1937         case RA_WINXP64:
1938                 remote_arch_str = "WinXP64";
1939                 break;
1940         case RA_WIN2K3:
1941                 remote_arch_str = "Win2K3";
1942                 break;
1943         case RA_VISTA:
1944                 remote_arch_str = "Vista";
1945                 break;
1946         case RA_SAMBA:
1947                 remote_arch_str = "Samba";
1948                 break;
1949         case RA_CIFSFS:
1950                 remote_arch_str = "CIFSFS";
1951                 break;
1952         default:
1953                 ra_type = RA_UNKNOWN;
1954                 remote_arch_str = "UNKNOWN";
1955                 break;
1956         }
1957
1958         DEBUG(10,("set_remote_arch: Client arch is \'%s\'\n",
1959                                 remote_arch_str));
1960 }
1961
1962 /*******************************************************************
1963  Get the remote_arch type.
1964 ********************************************************************/
1965
1966 enum remote_arch_types get_remote_arch(void)
1967 {
1968         return ra_type;
1969 }
1970
1971 const char *tab_depth(int level, int depth)
1972 {
1973         if( CHECK_DEBUGLVL(level) ) {
1974                 dbgtext("%*s", depth*4, "");
1975         }
1976         return "";
1977 }
1978
1979 /*****************************************************************************
1980  Provide a checksum on a string
1981
1982  Input:  s - the null-terminated character string for which the checksum
1983              will be calculated.
1984
1985   Output: The checksum value calculated for s.
1986 *****************************************************************************/
1987
1988 int str_checksum(const char *s)
1989 {
1990         int res = 0;
1991         int c;
1992         int i=0;
1993
1994         while(*s) {
1995                 c = *s;
1996                 res ^= (c << (i % 15)) ^ (c >> (15-(i%15)));
1997                 s++;
1998                 i++;
1999         }
2000         return(res);
2001 }
2002
2003 /*****************************************************************
2004  Zero a memory area then free it. Used to catch bugs faster.
2005 *****************************************************************/  
2006
2007 void zero_free(void *p, size_t size)
2008 {
2009         memset(p, 0, size);
2010         SAFE_FREE(p);
2011 }
2012
2013 /*****************************************************************
2014  Set our open file limit to a requested max and return the limit.
2015 *****************************************************************/  
2016
2017 int set_maxfiles(int requested_max)
2018 {
2019 #if (defined(HAVE_GETRLIMIT) && defined(RLIMIT_NOFILE))
2020         struct rlimit rlp;
2021         int saved_current_limit;
2022
2023         if(getrlimit(RLIMIT_NOFILE, &rlp)) {
2024                 DEBUG(0,("set_maxfiles: getrlimit (1) for RLIMIT_NOFILE failed with error %s\n",
2025                         strerror(errno) ));
2026                 /* just guess... */
2027                 return requested_max;
2028         }
2029
2030         /* 
2031          * Set the fd limit to be real_max_open_files + MAX_OPEN_FUDGEFACTOR to
2032          * account for the extra fd we need 
2033          * as well as the log files and standard
2034          * handles etc. Save the limit we want to set in case
2035          * we are running on an OS that doesn't support this limit (AIX)
2036          * which always returns RLIM_INFINITY for rlp.rlim_max.
2037          */
2038
2039         /* Try raising the hard (max) limit to the requested amount. */
2040
2041 #if defined(RLIM_INFINITY)
2042         if (rlp.rlim_max != RLIM_INFINITY) {
2043                 int orig_max = rlp.rlim_max;
2044
2045                 if ( rlp.rlim_max < requested_max )
2046                         rlp.rlim_max = requested_max;
2047
2048                 /* This failing is not an error - many systems (Linux) don't
2049                         support our default request of 10,000 open files. JRA. */
2050
2051                 if(setrlimit(RLIMIT_NOFILE, &rlp)) {
2052                         DEBUG(3,("set_maxfiles: setrlimit for RLIMIT_NOFILE for %d max files failed with error %s\n", 
2053                                 (int)rlp.rlim_max, strerror(errno) ));
2054
2055                         /* Set failed - restore original value from get. */
2056                         rlp.rlim_max = orig_max;
2057                 }
2058         }
2059 #endif
2060
2061         /* Now try setting the soft (current) limit. */
2062
2063         saved_current_limit = rlp.rlim_cur = MIN(requested_max,rlp.rlim_max);
2064
2065         if(setrlimit(RLIMIT_NOFILE, &rlp)) {
2066                 DEBUG(0,("set_maxfiles: setrlimit for RLIMIT_NOFILE for %d files failed with error %s\n", 
2067                         (int)rlp.rlim_cur, strerror(errno) ));
2068                 /* just guess... */
2069                 return saved_current_limit;
2070         }
2071
2072         if(getrlimit(RLIMIT_NOFILE, &rlp)) {
2073                 DEBUG(0,("set_maxfiles: getrlimit (2) for RLIMIT_NOFILE failed with error %s\n",
2074                         strerror(errno) ));
2075                 /* just guess... */
2076                 return saved_current_limit;
2077     }
2078
2079 #if defined(RLIM_INFINITY)
2080         if(rlp.rlim_cur == RLIM_INFINITY)
2081                 return saved_current_limit;
2082 #endif
2083
2084         if((int)rlp.rlim_cur > saved_current_limit)
2085                 return saved_current_limit;
2086
2087         return rlp.rlim_cur;
2088 #else /* !defined(HAVE_GETRLIMIT) || !defined(RLIMIT_NOFILE) */
2089         /*
2090          * No way to know - just guess...
2091          */
2092         return requested_max;
2093 #endif
2094 }
2095
2096 /*****************************************************************
2097  malloc that aborts with smb_panic on fail or zero size.
2098  *****************************************************************/  
2099
2100 void *smb_xmalloc_array(size_t size, unsigned int count)
2101 {
2102         void *p;
2103         if (size == 0) {
2104                 smb_panic("smb_xmalloc_array: called with zero size");
2105         }
2106         if (count >= MAX_ALLOC_SIZE/size) {
2107                 smb_panic("smb_xmalloc_array: alloc size too large");
2108         }
2109         if ((p = SMB_MALLOC(size*count)) == NULL) {
2110                 DEBUG(0, ("smb_xmalloc_array failed to allocate %lu * %lu bytes\n",
2111                         (unsigned long)size, (unsigned long)count));
2112                 smb_panic("smb_xmalloc_array: malloc failed");
2113         }
2114         return p;
2115 }
2116
2117 /*
2118   vasprintf that aborts on malloc fail
2119 */
2120
2121  int smb_xvasprintf(char **ptr, const char *format, va_list ap)
2122 {
2123         int n;
2124         va_list ap2;
2125
2126         va_copy(ap2, ap);
2127
2128         n = vasprintf(ptr, format, ap2);
2129         va_end(ap2);
2130         if (n == -1 || ! *ptr) {
2131                 smb_panic("smb_xvasprintf: out of memory");
2132         }
2133         return n;
2134 }
2135
2136 /*****************************************************************
2137  Get local hostname and cache result.
2138 *****************************************************************/
2139
2140 char *myhostname(void)
2141 {
2142         static char *ret;
2143         if (ret == NULL) {
2144                 /* This is cached forever so
2145                  * use talloc_autofree_context() ctx. */
2146                 ret = get_myname(talloc_autofree_context());
2147         }
2148         return ret;
2149 }
2150
2151 /**
2152  * @brief Returns an absolute path to a file concatenating the provided
2153  * @a rootpath and @a basename
2154  *
2155  * @param name Filename, relative to @a rootpath
2156  *
2157  * @retval Pointer to a string containing the full path.
2158  **/
2159
2160 static char *xx_path(const char *name, const char *rootpath)
2161 {
2162         char *fname = NULL;
2163
2164         fname = talloc_strdup(talloc_tos(), rootpath);
2165         if (!fname) {
2166                 return NULL;
2167         }
2168         trim_string(fname,"","/");
2169
2170         if (!directory_exist(fname)) {
2171                 if (!mkdir(fname,0755))
2172                         DEBUG(1, ("Unable to create directory %s for file %s. "
2173                               "Error was %s\n", fname, name, strerror(errno)));
2174         }
2175
2176         return talloc_asprintf(talloc_tos(),
2177                                 "%s/%s",
2178                                 fname,
2179                                 name);
2180 }
2181
2182 /**
2183  * @brief Returns an absolute path to a file in the Samba lock directory.
2184  *
2185  * @param name File to find, relative to LOCKDIR.
2186  *
2187  * @retval Pointer to a talloc'ed string containing the full path.
2188  **/
2189
2190 char *lock_path(const char *name)
2191 {
2192         return xx_path(name, lp_lockdir());
2193 }
2194
2195 /**
2196  * @brief Returns an absolute path to a file in the Samba pid directory.
2197  *
2198  * @param name File to find, relative to PIDDIR.
2199  *
2200  * @retval Pointer to a talloc'ed string containing the full path.
2201  **/
2202
2203 char *pid_path(const char *name)
2204 {
2205         return xx_path(name, lp_piddir());
2206 }
2207
2208 /**
2209  * @brief Returns an absolute path to a file in the Samba lib directory.
2210  *
2211  * @param name File to find, relative to LIBDIR.
2212  *
2213  * @retval Pointer to a string containing the full path.
2214  **/
2215
2216 char *lib_path(const char *name)
2217 {
2218         return talloc_asprintf(talloc_tos(), "%s/%s", get_dyn_LIBDIR(), name);
2219 }
2220
2221 /**
2222  * @brief Returns an absolute path to a file in the Samba modules directory.
2223  *
2224  * @param name File to find, relative to MODULESDIR.
2225  *
2226  * @retval Pointer to a string containing the full path.
2227  **/
2228
2229 char *modules_path(const char *name)
2230 {
2231         return talloc_asprintf(talloc_tos(), "%s/%s", get_dyn_MODULESDIR(), name);
2232 }
2233
2234 /**
2235  * @brief Returns an absolute path to a file in the Samba data directory.
2236  *
2237  * @param name File to find, relative to CODEPAGEDIR.
2238  *
2239  * @retval Pointer to a talloc'ed string containing the full path.
2240  **/
2241
2242 char *data_path(const char *name)
2243 {
2244         return talloc_asprintf(talloc_tos(), "%s/%s", get_dyn_CODEPAGEDIR(), name);
2245 }
2246
2247 /**
2248  * @brief Returns an absolute path to a file in the Samba state directory.
2249  *
2250  * @param name File to find, relative to STATEDIR.
2251  *
2252  * @retval Pointer to a talloc'ed string containing the full path.
2253  **/
2254
2255 char *state_path(const char *name)
2256 {
2257         return xx_path(name, lp_statedir());
2258 }
2259
2260 /**
2261  * @brief Returns an absolute path to a file in the Samba cache directory.
2262  *
2263  * @param name File to find, relative to CACHEDIR.
2264  *
2265  * @retval Pointer to a talloc'ed string containing the full path.
2266  **/
2267
2268 char *cache_path(const char *name)
2269 {
2270         return xx_path(name, lp_cachedir());
2271 }
2272
2273 /**
2274  * @brief Returns the platform specific shared library extension.
2275  *
2276  * @retval Pointer to a const char * containing the extension.
2277  **/
2278
2279 const char *shlib_ext(void)
2280 {
2281         return get_dyn_SHLIBEXT();
2282 }
2283
2284 /*******************************************************************
2285  Given a filename - get its directory name
2286 ********************************************************************/
2287
2288 bool parent_dirname(TALLOC_CTX *mem_ctx, const char *dir, char **parent,
2289                     const char **name)
2290 {
2291         char *p;
2292         ptrdiff_t len;
2293
2294         p = strrchr_m(dir, '/'); /* Find final '/', if any */
2295
2296         if (p == NULL) {
2297                 if (!(*parent = talloc_strdup(mem_ctx, "."))) {
2298                         return False;
2299                 }
2300                 if (name) {
2301                         *name = dir;
2302                 }
2303                 return True;
2304         }
2305
2306         len = p-dir;
2307
2308         if (!(*parent = (char *)TALLOC_MEMDUP(mem_ctx, dir, len+1))) {
2309                 return False;
2310         }
2311         (*parent)[len] = '\0';
2312
2313         if (name) {
2314                 *name = p+1;
2315         }
2316         return True;
2317 }
2318
2319 /*******************************************************************
2320  Determine if a pattern contains any Microsoft wildcard characters.
2321 *******************************************************************/
2322
2323 bool ms_has_wild(const char *s)
2324 {
2325         char c;
2326
2327         if (lp_posix_pathnames()) {
2328                 /* With posix pathnames no characters are wild. */
2329                 return False;
2330         }
2331
2332         while ((c = *s++)) {
2333                 switch (c) {
2334                 case '*':
2335                 case '?':
2336                 case '<':
2337                 case '>':
2338                 case '"':
2339                         return True;
2340                 }
2341         }
2342         return False;
2343 }
2344
2345 bool ms_has_wild_w(const smb_ucs2_t *s)
2346 {
2347         smb_ucs2_t c;
2348         if (!s) return False;
2349         while ((c = *s++)) {
2350                 switch (c) {
2351                 case UCS2_CHAR('*'):
2352                 case UCS2_CHAR('?'):
2353                 case UCS2_CHAR('<'):
2354                 case UCS2_CHAR('>'):
2355                 case UCS2_CHAR('"'):
2356                         return True;
2357                 }
2358         }
2359         return False;
2360 }
2361
2362 /*******************************************************************
2363  A wrapper that handles case sensitivity and the special handling
2364  of the ".." name.
2365 *******************************************************************/
2366
2367 bool mask_match(const char *string, const char *pattern, bool is_case_sensitive)
2368 {
2369         if (ISDOTDOT(string))
2370                 string = ".";
2371         if (ISDOT(pattern))
2372                 return False;
2373
2374         return ms_fnmatch(pattern, string, Protocol <= PROTOCOL_LANMAN2, is_case_sensitive) == 0;
2375 }
2376
2377 /*******************************************************************
2378  A wrapper that handles case sensitivity and the special handling
2379  of the ".." name. Varient that is only called by old search code which requires
2380  pattern translation.
2381 *******************************************************************/
2382
2383 bool mask_match_search(const char *string, const char *pattern, bool is_case_sensitive)
2384 {
2385         if (ISDOTDOT(string))
2386                 string = ".";
2387         if (ISDOT(pattern))
2388                 return False;
2389
2390         return ms_fnmatch(pattern, string, True, is_case_sensitive) == 0;
2391 }
2392
2393 /*******************************************************************
2394  A wrapper that handles a list of patters and calls mask_match()
2395  on each.  Returns True if any of the patterns match.
2396 *******************************************************************/
2397
2398 bool mask_match_list(const char *string, char **list, int listLen, bool is_case_sensitive)
2399 {
2400        while (listLen-- > 0) {
2401                if (mask_match(string, *list++, is_case_sensitive))
2402                        return True;
2403        }
2404        return False;
2405 }
2406
2407 /*********************************************************
2408  Recursive routine that is called by unix_wild_match.
2409 *********************************************************/
2410
2411 static bool unix_do_match(const char *regexp, const char *str)
2412 {
2413         const char *p;
2414
2415         for( p = regexp; *p && *str; ) {
2416
2417                 switch(*p) {
2418                         case '?':
2419                                 str++;
2420                                 p++;
2421                                 break;
2422
2423                         case '*':
2424
2425                                 /*
2426                                  * Look for a character matching 
2427                                  * the one after the '*'.
2428                                  */
2429                                 p++;
2430                                 if(!*p)
2431                                         return true; /* Automatic match */
2432                                 while(*str) {
2433
2434                                         while(*str && (*p != *str))
2435                                                 str++;
2436
2437                                         /*
2438                                          * Patch from weidel@multichart.de. In the case of the regexp
2439                                          * '*XX*' we want to ensure there are at least 2 'X' characters
2440                                          * in the string after the '*' for a match to be made.
2441                                          */
2442
2443                                         {
2444                                                 int matchcount=0;
2445
2446                                                 /*
2447                                                  * Eat all the characters that match, but count how many there were.
2448                                                  */
2449
2450                                                 while(*str && (*p == *str)) {
2451                                                         str++;
2452                                                         matchcount++;
2453                                                 }
2454
2455                                                 /*
2456                                                  * Now check that if the regexp had n identical characters that
2457                                                  * matchcount had at least that many matches.
2458                                                  */
2459
2460                                                 while ( *(p+1) && (*(p+1) == *p)) {
2461                                                         p++;
2462                                                         matchcount--;
2463                                                 }
2464
2465                                                 if ( matchcount <= 0 )
2466                                                         return false;
2467                                         }
2468
2469                                         str--; /* We've eaten the match char after the '*' */
2470
2471                                         if(unix_do_match(p, str))
2472                                                 return true;
2473
2474                                         if(!*str)
2475                                                 return false;
2476                                         else
2477                                                 str++;
2478                                 }
2479                                 return false;
2480
2481                         default:
2482                                 if(*str != *p)
2483                                         return false;
2484                                 str++;
2485                                 p++;
2486                                 break;
2487                 }
2488         }
2489
2490         if(!*p && !*str)
2491                 return true;
2492
2493         if (!*p && str[0] == '.' && str[1] == 0)
2494                 return true;
2495
2496         if (!*str && *p == '?') {
2497                 while (*p == '?')
2498                         p++;
2499                 return(!*p);
2500         }
2501
2502         if(!*str && (*p == '*' && p[1] == '\0'))
2503                 return true;
2504
2505         return false;
2506 }
2507
2508 /*******************************************************************
2509  Simple case insensitive interface to a UNIX wildcard matcher.
2510  Returns True if match, False if not.
2511 *******************************************************************/
2512
2513 bool unix_wild_match(const char *pattern, const char *string)
2514 {
2515         TALLOC_CTX *ctx = talloc_stackframe();
2516         char *p2;
2517         char *s2;
2518         char *p;
2519         bool ret = false;
2520
2521         p2 = talloc_strdup(ctx,pattern);
2522         s2 = talloc_strdup(ctx,string);
2523         if (!p2 || !s2) {
2524                 TALLOC_FREE(ctx);
2525                 return false;
2526         }
2527         strlower_m(p2);
2528         strlower_m(s2);
2529
2530         /* Remove any *? and ** from the pattern as they are meaningless */
2531         for(p = p2; *p; p++) {
2532                 while( *p == '*' && (p[1] == '?' ||p[1] == '*')) {
2533                         memmove(&p[1], &p[2], strlen(&p[2])+1);
2534                 }
2535         }
2536
2537         if (strequal(p2,"*")) {
2538                 TALLOC_FREE(ctx);
2539                 return true;
2540         }
2541
2542         ret = unix_do_match(p2, s2);
2543         TALLOC_FREE(ctx);
2544         return ret;
2545 }
2546
2547 /**********************************************************************
2548  Converts a name to a fully qualified domain name.
2549  Returns true if lookup succeeded, false if not (then fqdn is set to name)
2550  Note we deliberately use gethostbyname here, not getaddrinfo as we want
2551  to examine the h_aliases and I don't know how to do that with getaddrinfo.
2552 ***********************************************************************/
2553
2554 bool name_to_fqdn(fstring fqdn, const char *name)
2555 {
2556         char *full = NULL;
2557         struct hostent *hp = gethostbyname(name);
2558
2559         if (!hp || !hp->h_name || !*hp->h_name) {
2560                 DEBUG(10,("name_to_fqdn: lookup for %s failed.\n", name));
2561                 fstrcpy(fqdn, name);
2562                 return false;
2563         }
2564
2565         /* Find out if the fqdn is returned as an alias
2566          * to cope with /etc/hosts files where the first
2567          * name is not the fqdn but the short name */
2568         if (hp->h_aliases && (! strchr_m(hp->h_name, '.'))) {
2569                 int i;
2570                 for (i = 0; hp->h_aliases[i]; i++) {
2571                         if (strchr_m(hp->h_aliases[i], '.')) {
2572                                 full = hp->h_aliases[i];
2573                                 break;
2574                         }
2575                 }
2576         }
2577         if (full && (StrCaseCmp(full, "localhost.localdomain") == 0)) {
2578                 DEBUG(1, ("WARNING: your /etc/hosts file may be broken!\n"));
2579                 DEBUGADD(1, ("    Specifing the machine hostname for address 127.0.0.1 may lead\n"));
2580                 DEBUGADD(1, ("    to Kerberos authentication problems as localhost.localdomain\n"));
2581                 DEBUGADD(1, ("    may end up being used instead of the real machine FQDN.\n"));
2582                 full = hp->h_name;
2583         }
2584         if (!full) {
2585                 full = hp->h_name;
2586         }
2587
2588         DEBUG(10,("name_to_fqdn: lookup for %s -> %s.\n", name, full));
2589         fstrcpy(fqdn, full);
2590         return true;
2591 }
2592
2593 /**********************************************************************
2594  Append a DATA_BLOB to a talloc'ed object
2595 ***********************************************************************/
2596
2597 void *talloc_append_blob(TALLOC_CTX *mem_ctx, void *buf, DATA_BLOB blob)
2598 {
2599         size_t old_size = 0;
2600         char *result;
2601
2602         if (blob.length == 0) {
2603                 return buf;
2604         }
2605
2606         if (buf != NULL) {
2607                 old_size = talloc_get_size(buf);
2608         }
2609
2610         result = (char *)TALLOC_REALLOC(mem_ctx, buf, old_size + blob.length);
2611         if (result == NULL) {
2612                 return NULL;
2613         }
2614
2615         memcpy(result + old_size, blob.data, blob.length);
2616         return result;
2617 }
2618
2619 uint32 map_share_mode_to_deny_mode(uint32 share_access, uint32 private_options)
2620 {
2621         switch (share_access & ~FILE_SHARE_DELETE) {
2622                 case FILE_SHARE_NONE:
2623                         return DENY_ALL;
2624                 case FILE_SHARE_READ:
2625                         return DENY_WRITE;
2626                 case FILE_SHARE_WRITE:
2627                         return DENY_READ;
2628                 case FILE_SHARE_READ|FILE_SHARE_WRITE:
2629                         return DENY_NONE;
2630         }
2631         if (private_options & NTCREATEX_OPTIONS_PRIVATE_DENY_DOS) {
2632                 return DENY_DOS;
2633         } else if (private_options & NTCREATEX_OPTIONS_PRIVATE_DENY_FCB) {
2634                 return DENY_FCB;
2635         }
2636
2637         return (uint32)-1;
2638 }
2639
2640 pid_t procid_to_pid(const struct server_id *proc)
2641 {
2642         return proc->pid;
2643 }
2644
2645 static uint32 my_vnn = NONCLUSTER_VNN;
2646
2647 void set_my_vnn(uint32 vnn)
2648 {
2649         DEBUG(10, ("vnn pid %d = %u\n", (int)sys_getpid(), (unsigned int)vnn));
2650         my_vnn = vnn;
2651 }
2652
2653 uint32 get_my_vnn(void)
2654 {
2655         return my_vnn;
2656 }
2657
2658 struct server_id pid_to_procid(pid_t pid)
2659 {
2660         struct server_id result;
2661         result.pid = pid;
2662 #ifdef CLUSTER_SUPPORT
2663         result.vnn = my_vnn;
2664 #endif
2665         return result;
2666 }
2667
2668 struct server_id procid_self(void)
2669 {
2670         return pid_to_procid(sys_getpid());
2671 }
2672
2673 struct server_id server_id_self(void)
2674 {
2675         return procid_self();
2676 }
2677
2678 bool procid_equal(const struct server_id *p1, const struct server_id *p2)
2679 {
2680         if (p1->pid != p2->pid)
2681                 return False;
2682 #ifdef CLUSTER_SUPPORT
2683         if (p1->vnn != p2->vnn)
2684                 return False;
2685 #endif
2686         return True;
2687 }
2688
2689 bool cluster_id_equal(const struct server_id *id1,
2690                       const struct server_id *id2)
2691 {
2692         return procid_equal(id1, id2);
2693 }
2694
2695 bool procid_is_me(const struct server_id *pid)
2696 {
2697         if (pid->pid != sys_getpid())
2698                 return False;
2699 #ifdef CLUSTER_SUPPORT
2700         if (pid->vnn != my_vnn)
2701                 return False;
2702 #endif
2703         return True;
2704 }
2705
2706 struct server_id interpret_pid(const char *pid_string)
2707 {
2708         struct server_id result;
2709         int pid;
2710 #ifdef CLUSTER_SUPPORT
2711         unsigned int vnn;
2712         if (sscanf(pid_string, "%u:%d", &vnn, &pid) == 2) {
2713                 result.vnn = vnn;
2714                 result.pid = pid;
2715         }
2716         else if (sscanf(pid_string, "%d", &pid) == 1) {
2717                 result.vnn = get_my_vnn();
2718                 result.pid = pid;
2719         }
2720         else {
2721                 result.vnn = NONCLUSTER_VNN;
2722                 result.pid = -1;
2723         }
2724 #else
2725         if (sscanf(pid_string, "%d", &pid) != 1) {
2726                 result.pid = -1;
2727         } else {
2728                 result.pid = pid;
2729         }
2730 #endif
2731         /* Assigning to result.pid may have overflowed
2732            Map negative pid to -1: i.e. error */
2733         if (result.pid < 0) {
2734                 result.pid = -1;
2735         }
2736         return result;
2737 }
2738
2739 char *procid_str(TALLOC_CTX *mem_ctx, const struct server_id *pid)
2740 {
2741 #ifdef CLUSTER_SUPPORT
2742         if (pid->vnn == NONCLUSTER_VNN) {
2743                 return talloc_asprintf(mem_ctx,
2744                                 "%d",
2745                                 (int)pid->pid);
2746         }
2747         else {
2748                 return talloc_asprintf(mem_ctx,
2749                                         "%u:%d",
2750                                         (unsigned)pid->vnn,
2751                                         (int)pid->pid);
2752         }
2753 #else
2754         return talloc_asprintf(mem_ctx,
2755                         "%d",
2756                         (int)pid->pid);
2757 #endif
2758 }
2759
2760 char *procid_str_static(const struct server_id *pid)
2761 {
2762         return procid_str(talloc_tos(), pid);
2763 }
2764
2765 bool procid_valid(const struct server_id *pid)
2766 {
2767         return (pid->pid != -1);
2768 }
2769
2770 bool procid_is_local(const struct server_id *pid)
2771 {
2772 #ifdef CLUSTER_SUPPORT
2773         return pid->vnn == my_vnn;
2774 #else
2775         return True;
2776 #endif
2777 }
2778
2779 int this_is_smp(void)
2780 {
2781 #if defined(HAVE_SYSCONF)
2782
2783 #if defined(SYSCONF_SC_NPROC_ONLN)
2784         return (sysconf(_SC_NPROC_ONLN) > 1) ? 1 : 0;
2785 #elif defined(SYSCONF_SC_NPROCESSORS_ONLN)
2786         return (sysconf(_SC_NPROCESSORS_ONLN) > 1) ? 1 : 0;
2787 #else
2788         return 0;
2789 #endif
2790
2791 #else
2792         return 0;
2793 #endif
2794 }
2795
2796 /****************************************************************
2797  Check if offset/length fit into bufsize. Should probably be
2798  merged with is_offset_safe, but this would require a rewrite
2799  of lanman.c. Later :-)
2800 ****************************************************************/
2801
2802 bool trans_oob(uint32_t bufsize, uint32_t offset, uint32_t length)
2803 {
2804         if ((offset + length < offset) || (offset + length < length)) {
2805                 /* wrap */
2806                 return true;
2807         }
2808         if ((offset > bufsize) || (offset + length > bufsize)) {
2809                 /* overflow */
2810                 return true;
2811         }
2812         return false;
2813 }
2814
2815 /****************************************************************
2816  Check if an offset into a buffer is safe.
2817  If this returns True it's safe to indirect into the byte at
2818  pointer ptr+off.
2819 ****************************************************************/
2820
2821 bool is_offset_safe(const char *buf_base, size_t buf_len, char *ptr, size_t off)
2822 {
2823         const char *end_base = buf_base + buf_len;
2824         char *end_ptr = ptr + off;
2825
2826         if (!buf_base || !ptr) {
2827                 return False;
2828         }
2829
2830         if (end_base < buf_base || end_ptr < ptr) {
2831                 return False; /* wrap. */
2832         }
2833
2834         if (end_ptr < end_base) {
2835                 return True;
2836         }
2837         return False;
2838 }
2839
2840 /****************************************************************
2841  Return a safe pointer into a buffer, or NULL.
2842 ****************************************************************/
2843
2844 char *get_safe_ptr(const char *buf_base, size_t buf_len, char *ptr, size_t off)
2845 {
2846         return is_offset_safe(buf_base, buf_len, ptr, off) ?
2847                         ptr + off : NULL;
2848 }
2849
2850 /****************************************************************
2851  Return a safe pointer into a string within a buffer, or NULL.
2852 ****************************************************************/
2853
2854 char *get_safe_str_ptr(const char *buf_base, size_t buf_len, char *ptr, size_t off)
2855 {
2856         if (!is_offset_safe(buf_base, buf_len, ptr, off)) {
2857                 return NULL;
2858         }
2859         /* Check if a valid string exists at this offset. */
2860         if (skip_string(buf_base,buf_len, ptr + off) == NULL) {
2861                 return NULL;
2862         }
2863         return ptr + off;
2864 }
2865
2866 /****************************************************************
2867  Return an SVAL at a pointer, or failval if beyond the end.
2868 ****************************************************************/
2869
2870 int get_safe_SVAL(const char *buf_base, size_t buf_len, char *ptr, size_t off, int failval)
2871 {
2872         /*
2873          * Note we use off+1 here, not off+2 as SVAL accesses ptr[0] and ptr[1],
2874          * NOT ptr[2].
2875          */
2876         if (!is_offset_safe(buf_base, buf_len, ptr, off+1)) {
2877                 return failval;
2878         }
2879         return SVAL(ptr,off);
2880 }
2881
2882 /****************************************************************
2883  Return an IVAL at a pointer, or failval if beyond the end.
2884 ****************************************************************/
2885
2886 int get_safe_IVAL(const char *buf_base, size_t buf_len, char *ptr, size_t off, int failval)
2887 {
2888         /*
2889          * Note we use off+3 here, not off+4 as IVAL accesses 
2890          * ptr[0] ptr[1] ptr[2] ptr[3] NOT ptr[4].
2891          */
2892         if (!is_offset_safe(buf_base, buf_len, ptr, off+3)) {
2893                 return failval;
2894         }
2895         return IVAL(ptr,off);
2896 }
2897
2898 /****************************************************************
2899  Split DOM\user into DOM and user. Do not mix with winbind variants of that
2900  call (they take care of winbind separator and other winbind specific settings).
2901 ****************************************************************/
2902
2903 void split_domain_user(TALLOC_CTX *mem_ctx,
2904                        const char *full_name,
2905                        char **domain,
2906                        char **user)
2907 {
2908         const char *p = NULL;
2909
2910         p = strchr_m(full_name, '\\');
2911
2912         if (p != NULL) {
2913                 *domain = talloc_strndup(mem_ctx, full_name,
2914                                          PTR_DIFF(p, full_name));
2915                 *user = talloc_strdup(mem_ctx, p+1);
2916         } else {
2917                 *domain = talloc_strdup(mem_ctx, "");
2918                 *user = talloc_strdup(mem_ctx, full_name);
2919         }
2920 }
2921
2922 #if 0
2923
2924 Disable these now we have checked all code paths and ensured
2925 NULL returns on zero request. JRA.
2926
2927 /****************************************************************
2928  talloc wrapper functions that guarentee a null pointer return
2929  if size == 0.
2930 ****************************************************************/
2931
2932 #ifndef MAX_TALLOC_SIZE
2933 #define MAX_TALLOC_SIZE 0x10000000
2934 #endif
2935
2936 /*
2937  *    talloc and zero memory.
2938  *    - returns NULL if size is zero.
2939  */
2940
2941 void *_talloc_zero_zeronull(const void *ctx, size_t size, const char *name)
2942 {
2943         void *p;
2944
2945         if (size == 0) {
2946                 return NULL;
2947         }
2948
2949         p = talloc_named_const(ctx, size, name);
2950
2951         if (p) {
2952                 memset(p, '\0', size);
2953         }
2954
2955         return p;
2956 }
2957
2958 /*
2959  *   memdup with a talloc.
2960  *   - returns NULL if size is zero.
2961  */
2962
2963 void *_talloc_memdup_zeronull(const void *t, const void *p, size_t size, const char *name)
2964 {
2965         void *newp;
2966
2967         if (size == 0) {
2968                 return NULL;
2969         }
2970
2971         newp = talloc_named_const(t, size, name);
2972         if (newp) {
2973                 memcpy(newp, p, size);
2974         }
2975
2976         return newp;
2977 }
2978
2979 /*
2980  *   alloc an array, checking for integer overflow in the array size.
2981  *   - returns NULL if count or el_size are zero.
2982  */
2983
2984 void *_talloc_array_zeronull(const void *ctx, size_t el_size, unsigned count, const char *name)
2985 {
2986         if (count >= MAX_TALLOC_SIZE/el_size) {
2987                 return NULL;
2988         }
2989
2990         if (el_size == 0 || count == 0) {
2991                 return NULL;
2992         }
2993
2994         return talloc_named_const(ctx, el_size * count, name);
2995 }
2996
2997 /*
2998  *   alloc an zero array, checking for integer overflow in the array size
2999  *   - returns NULL if count or el_size are zero.
3000  */
3001
3002 void *_talloc_zero_array_zeronull(const void *ctx, size_t el_size, unsigned count, const char *name)
3003 {
3004         if (count >= MAX_TALLOC_SIZE/el_size) {
3005                 return NULL;
3006         }
3007
3008         if (el_size == 0 || count == 0) {
3009                 return NULL;
3010         }
3011
3012         return _talloc_zero(ctx, el_size * count, name);
3013 }
3014
3015 /*
3016  *   Talloc wrapper that returns NULL if size == 0.
3017  */
3018 void *talloc_zeronull(const void *context, size_t size, const char *name)
3019 {
3020         if (size == 0) {
3021                 return NULL;
3022         }
3023         return talloc_named_const(context, size, name);
3024 }
3025 #endif
3026
3027 bool is_valid_policy_hnd(const struct policy_handle *hnd)
3028 {
3029         struct policy_handle tmp;
3030         ZERO_STRUCT(tmp);
3031         return (memcmp(&tmp, hnd, sizeof(tmp)) != 0);
3032 }
3033
3034 bool policy_hnd_equal(const struct policy_handle *hnd1,
3035                       const struct policy_handle *hnd2)
3036 {
3037         if (!hnd1 || !hnd2) {
3038                 return false;
3039         }
3040
3041         return (memcmp(hnd1, hnd2, sizeof(*hnd1)) == 0);
3042 }
3043
3044 /****************************************************************
3045  strip off leading '\\' from a hostname
3046 ****************************************************************/
3047
3048 const char *strip_hostname(const char *s)
3049 {
3050         if (!s) {
3051                 return NULL;
3052         }
3053
3054         if (strlen_m(s) < 3) {
3055                 return s;
3056         }
3057
3058         if (s[0] == '\\') s++;
3059         if (s[0] == '\\') s++;
3060
3061         return s;
3062 }
3063
3064 bool tevent_req_poll_ntstatus(struct tevent_req *req,
3065                               struct tevent_context *ev,
3066                               NTSTATUS *status)
3067 {
3068         bool ret = tevent_req_poll(req, ev);
3069         if (!ret) {
3070                 *status = map_nt_error_from_unix(errno);
3071         }
3072         return ret;
3073 }