param: copy parametric option helper to lib/param
[mat/samba.git] / source3 / param / loadparm.c
1 /* 
2    Unix SMB/CIFS implementation.
3    Parameter loading functions
4    Copyright (C) Karl Auer 1993-1998
5
6    Largely re-written by Andrew Tridgell, September 1994
7
8    Copyright (C) Simo Sorce 2001
9    Copyright (C) Alexander Bokovoy 2002
10    Copyright (C) Stefan (metze) Metzmacher 2002
11    Copyright (C) Jim McDonough <jmcd@us.ibm.com> 2003
12    Copyright (C) Michael Adam 2008
13    Copyright (C) Jelmer Vernooij <jelmer@samba.org> 2007
14    Copyright (C) Andrew Bartlett 2011
15
16    This program is free software; you can redistribute it and/or modify
17    it under the terms of the GNU General Public License as published by
18    the Free Software Foundation; either version 3 of the License, or
19    (at your option) any later version.
20
21    This program is distributed in the hope that it will be useful,
22    but WITHOUT ANY WARRANTY; without even the implied warranty of
23    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
24    GNU General Public License for more details.
25
26    You should have received a copy of the GNU General Public License
27    along with this program.  If not, see <http://www.gnu.org/licenses/>.
28 */
29
30 /*
31  *  Load parameters.
32  *
33  *  This module provides suitable callback functions for the params
34  *  module. It builds the internal table of service details which is
35  *  then used by the rest of the server.
36  *
37  * To add a parameter:
38  *
39  * 1) add it to the global or service structure definition
40  * 2) add it to the parm_table
41  * 3) add it to the list of available functions (eg: using FN_GLOBAL_STRING())
42  * 4) If it's a global then initialise it in init_globals. If a local
43  *    (ie. service) parameter then initialise it in the sDefault structure
44  *  
45  *
46  * Notes:
47  *   The configuration file is processed sequentially for speed. It is NOT
48  *   accessed randomly as happens in 'real' Windows. For this reason, there
49  *   is a fair bit of sequence-dependent code here - ie., code which assumes
50  *   that certain things happen before others. In particular, the code which
51  *   happens at the boundary between sections is delicately poised, so be
52  *   careful!
53  *
54  */
55
56 #include "includes.h"
57 #include "system/filesys.h"
58 #include "util_tdb.h"
59 #include "lib/param/loadparm.h"
60 #include "lib/param/param.h"
61 #include "printing.h"
62 #include "lib/smbconf/smbconf.h"
63 #include "lib/smbconf/smbconf_init.h"
64
65 #include "ads.h"
66 #include "../librpc/gen_ndr/svcctl.h"
67 #include "intl.h"
68 #include "../libcli/smb/smb_signing.h"
69 #include "dbwrap/dbwrap.h"
70 #include "dbwrap/dbwrap_rbt.h"
71 #include "../lib/util/bitmap.h"
72
73 #ifdef HAVE_SYS_SYSCTL_H
74 #include <sys/sysctl.h>
75 #endif
76
77 #ifdef HAVE_HTTPCONNECTENCRYPT
78 #include <cups/http.h>
79 #endif
80
81 bool bLoaded = false;
82
83 extern userdom_struct current_user_info;
84
85 /* the special value for the include parameter
86  * to be interpreted not as a file name but to
87  * trigger loading of the global smb.conf options
88  * from registry. */
89 #ifndef INCLUDE_REGISTRY_NAME
90 #define INCLUDE_REGISTRY_NAME "registry"
91 #endif
92
93 static bool in_client = false;          /* Not in the client by default */
94 static struct smbconf_csn conf_last_csn;
95
96 static int config_backend = CONFIG_BACKEND_FILE;
97
98 /* some helpful bits */
99 #define LP_SNUM_OK(i) (((i) >= 0) && ((i) < iNumServices) && (ServicePtrs != NULL) && ServicePtrs[(i)]->valid)
100 #define VALID(i) (ServicePtrs != NULL && ServicePtrs[i]->valid)
101
102 #define USERSHARE_VALID 1
103 #define USERSHARE_PENDING_DELETE 2
104
105 static bool defaults_saved = false;
106
107 #include "lib/param/param_global.h"
108
109 static struct loadparm_global Globals;
110
111 /* This is a default service used to prime a services structure */
112 static struct loadparm_service sDefault =
113 {
114         .valid = true,
115         .autoloaded = false,
116         .usershare = 0,
117         .usershare_last_mod = {0, 0},
118         .szService = NULL,
119         .path = NULL,
120         .username = NULL,
121         .invalid_users = NULL,
122         .valid_users = NULL,
123         .admin_users = NULL,
124         .szCopy = NULL,
125         .szInclude = NULL,
126         .preexec = NULL,
127         .postexec = NULL,
128         .root_preexec = NULL,
129         .root_postexec = NULL,
130         .cups_options = NULL,
131         .print_command = NULL,
132         .lpq_command = NULL,
133         .lprm_command = NULL,
134         .lppause_command = NULL,
135         .lpresume_command = NULL,
136         .queuepause_command = NULL,
137         .queueresume_command = NULL,
138         ._printername = NULL,
139         .printjob_username = NULL,
140         .dont_descend = NULL,
141         .hosts_allow = NULL,
142         .hosts_deny = NULL,
143         .magic_script = NULL,
144         .magic_output = NULL,
145         .veto_files = NULL,
146         .hide_files = NULL,
147         .veto_oplock_files = NULL,
148         .comment = NULL,
149         .force_user = NULL,
150         .force_group = NULL,
151         .read_list = NULL,
152         .write_list = NULL,
153         .volume = NULL,
154         .fstype = NULL,
155         .vfs_objects = NULL,
156         .msdfs_proxy = NULL,
157         .aio_write_behind = NULL,
158         .dfree_command = NULL,
159         .min_print_space = 0,
160         .iMaxPrintJobs = 1000,
161         .max_reported_print_jobs = 0,
162         .write_cache_size = 0,
163         .create_mask = 0744,
164         .force_create_mode = 0,
165         .directory_mask = 0755,
166         .force_directory_mode = 0,
167         .max_connections = 0,
168         .default_case = CASE_LOWER,
169         .printing = DEFAULT_PRINTING,
170         .oplock_contention_limit = 2,
171         .csc_policy = 0,
172         .block_size = 1024,
173         .dfree_cache_time = 0,
174         .preexec_close = false,
175         .root_preexec_close = false,
176         .case_sensitive = Auto,
177         .preserve_case = true,
178         .short_preserve_case = true,
179         .hide_dot_files = true,
180         .hide_special_files = false,
181         .hide_unreadable = false,
182         .hide_unwriteable_files = false,
183         .browseable = true,
184         .access_based_share_enum = false,
185         .bAvailable = true,
186         .read_only = true,
187         .guest_only = false,
188         .administrative_share = false,
189         .guest_ok = false,
190         .printable = false,
191         .print_notify_backchannel = false,
192         .map_system = false,
193         .map_hidden = false,
194         .map_archive = true,
195         .store_dos_attributes = false,
196         .dmapi_support = false,
197         .locking = true,
198         .strict_locking = Auto,
199         .posix_locking = true,
200         .oplocks = true,
201         .kernel_oplocks = false,
202         .level2_oplocks = true,
203         .only_user = false,
204         .mangled_names = true,
205         .bWidelinks = false,
206         .follow_symlinks = true,
207         .sync_always = false,
208         .strict_allocate = false,
209         .strict_sync = false,
210         .mangling_char = '~',
211         .copymap = NULL,
212         .delete_readonly = false,
213         .fake_oplocks = false,
214         .delete_veto_files = false,
215         .dos_filemode = false,
216         .dos_filetimes = true,
217         .dos_filetime_resolution = false,
218         .fake_directory_create_times = false,
219         .blocking_locks = true,
220         .inherit_permissions = false,
221         .inherit_acls = false,
222         .inherit_owner = false,
223         .msdfs_root = false,
224         .use_client_driver = false,
225         .default_devmode = true,
226         .force_printername = false,
227         .nt_acl_support = true,
228         .force_unknown_acl_user = false,
229         ._use_sendfile = false,
230         .profile_acls = false,
231         .map_acl_inherit = false,
232         .afs_share = false,
233         .ea_support = false,
234         .acl_check_permissions = true,
235         .acl_map_full_control = true,
236         .acl_group_control = false,
237         .acl_allow_execute_always = false,
238         .change_notify = true,
239         .kernel_change_notify = true,
240         .allocation_roundup_size = SMB_ROUNDUP_ALLOCATION_SIZE,
241         .aio_read_size = 0,
242         .aio_write_size = 0,
243         .map_readonly = MAP_READONLY_YES,
244         .directory_name_cache_size = 100,
245         .smb_encrypt = SMB_SIGNING_DEFAULT,
246         .kernel_share_modes = true,
247         .durable_handles = true,
248         .param_opt = NULL,
249         .dummy = ""
250 };
251
252 /* local variables */
253 static struct loadparm_service **ServicePtrs = NULL;
254 static int iNumServices = 0;
255 static int iServiceIndex = 0;
256 static struct db_context *ServiceHash;
257 static bool bInGlobalSection = true;
258 static bool bGlobalOnly = false;
259 static struct file_lists *file_lists = NULL;
260
261 static void set_allowed_client_auth(void);
262
263 static bool lp_set_cmdline_helper(const char *pszParmName, const char *pszParmValue);
264 static void free_param_opts(struct parmlist_entry **popts);
265
266 /* this is used to prevent lots of mallocs of size 1 */
267 static const char null_string[] = "";
268
269 /**
270  Free a string value.
271 **/
272
273 static void string_free(char **s)
274 {
275         if (!s || !(*s))
276                 return;
277         if (*s == null_string)
278                 *s = NULL;
279         TALLOC_FREE(*s);
280 }
281
282 /**
283  Set a string value, deallocating any existing space, and allocing the space
284  for the string
285 **/
286
287 static bool string_set(TALLOC_CTX *mem_ctx, char **dest,const char *src)
288 {
289         string_free(dest);
290
291         if (!src) {
292                 src = "";
293         }
294
295         (*dest) = talloc_strdup(mem_ctx, src);
296         if ((*dest) == NULL) {
297                 DEBUG(0,("Out of memory in string_init\n"));
298                 return false;
299         }
300
301         return true;
302 }
303
304 bool lp_string_set(char **dest, const char *src) {
305         return string_set(Globals.ctx, dest, src);
306 }
307
308 /***************************************************************************
309  Initialise the sDefault parameter structure for the printer values.
310 ***************************************************************************/
311
312 void init_printer_values(TALLOC_CTX *ctx, struct loadparm_service *pService)
313 {
314         /* choose defaults depending on the type of printing */
315         switch (pService->printing) {
316                 case PRINT_BSD:
317                 case PRINT_AIX:
318                 case PRINT_LPRNT:
319                 case PRINT_LPROS2:
320                         lpcfg_string_set(ctx, &pService->lpq_command, "lpq -P'%p'");
321                         lpcfg_string_set(ctx, &pService->lprm_command, "lprm -P'%p' %j");
322                         lpcfg_string_set(ctx, &pService->print_command, "lpr -r -P'%p' %s");
323                         break;
324
325                 case PRINT_LPRNG:
326                 case PRINT_PLP:
327                         lpcfg_string_set(ctx, &pService->lpq_command, "lpq -P'%p'");
328                         lpcfg_string_set(ctx, &pService->lprm_command, "lprm -P'%p' %j");
329                         lpcfg_string_set(ctx, &pService->print_command, "lpr -r -P'%p' %s");
330                         lpcfg_string_set(ctx, &pService->queuepause_command, "lpc stop '%p'");
331                         lpcfg_string_set(ctx, &pService->queueresume_command, "lpc start '%p'");
332                         lpcfg_string_set(ctx, &pService->lppause_command, "lpc hold '%p' %j");
333                         lpcfg_string_set(ctx, &pService->lpresume_command, "lpc release '%p' %j");
334                         break;
335
336                 case PRINT_CUPS:
337                 case PRINT_IPRINT:
338                         /* set the lpq command to contain the destination printer
339                            name only.  This is used by cups_queue_get() */
340                         lpcfg_string_set(ctx, &pService->lpq_command, "%p");
341                         lpcfg_string_set(ctx, &pService->lprm_command, "");
342                         lpcfg_string_set(ctx, &pService->print_command, "");
343                         lpcfg_string_set(ctx, &pService->lppause_command, "");
344                         lpcfg_string_set(ctx, &pService->lpresume_command, "");
345                         lpcfg_string_set(ctx, &pService->queuepause_command, "");
346                         lpcfg_string_set(ctx, &pService->queueresume_command, "");
347                         break;
348
349                 case PRINT_SYSV:
350                 case PRINT_HPUX:
351                         lpcfg_string_set(ctx, &pService->lpq_command, "lpstat -o%p");
352                         lpcfg_string_set(ctx, &pService->lprm_command, "cancel %p-%j");
353                         lpcfg_string_set(ctx, &pService->print_command, "lp -c -d%p %s; rm %s");
354                         lpcfg_string_set(ctx, &pService->queuepause_command, "disable %p");
355                         lpcfg_string_set(ctx, &pService->queueresume_command, "enable %p");
356 #ifndef HPUX
357                         lpcfg_string_set(ctx, &pService->lppause_command, "lp -i %p-%j -H hold");
358                         lpcfg_string_set(ctx, &pService->lpresume_command, "lp -i %p-%j -H resume");
359 #endif /* HPUX */
360                         break;
361
362                 case PRINT_QNX:
363                         lpcfg_string_set(ctx, &pService->lpq_command, "lpq -P%p");
364                         lpcfg_string_set(ctx, &pService->lprm_command, "lprm -P%p %j");
365                         lpcfg_string_set(ctx, &pService->print_command, "lp -r -P%p %s");
366                         break;
367
368 #if defined(DEVELOPER) || defined(ENABLE_SELFTEST)
369
370         case PRINT_TEST:
371         case PRINT_VLP: {
372                 const char *tdbfile;
373                 TALLOC_CTX *tmp_ctx = talloc_new(ctx);
374                 char *tmp;
375
376                 tdbfile = talloc_asprintf(
377                         tmp_ctx, "tdbfile=%s",
378                         lp_parm_const_string(-1, "vlp", "tdbfile",
379                                              "/tmp/vlp.tdb"));
380                 if (tdbfile == NULL) {
381                         tdbfile="tdbfile=/tmp/vlp.tdb";
382                 }
383
384                 tmp = talloc_asprintf(tmp_ctx, "vlp %s print %%p %%s",
385                                       tdbfile);
386                 lpcfg_string_set(ctx, &pService->print_command,
387                            tmp ? tmp : "vlp print %p %s");
388
389                 tmp = talloc_asprintf(tmp_ctx, "vlp %s lpq %%p",
390                                       tdbfile);
391                 lpcfg_string_set(ctx, &pService->lpq_command,
392                            tmp ? tmp : "vlp lpq %p");
393
394                 tmp = talloc_asprintf(tmp_ctx, "vlp %s lprm %%p %%j",
395                                       tdbfile);
396                 lpcfg_string_set(ctx, &pService->lprm_command,
397                            tmp ? tmp : "vlp lprm %p %j");
398
399                 tmp = talloc_asprintf(tmp_ctx, "vlp %s lppause %%p %%j",
400                                       tdbfile);
401                 lpcfg_string_set(ctx, &pService->lppause_command,
402                            tmp ? tmp : "vlp lppause %p %j");
403
404                 tmp = talloc_asprintf(tmp_ctx, "vlp %s lpresume %%p %%j",
405                                       tdbfile);
406                 lpcfg_string_set(ctx, &pService->lpresume_command,
407                            tmp ? tmp : "vlp lpresume %p %j");
408
409                 tmp = talloc_asprintf(tmp_ctx, "vlp %s queuepause %%p",
410                                       tdbfile);
411                 lpcfg_string_set(ctx, &pService->queuepause_command,
412                            tmp ? tmp : "vlp queuepause %p");
413
414                 tmp = talloc_asprintf(tmp_ctx, "vlp %s queueresume %%p",
415                                       tdbfile);
416                 lpcfg_string_set(ctx, &pService->queueresume_command,
417                            tmp ? tmp : "vlp queueresume %p");
418                 TALLOC_FREE(tmp_ctx);
419
420                 break;
421         }
422 #endif /* DEVELOPER */
423
424         }
425 }
426 /**
427  *  Function to return the default value for the maximum number of open
428  *  file descriptors permitted.  This function tries to consult the
429  *  kernel-level (sysctl) and ulimit (getrlimit()) values and goes
430  *  the smaller of those.
431  */
432 static int max_open_files(void)
433 {
434         int sysctl_max = MAX_OPEN_FILES;
435         int rlimit_max = MAX_OPEN_FILES;
436
437 #ifdef HAVE_SYSCTLBYNAME
438         {
439                 size_t size = sizeof(sysctl_max);
440                 sysctlbyname("kern.maxfilesperproc", &sysctl_max, &size, NULL,
441                              0);
442         }
443 #endif
444
445 #if (defined(HAVE_GETRLIMIT) && defined(RLIMIT_NOFILE))
446         {
447                 struct rlimit rl;
448
449                 ZERO_STRUCT(rl);
450
451                 if (getrlimit(RLIMIT_NOFILE, &rl) == 0)
452                         rlimit_max = rl.rlim_cur;
453
454 #if defined(RLIM_INFINITY)
455                 if(rl.rlim_cur == RLIM_INFINITY)
456                         rlimit_max = MAX_OPEN_FILES;
457 #endif
458         }
459 #endif
460
461         if (sysctl_max < MIN_OPEN_FILES_WINDOWS) {
462                 DEBUG(2,("max_open_files: increasing sysctl_max (%d) to "
463                         "minimum Windows limit (%d)\n",
464                         sysctl_max,
465                         MIN_OPEN_FILES_WINDOWS));
466                 sysctl_max = MIN_OPEN_FILES_WINDOWS;
467         }
468
469         if (rlimit_max < MIN_OPEN_FILES_WINDOWS) {
470                 DEBUG(2,("rlimit_max: increasing rlimit_max (%d) to "
471                         "minimum Windows limit (%d)\n",
472                         rlimit_max,
473                         MIN_OPEN_FILES_WINDOWS));
474                 rlimit_max = MIN_OPEN_FILES_WINDOWS;
475         }
476
477         return MIN(sysctl_max, rlimit_max);
478 }
479
480 /**
481  * Common part of freeing allocated data for one parameter.
482  */
483 static void free_one_parameter_common(void *parm_ptr,
484                                       struct parm_struct parm)
485 {
486         if ((parm.type == P_STRING) ||
487             (parm.type == P_USTRING))
488         {
489                 string_free((char**)parm_ptr);
490         } else if (parm.type == P_LIST) {
491                 TALLOC_FREE(*((char***)parm_ptr));
492         }
493 }
494
495 /**
496  * Free the allocated data for one parameter for a share
497  * given as a service struct.
498  */
499 static void free_one_parameter(struct loadparm_service *service,
500                                struct parm_struct parm)
501 {
502         void *parm_ptr;
503
504         if (parm.p_class != P_LOCAL) {
505                 return;
506         }
507
508         parm_ptr = lp_parm_ptr(service, &parm);
509
510         free_one_parameter_common(parm_ptr, parm);
511 }
512
513 /**
514  * Free the allocated parameter data of a share given
515  * as a service struct.
516  */
517 static void free_parameters(struct loadparm_service *service)
518 {
519         uint32_t i;
520
521         for (i=0; parm_table[i].label; i++) {
522                 free_one_parameter(service, parm_table[i]);
523         }
524 }
525
526 /**
527  * Free the allocated data for one parameter for a given share
528  * specified by an snum.
529  */
530 static void free_one_parameter_by_snum(int snum, struct parm_struct parm)
531 {
532         void *parm_ptr;
533
534         if (snum < 0) {
535                 parm_ptr = lp_parm_ptr(NULL, &parm);
536         } else if (parm.p_class != P_LOCAL) {
537                 return;
538         } else {
539                 parm_ptr = lp_local_ptr_by_snum(snum, &parm);
540         }
541
542         free_one_parameter_common(parm_ptr, parm);
543 }
544
545 /**
546  * Free the allocated parameter data for a share specified
547  * by an snum.
548  */
549 static void free_parameters_by_snum(int snum)
550 {
551         uint32_t i;
552
553         for (i=0; parm_table[i].label; i++) {
554                 free_one_parameter_by_snum(snum, parm_table[i]);
555         }
556 }
557
558 /**
559  * Free the allocated global parameters.
560  */
561 static void free_global_parameters(void)
562 {
563         free_param_opts(&Globals.param_opt);
564         free_parameters_by_snum(GLOBAL_SECTION_SNUM);
565         TALLOC_FREE(Globals.ctx);
566 }
567
568 struct lp_stored_option {
569         struct lp_stored_option *prev, *next;
570         const char *label;
571         const char *value;
572 };
573
574 static struct lp_stored_option *stored_options;
575
576 /*
577   save options set by lp_set_cmdline() into a list. This list is
578   re-applied when we do a globals reset, so that cmdline set options
579   are sticky across reloads of smb.conf
580  */
581 static bool store_lp_set_cmdline(const char *pszParmName, const char *pszParmValue)
582 {
583         struct lp_stored_option *entry, *entry_next;
584         for (entry = stored_options; entry != NULL; entry = entry_next) {
585                 entry_next = entry->next;
586                 if (strcmp(pszParmName, entry->label) == 0) {
587                         DLIST_REMOVE(stored_options, entry);
588                         talloc_free(entry);
589                         break;
590                 }
591         }
592
593         entry = talloc(NULL, struct lp_stored_option);
594         if (!entry) {
595                 return false;
596         }
597
598         entry->label = talloc_strdup(entry, pszParmName);
599         if (!entry->label) {
600                 talloc_free(entry);
601                 return false;
602         }
603
604         entry->value = talloc_strdup(entry, pszParmValue);
605         if (!entry->value) {
606                 talloc_free(entry);
607                 return false;
608         }
609
610         DLIST_ADD_END(stored_options, entry, struct lp_stored_option);
611
612         return true;
613 }
614
615 static bool apply_lp_set_cmdline(void)
616 {
617         struct lp_stored_option *entry = NULL;
618         for (entry = stored_options; entry != NULL; entry = entry->next) {
619                 if (!lp_set_cmdline_helper(entry->label, entry->value)) {
620                         DEBUG(0, ("Failed to re-apply cmdline parameter %s = %s\n",
621                                   entry->label, entry->value));
622                         return false;
623                 }
624         }
625         return true;
626 }
627
628 /***************************************************************************
629  Initialise the global parameter structure.
630 ***************************************************************************/
631
632 static void init_globals(bool reinit_globals)
633 {
634         static bool done_init = false;
635         char *s = NULL;
636         int i;
637
638         /* If requested to initialize only once and we've already done it... */
639         if (!reinit_globals && done_init) {
640                 /* ... then we have nothing more to do */
641                 return;
642         }
643
644         if (!done_init) {
645                 /* The logfile can be set before this is invoked. Free it if so. */
646                 if (Globals.logfile != NULL) {
647                         string_free(&Globals.logfile);
648                         Globals.logfile = NULL;
649                 }
650                 done_init = true;
651         } else {
652                 free_global_parameters();
653         }
654
655         /* This memset and the free_global_parameters() above will
656          * wipe out smb.conf options set with lp_set_cmdline().  The
657          * apply_lp_set_cmdline() call puts these values back in the
658          * table once the defaults are set */
659         ZERO_STRUCT(Globals);
660
661         Globals.ctx = talloc_pooled_object(NULL, char, 272, 2048);
662
663         for (i = 0; parm_table[i].label; i++) {
664                 if ((parm_table[i].type == P_STRING ||
665                      parm_table[i].type == P_USTRING))
666                 {
667                         string_set(Globals.ctx, (char **)lp_parm_ptr(NULL, &parm_table[i]), "");
668                 }
669         }
670
671
672         string_set(Globals.ctx, &sDefault.fstype, FSTYPE_STRING);
673         string_set(Globals.ctx, &sDefault.printjob_username, "%U");
674
675         init_printer_values(Globals.ctx, &sDefault);
676
677         sDefault.ntvfs_handler = (const char **)str_list_make_v3(NULL, "unixuid default", NULL);
678
679         DEBUG(3, ("Initialising global parameters\n"));
680
681         /* Must manually force to upper case here, as this does not go via the handler */
682         string_set(Globals.ctx, &Globals.netbios_name, myhostname_upper());
683
684         string_set(Globals.ctx, &Globals.smb_passwd_file, get_dyn_SMB_PASSWD_FILE());
685         string_set(Globals.ctx, &Globals.private_dir, get_dyn_PRIVATE_DIR());
686
687         /* use the new 'hash2' method by default, with a prefix of 1 */
688         string_set(Globals.ctx, &Globals.mangling_method, "hash2");
689         Globals.mangle_prefix = 1;
690
691         string_set(Globals.ctx, &Globals.guest_account, GUEST_ACCOUNT);
692
693         /* using UTF8 by default allows us to support all chars */
694         string_set(Globals.ctx, &Globals.unix_charset, DEFAULT_UNIX_CHARSET);
695
696         /* Use codepage 850 as a default for the dos character set */
697         string_set(Globals.ctx, &Globals.dos_charset, DEFAULT_DOS_CHARSET);
698
699         /*
700          * Allow the default PASSWD_CHAT to be overridden in local.h.
701          */
702         string_set(Globals.ctx, &Globals.passwd_chat, DEFAULT_PASSWD_CHAT);
703
704         string_set(Globals.ctx, &Globals.workgroup, DEFAULT_WORKGROUP);
705
706         string_set(Globals.ctx, &Globals.passwd_program, "");
707         string_set(Globals.ctx, &Globals.lock_directory, get_dyn_LOCKDIR());
708         string_set(Globals.ctx, &Globals.state_directory, get_dyn_STATEDIR());
709         string_set(Globals.ctx, &Globals.cache_directory, get_dyn_CACHEDIR());
710         string_set(Globals.ctx, &Globals.pid_directory, get_dyn_PIDDIR());
711         string_set(Globals.ctx, &Globals.nbt_client_socket_address, "0.0.0.0");
712         /*
713          * By default support explicit binding to broadcast
714          * addresses.
715          */
716         Globals.nmbd_bind_explicit_broadcast = true;
717
718         s = talloc_asprintf(talloc_tos(), "Samba %s", samba_version_string());
719         if (s == NULL) {
720                 smb_panic("init_globals: ENOMEM");
721         }
722         string_set(Globals.ctx, &Globals.server_string, s);
723         TALLOC_FREE(s);
724 #ifdef DEVELOPER
725         string_set(Globals.ctx, &Globals.panic_action, "/bin/sleep 999999999");
726 #endif
727
728         string_set(Globals.ctx, &Globals.socket_options, DEFAULT_SOCKET_OPTIONS);
729
730         string_set(Globals.ctx, &Globals.logon_drive, "");
731         /* %N is the NIS auto.home server if -DAUTOHOME is used, else same as %L */
732         string_set(Globals.ctx, &Globals.logon_home, "\\\\%N\\%U");
733         string_set(Globals.ctx, &Globals.logon_path, "\\\\%N\\%U\\profile");
734
735         Globals.name_resolve_order = (const char **)str_list_make_v3(NULL, "lmhosts wins host bcast", NULL);
736         string_set(Globals.ctx, &Globals.password_server, "*");
737
738         Globals.algorithmic_rid_base = BASE_RID;
739
740         Globals.load_printers = true;
741         Globals.printcap_cache_time = 750;      /* 12.5 minutes */
742
743         Globals.config_backend = config_backend;
744         Globals._server_role = ROLE_AUTO;
745
746         /* Was 65535 (0xFFFF). 0x4101 matches W2K and causes major speed improvements... */
747         /* Discovered by 2 days of pain by Don McCall @ HP :-). */
748         Globals.max_xmit = 0x4104;
749         Globals.max_mux = 50;   /* This is *needed* for profile support. */
750         Globals.lpq_cache_time = 30;    /* changed to handle large print servers better -- jerry */
751         Globals._disable_spoolss = false;
752         Globals.max_smbd_processes = 0;/* no limit specified */
753         Globals.username_level = 0;
754         Globals.deadtime = 0;
755         Globals.getwd_cache = true;
756         Globals.large_readwrite = true;
757         Globals.max_log_size = 5000;
758         Globals.max_open_files = max_open_files();
759         Globals.server_max_protocol = PROTOCOL_SMB3_00;
760         Globals.server_min_protocol = PROTOCOL_LANMAN1;
761         Globals.client_max_protocol = PROTOCOL_NT1;
762         Globals.client_min_protocol = PROTOCOL_CORE;
763         Globals._security = SEC_AUTO;
764         Globals.encrypt_passwords = true;
765         Globals.client_schannel = Auto;
766         Globals.winbind_sealed_pipes = true;
767         Globals.require_strong_key = true;
768         Globals.server_schannel = Auto;
769         Globals.read_raw = true;
770         Globals.write_raw = true;
771         Globals.null_passwords = false;
772         Globals.old_password_allowed_period = 60;
773         Globals.obey_pam_restrictions = false;
774         Globals.syslog = 1;
775         Globals.syslog_only = false;
776         Globals.timestamp_logs = true;
777         string_set(Globals.ctx, &Globals.log_level, "0");
778         Globals.debug_prefix_timestamp = false;
779         Globals.debug_hires_timestamp = true;
780         Globals.debug_pid = false;
781         Globals.debug_uid = false;
782         Globals.debug_class = false;
783         Globals.enable_core_files = true;
784         Globals.max_ttl = 60 * 60 * 24 * 3;     /* 3 days default. */
785         Globals.max_wins_ttl = 60 * 60 * 24 * 6;        /* 6 days default. */
786         Globals.min_wins_ttl = 60 * 60 * 6;     /* 6 hours default. */
787         Globals.machine_password_timeout = 60 * 60 * 24 * 7;    /* 7 days default. */
788         Globals.lm_announce = Auto;     /* = Auto: send only if LM clients found */
789         Globals.lm_interval = 60;
790 #if (defined(HAVE_NETGROUP) && defined(WITH_AUTOMOUNT))
791         Globals.nis_homedir = false;
792 #ifdef WITH_NISPLUS_HOME
793         string_set(Globals.ctx, &Globals.homedir_map, "auto_home.org_dir");
794 #else
795         string_set(Globals.ctx, &Globals.homedir_map, "auto.home");
796 #endif
797 #endif
798         Globals.time_server = false;
799         Globals.bind_interfaces_only = false;
800         Globals.unix_password_sync = false;
801         Globals.pam_password_change = false;
802         Globals.passwd_chat_debug = false;
803         Globals.passwd_chat_timeout = 2; /* 2 second default. */
804         Globals.nt_pipe_support = true; /* Do NT pipes by default. */
805         Globals.nt_status_support = true; /* Use NT status by default. */
806         Globals.stat_cache = true;      /* use stat cache by default */
807         Globals.max_stat_cache_size = 256; /* 256k by default */
808         Globals.restrict_anonymous = 0;
809         Globals.client_lanman_auth = false;     /* Do NOT use the LanMan hash if it is available */
810         Globals.client_plaintext_auth = false;  /* Do NOT use a plaintext password even if is requested by the server */
811         Globals.lanman_auth = false;    /* Do NOT use the LanMan hash, even if it is supplied */
812         Globals.ntlm_auth = true;       /* Do use NTLMv1 if it is supplied by the client (otherwise NTLMv2) */
813         Globals.client_ntlmv2_auth = true; /* Client should always use use NTLMv2, as we can't tell that the server supports it, but most modern servers do */
814         /* Note, that we will also use NTLM2 session security (which is different), if it is available */
815
816         Globals.map_to_guest = 0;       /* By Default, "Never" */
817         Globals.oplock_break_wait_time = 0;     /* By Default, 0 msecs. */
818         Globals.enhanced_browsing = true;
819         Globals.lock_spin_time = WINDOWS_MINIMUM_LOCK_TIMEOUT_MS; /* msec. */
820 #ifdef MMAP_BLACKLIST
821         Globals.use_mmap = false;
822 #else
823         Globals.use_mmap = true;
824 #endif
825         Globals.unicode = true;
826         Globals.unix_extensions = true;
827         Globals.reset_on_zero_vc = false;
828         Globals.log_writeable_files_on_exit = false;
829         Globals.create_krb5_conf = true;
830         Globals.winbindMaxDomainConnections = 1;
831
832         /* hostname lookups can be very expensive and are broken on
833            a large number of sites (tridge) */
834         Globals.hostname_lookups = false;
835
836         string_set(Globals.ctx, &Globals.passdb_backend, "tdbsam");
837         string_set(Globals.ctx, &Globals.ldap_suffix, "");
838         string_set(Globals.ctx, &Globals.szLdapMachineSuffix, "");
839         string_set(Globals.ctx, &Globals.szLdapUserSuffix, "");
840         string_set(Globals.ctx, &Globals.szLdapGroupSuffix, "");
841         string_set(Globals.ctx, &Globals.szLdapIdmapSuffix, "");
842
843         string_set(Globals.ctx, &Globals.ldap_admin_dn, "");
844         Globals.ldap_ssl = LDAP_SSL_START_TLS;
845         Globals.ldap_ssl_ads = false;
846         Globals.ldap_deref = -1;
847         Globals.ldap_passwd_sync = LDAP_PASSWD_SYNC_OFF;
848         Globals.ldap_delete_dn = false;
849         Globals.ldap_replication_sleep = 1000; /* wait 1 sec for replication */
850         Globals.ldap_follow_referral = Auto;
851         Globals.ldap_timeout = LDAP_DEFAULT_TIMEOUT;
852         Globals.ldap_connection_timeout = LDAP_CONNECTION_DEFAULT_TIMEOUT;
853         Globals.ldap_page_size = LDAP_PAGE_SIZE;
854
855         Globals.ldap_debug_level = 0;
856         Globals.ldap_debug_threshold = 10;
857
858         /* This is what we tell the afs client. in reality we set the token 
859          * to never expire, though, when this runs out the afs client will 
860          * forget the token. Set to 0 to get NEVERDATE.*/
861         Globals.afs_token_lifetime = 604800;
862         Globals.cups_connection_timeout = CUPS_DEFAULT_CONNECTION_TIMEOUT;
863
864 /* these parameters are set to defaults that are more appropriate
865    for the increasing samba install base:
866
867    as a member of the workgroup, that will possibly become a
868    _local_ master browser (lm = true).  this is opposed to a forced
869    local master browser startup (pm = true).
870
871    doesn't provide WINS server service by default (wsupp = false),
872    and doesn't provide domain master browser services by default, either.
873
874 */
875
876         Globals.show_add_printer_wizard = true;
877         Globals.os_level = 20;
878         Globals.local_master = true;
879         Globals._domain_master = Auto;  /* depending on _domain_logons */
880         Globals._domain_logons = false;
881         Globals.browse_list = true;
882         Globals.we_are_a_wins_server = false;
883         Globals.wins_proxy = false;
884
885         TALLOC_FREE(Globals.init_logon_delayed_hosts);
886         Globals.init_logon_delay = 100; /* 100 ms default delay */
887
888         Globals.wins_dns_proxy = true;
889
890         Globals.allow_trusted_domains = true;
891         string_set(Globals.ctx, &Globals.szIdmapBackend, "tdb");
892
893         string_set(Globals.ctx, &Globals.template_shell, "/bin/false");
894         string_set(Globals.ctx, &Globals.template_homedir, "/home/%D/%U");
895         string_set(Globals.ctx, &Globals.winbind_separator, "\\");
896         string_set(Globals.ctx, &Globals.winbindd_socket_directory, dyn_WINBINDD_SOCKET_DIR);
897
898         string_set(Globals.ctx, &Globals.cups_server, "");
899         string_set(Globals.ctx, &Globals.iprint_server, "");
900
901         string_set(Globals.ctx, &Globals._ctdbd_socket, "");
902
903         Globals.cluster_addresses = NULL;
904         Globals.clustering = false;
905         Globals.ctdb_timeout = 0;
906         Globals.ctdb_locktime_warn_threshold = 0;
907
908         Globals.winbind_cache_time = 300;       /* 5 minutes */
909         Globals.winbind_reconnect_delay = 30;   /* 30 seconds */
910         Globals.winbind_max_clients = 200;
911         Globals.winbind_enum_users = false;
912         Globals.winbind_enum_groups = false;
913         Globals.winbind_use_default_domain = false;
914         Globals.winbind_trusted_domains_only = false;
915         Globals.winbind_nested_groups = true;
916         Globals.winbind_expand_groups = 1;
917         Globals.winbind_nss_info = (const char **)str_list_make_v3(NULL, "template", NULL);
918         Globals.winbind_refresh_tickets = false;
919         Globals.winbind_offline_logon = false;
920
921         Globals.idmap_cache_time = 86400 * 7; /* a week by default */
922         Globals.idmap_negative_cache_time = 120; /* 2 minutes by default */
923
924         Globals.passdb_expand_explicit = false;
925
926         Globals.name_cache_timeout = 660; /* In seconds */
927
928         Globals.use_spnego = true;
929         Globals.client_use_spnego = true;
930
931         Globals.client_signing = SMB_SIGNING_DEFAULT;
932         Globals.server_signing = SMB_SIGNING_DEFAULT;
933
934         Globals.defer_sharing_violations = true;
935         Globals.smb_ports = (const char **)str_list_make_v3(NULL, SMB_PORTS, NULL);
936
937         Globals.enable_privileges = true;
938         Globals.host_msdfs        = true;
939         Globals.enable_asu_support       = false;
940
941         /* User defined shares. */
942         s = talloc_asprintf(talloc_tos(), "%s/usershares", get_dyn_STATEDIR());
943         if (s == NULL) {
944                 smb_panic("init_globals: ENOMEM");
945         }
946         string_set(Globals.ctx, &Globals.usershare_path, s);
947         TALLOC_FREE(s);
948         string_set(Globals.ctx, &Globals.usershare_template_share, "");
949         Globals.usershare_max_shares = 0;
950         /* By default disallow sharing of directories not owned by the sharer. */
951         Globals.usershare_owner_only = true;
952         /* By default disallow guest access to usershares. */
953         Globals.usershare_allow_guests = false;
954
955         Globals.keepalive = DEFAULT_KEEPALIVE;
956
957         /* By default no shares out of the registry */
958         Globals.registry_shares = false;
959
960         Globals.iminreceivefile = 0;
961
962         Globals.map_untrusted_to_domain = false;
963         Globals.multicast_dns_register = true;
964
965         Globals.smb2_max_read = DEFAULT_SMB2_MAX_READ;
966         Globals.smb2_max_write = DEFAULT_SMB2_MAX_WRITE;
967         Globals.smb2_max_trans = DEFAULT_SMB2_MAX_TRANSACT;
968         Globals.ismb2_max_credits = DEFAULT_SMB2_MAX_CREDITS;
969
970         string_set(Globals.ctx, &Globals.ncalrpc_dir, get_dyn_NCALRPCDIR());
971
972         Globals.server_services = (const char **)str_list_make_v3(NULL, "s3fs rpc nbt wrepl ldap cldap kdc drepl winbind ntp_signd kcc dnsupdate dns", NULL);
973
974         Globals.dcerpc_endpoint_servers = (const char **)str_list_make_v3(NULL, "epmapper wkssvc rpcecho samr netlogon lsarpc spoolss drsuapi dssetup unixinfo browser eventlog6 backupkey dnsserver", NULL);
975
976         Globals.tls_enabled = true;
977
978         string_set(Globals.ctx, &Globals._tls_keyfile, "tls/key.pem");
979         string_set(Globals.ctx, &Globals._tls_certfile, "tls/cert.pem");
980         string_set(Globals.ctx, &Globals._tls_cafile, "tls/ca.pem");
981
982         string_set(Globals.ctx, &Globals.share_backend, "classic");
983
984         Globals.iPreferredMaster = Auto;
985
986         Globals.allow_dns_updates = DNS_UPDATE_SIGNED;
987
988         string_set(Globals.ctx, &Globals.ntp_signd_socket_directory, get_dyn_NTP_SIGND_SOCKET_DIR());
989
990         string_set(Globals.ctx, &Globals.winbindd_privileged_socket_directory, get_dyn_WINBINDD_PRIVILEGED_SOCKET_DIR());
991
992         s = talloc_asprintf(talloc_tos(), "%s/samba_kcc", get_dyn_SCRIPTSBINDIR());
993         if (s == NULL) {
994                 smb_panic("init_globals: ENOMEM");
995         }
996         Globals.samba_kcc_command = (const char **)str_list_make_v3(NULL, s, NULL);
997         TALLOC_FREE(s);
998
999         s = talloc_asprintf(talloc_tos(), "%s/samba_dnsupdate", get_dyn_SCRIPTSBINDIR());
1000         if (s == NULL) {
1001                 smb_panic("init_globals: ENOMEM");
1002         }
1003         Globals.dns_update_command = (const char **)str_list_make_v3(NULL, s, NULL);
1004         TALLOC_FREE(s);
1005
1006         s = talloc_asprintf(talloc_tos(), "%s/samba_spnupdate", get_dyn_SCRIPTSBINDIR());
1007         if (s == NULL) {
1008                 smb_panic("init_globals: ENOMEM");
1009         }
1010         Globals.spn_update_command = (const char **)str_list_make_v3(NULL, s, NULL);
1011         TALLOC_FREE(s);
1012
1013         Globals.nsupdate_command = (const char **)str_list_make_v3(NULL, "/usr/bin/nsupdate -g", NULL);
1014
1015         Globals.rndc_command = (const char **)str_list_make_v3(NULL, "/usr/sbin/rndc", NULL);
1016
1017         Globals.cldap_port = 389;
1018
1019         Globals.dgram_port = 138;
1020
1021         Globals.nbt_port = 137;
1022
1023         Globals.krb5_port = 88;
1024
1025         Globals.kpasswd_port = 464;
1026
1027         Globals.web_port = 901;
1028
1029         /* Now put back the settings that were set with lp_set_cmdline() */
1030         apply_lp_set_cmdline();
1031 }
1032
1033 /*******************************************************************
1034  Convenience routine to grab string parameters into talloced memory
1035  and run standard_sub_basic on them. The buffers can be written to by
1036  callers without affecting the source string.
1037 ********************************************************************/
1038
1039 char *lp_string(TALLOC_CTX *ctx, const char *s)
1040 {
1041         char *ret;
1042
1043         /* The follow debug is useful for tracking down memory problems
1044            especially if you have an inner loop that is calling a lp_*()
1045            function that returns a string.  Perhaps this debug should be
1046            present all the time? */
1047
1048 #if 0
1049         DEBUG(10, ("lp_string(%s)\n", s));
1050 #endif
1051         if (!s) {
1052                 return NULL;
1053         }
1054
1055         ret = talloc_sub_basic(ctx,
1056                         get_current_username(),
1057                         current_user_info.domain,
1058                         s);
1059         if (trim_char(ret, '\"', '\"')) {
1060                 if (strchr(ret,'\"') != NULL) {
1061                         TALLOC_FREE(ret);
1062                         ret = talloc_sub_basic(ctx,
1063                                         get_current_username(),
1064                                         current_user_info.domain,
1065                                         s);
1066                 }
1067         }
1068         return ret;
1069 }
1070
1071 /*
1072    In this section all the functions that are used to access the
1073    parameters from the rest of the program are defined
1074 */
1075
1076 #define FN_GLOBAL_STRING(fn_name,ptr) \
1077 char *lp_ ## fn_name(TALLOC_CTX *ctx) {return(lp_string((ctx), *(char **)(&Globals.ptr) ? *(char **)(&Globals.ptr) : ""));}
1078 #define FN_GLOBAL_CONST_STRING(fn_name,ptr) \
1079  const char *lp_ ## fn_name(void) {return(*(const char * const *)(&Globals.ptr) ? *(const char * const *)(&Globals.ptr) : "");}
1080 #define FN_GLOBAL_LIST(fn_name,ptr) \
1081  const char **lp_ ## fn_name(void) {return(*(const char ***)(&Globals.ptr));}
1082 #define FN_GLOBAL_BOOL(fn_name,ptr) \
1083  bool lp_ ## fn_name(void) {return(*(bool *)(&Globals.ptr));}
1084 #define FN_GLOBAL_CHAR(fn_name,ptr) \
1085  char lp_ ## fn_name(void) {return(*(char *)(&Globals.ptr));}
1086 #define FN_GLOBAL_INTEGER(fn_name,ptr) \
1087  int lp_ ## fn_name(void) {return(*(int *)(&Globals.ptr));}
1088
1089 #define FN_LOCAL_STRING(fn_name,val) \
1090 char *lp_ ## fn_name(TALLOC_CTX *ctx,int i) {return(lp_string((ctx), (LP_SNUM_OK(i) && ServicePtrs[(i)]->val) ? ServicePtrs[(i)]->val : sDefault.val));}
1091 #define FN_LOCAL_CONST_STRING(fn_name,val) \
1092  const char *lp_ ## fn_name(int i) {return (const char *)((LP_SNUM_OK(i) && ServicePtrs[(i)]->val) ? ServicePtrs[(i)]->val : sDefault.val);}
1093 #define FN_LOCAL_LIST(fn_name,val) \
1094  const char **lp_ ## fn_name(int i) {return(const char **)(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1095 #define FN_LOCAL_BOOL(fn_name,val) \
1096  bool lp_ ## fn_name(int i) {return(bool)(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1097 #define FN_LOCAL_INTEGER(fn_name,val) \
1098  int lp_ ## fn_name(int i) {return(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1099
1100 #define FN_LOCAL_PARM_BOOL(fn_name,val) \
1101  bool lp_ ## fn_name(const struct share_params *p) {return(bool)(LP_SNUM_OK(p->service)? ServicePtrs[(p->service)]->val : sDefault.val);}
1102 #define FN_LOCAL_PARM_INTEGER(fn_name,val) \
1103  int lp_ ## fn_name(const struct share_params *p) {return(LP_SNUM_OK(p->service)? ServicePtrs[(p->service)]->val : sDefault.val);}
1104 #define FN_LOCAL_PARM_CHAR(fn_name,val) \
1105  char lp_ ## fn_name(const struct share_params *p) {return(LP_SNUM_OK(p->service)? ServicePtrs[(p->service)]->val : sDefault.val);}
1106
1107 static FN_GLOBAL_INTEGER(winbind_max_domain_connections_int,
1108                   winbindMaxDomainConnections)
1109
1110 int lp_winbind_max_domain_connections(void)
1111 {
1112         if (lp_winbind_offline_logon() &&
1113             lp_winbind_max_domain_connections_int() > 1) {
1114                 DEBUG(1, ("offline logons active, restricting max domain "
1115                           "connections to 1\n"));
1116                 return 1;
1117         }
1118         return MAX(1, lp_winbind_max_domain_connections_int());
1119 }
1120
1121 int lp_smb2_max_credits(void)
1122 {
1123         if (Globals.ismb2_max_credits == 0) {
1124                 Globals.ismb2_max_credits = DEFAULT_SMB2_MAX_CREDITS;
1125         }
1126         return Globals.ismb2_max_credits;
1127 }
1128 int lp_cups_encrypt(void)
1129 {
1130         int result = 0;
1131 #ifdef HAVE_HTTPCONNECTENCRYPT
1132         switch (Globals.CupsEncrypt) {
1133                 case Auto:
1134                         result = HTTP_ENCRYPT_REQUIRED;
1135                         break;
1136                 case true:
1137                         result = HTTP_ENCRYPT_ALWAYS;
1138                         break;
1139                 case false:
1140                         result = HTTP_ENCRYPT_NEVER;
1141                         break;
1142         }
1143 #endif
1144         return result;
1145 }
1146
1147 /* These functions remain in source3/param for now */
1148
1149 #include "lib/param/param_functions.c"
1150
1151 FN_LOCAL_STRING(servicename, szService)
1152 FN_LOCAL_CONST_STRING(const_servicename, szService)
1153
1154 /* These functions cannot be auto-generated */
1155 FN_LOCAL_BOOL(autoloaded, autoloaded)
1156
1157 /* local prototypes */
1158
1159 static int map_parameter_canonical(const char *pszParmName, bool *inverse);
1160 static const char *get_boolean(bool bool_value);
1161 static bool do_parameter(const char *pszParmName, const char *pszParmValue,
1162                          void *userdata);
1163 static bool do_section(const char *pszSectionName, void *userdata);
1164 static bool hash_a_service(const char *name, int number);
1165 static void free_service_byindex(int iService);
1166 static void show_parameter(int parmIndex);
1167 static bool is_synonym_of(int parm1, int parm2, bool *inverse);
1168
1169 /*
1170  * This is a helper function for parametrical options support.  It returns a
1171  * pointer to parametrical option value if it exists or NULL otherwise. Actual
1172  * parametrical functions are quite simple
1173  */
1174 static struct parmlist_entry *get_parametrics_by_service(struct loadparm_service *service, const char *type,
1175                                                          const char *option, struct parmlist_entry *global_opts)
1176 {
1177         char* param_key;
1178         struct parmlist_entry *data;
1179         TALLOC_CTX *mem_ctx = talloc_stackframe();
1180
1181         param_key = talloc_asprintf(mem_ctx, "%s:%s", type, option);
1182         if (param_key == NULL) {
1183                 DEBUG(0,("asprintf failed!\n"));
1184                 TALLOC_FREE(mem_ctx);
1185                 return NULL;
1186         }
1187
1188         /*
1189          * Try to fetch the option from the service.
1190          */
1191         if (service != NULL) {
1192                 data = service->param_opt;
1193                 while (data) {
1194                         if (strwicmp(data->key, param_key) == 0) {
1195                                 TALLOC_FREE(mem_ctx);
1196                                 return data;
1197                         }
1198                         data = data->next;
1199                 }
1200         }
1201
1202         /*
1203          * Fall back to fetching from the globals.
1204          */
1205         data = global_opts;
1206         while (data) {
1207                 if (strwicmp(data->key, param_key) == 0) {
1208                         TALLOC_FREE(mem_ctx);
1209                         return data;
1210                 }
1211                 data = data->next;
1212         }
1213
1214
1215         TALLOC_FREE(mem_ctx);
1216
1217         return NULL;
1218 }
1219
1220 /*
1221  * This is a helper function for parametrical options support.  It returns a
1222  * pointer to parametrical option value if it exists or NULL otherwise. Actual
1223  * parametrical functions are quite simple
1224  */
1225 static struct parmlist_entry *get_parametrics(int snum, const char *type,
1226                                                 const char *option)
1227 {
1228         if (snum >= iNumServices) return NULL;
1229
1230         if (snum < 0) {
1231                 return get_parametric_helper(NULL, type, option, Globals.param_opt);
1232         } else {
1233                 return get_parametric_helper(ServicePtrs[snum],
1234                                              type, option, Globals.param_opt);
1235         }
1236 }
1237
1238
1239 #define MISSING_PARAMETER(name) \
1240     DEBUG(0, ("%s(): value is NULL or empty!\n", #name))
1241
1242 /*******************************************************************
1243 convenience routine to return enum parameters.
1244 ********************************************************************/
1245 static int lp_enum(const char *s,const struct enum_list *_enum)
1246 {
1247         int i;
1248
1249         if (!s || !*s || !_enum) {
1250                 MISSING_PARAMETER(lp_enum);
1251                 return (-1);
1252         }
1253
1254         for (i=0; _enum[i].name; i++) {
1255                 if (strequal(_enum[i].name,s))
1256                         return _enum[i].value;
1257         }
1258
1259         DEBUG(0,("lp_enum(%s,enum): value is not in enum_list!\n",s));
1260         return (-1);
1261 }
1262
1263 #undef MISSING_PARAMETER
1264
1265 /* Return parametric option from a given service. Type is a part of option before ':' */
1266 /* Parametric option has following syntax: 'Type: option = value' */
1267 char *lp_parm_talloc_string(TALLOC_CTX *ctx, int snum, const char *type, const char *option, const char *def)
1268 {
1269         struct parmlist_entry *data = get_parametrics(snum, type, option);
1270
1271         if (data == NULL||data->value==NULL) {
1272                 if (def) {
1273                         return lp_string(ctx, def);
1274                 } else {
1275                         return NULL;
1276                 }
1277         }
1278
1279         return lp_string(ctx, data->value);
1280 }
1281
1282 /* Return parametric option from a given service. Type is a part of option before ':' */
1283 /* Parametric option has following syntax: 'Type: option = value' */
1284 const char *lp_parm_const_string(int snum, const char *type, const char *option, const char *def)
1285 {
1286         struct parmlist_entry *data = get_parametrics(snum, type, option);
1287
1288         if (data == NULL||data->value==NULL)
1289                 return def;
1290
1291         return data->value;
1292 }
1293
1294 const char *lp_parm_const_string_service(struct loadparm_service *service,
1295                                          const char *type, const char *option,
1296                                          const char *def)
1297 {
1298         struct parmlist_entry *data;
1299
1300         data = get_parametric_helper(service, type, option, Globals.param_opt);
1301
1302         if (data == NULL||data->value==NULL)
1303                 return def;
1304
1305         return data->value;
1306 }
1307
1308
1309 /* Return parametric option from a given service. Type is a part of option before ':' */
1310 /* Parametric option has following syntax: 'Type: option = value' */
1311
1312 const char **lp_parm_string_list(int snum, const char *type, const char *option, const char **def)
1313 {
1314         struct parmlist_entry *data = get_parametrics(snum, type, option);
1315
1316         if (data == NULL||data->value==NULL)
1317                 return (const char **)def;
1318
1319         if (data->list==NULL) {
1320                 data->list = str_list_make_v3(NULL, data->value, NULL);
1321         }
1322
1323         return (const char **)data->list;
1324 }
1325
1326 /* Return parametric option from a given service. Type is a part of option before ':' */
1327 /* Parametric option has following syntax: 'Type: option = value' */
1328
1329 int lp_parm_int(int snum, const char *type, const char *option, int def)
1330 {
1331         struct parmlist_entry *data = get_parametrics(snum, type, option);
1332
1333         if (data && data->value && *data->value)
1334                 return lp_int(data->value);
1335
1336         return def;
1337 }
1338
1339 /* Return parametric option from a given service. Type is a part of option before ':' */
1340 /* Parametric option has following syntax: 'Type: option = value' */
1341
1342 unsigned long lp_parm_ulong(int snum, const char *type, const char *option, unsigned long def)
1343 {
1344         struct parmlist_entry *data = get_parametrics(snum, type, option);
1345
1346         if (data && data->value && *data->value)
1347                 return lp_ulong(data->value);
1348
1349         return def;
1350 }
1351
1352 /* Return parametric option from a given service. Type is a part of option before ':' */
1353 /* Parametric option has following syntax: 'Type: option = value' */
1354
1355 bool lp_parm_bool(int snum, const char *type, const char *option, bool def)
1356 {
1357         struct parmlist_entry *data = get_parametrics(snum, type, option);
1358
1359         if (data && data->value && *data->value)
1360                 return lp_bool(data->value);
1361
1362         return def;
1363 }
1364
1365 /* Return parametric option from a given service. Type is a part of option before ':' */
1366 /* Parametric option has following syntax: 'Type: option = value' */
1367
1368 int lp_parm_enum(int snum, const char *type, const char *option,
1369                  const struct enum_list *_enum, int def)
1370 {
1371         struct parmlist_entry *data = get_parametrics(snum, type, option);
1372
1373         if (data && data->value && *data->value && _enum)
1374                 return lp_enum(data->value, _enum);
1375
1376         return def;
1377 }
1378
1379 /**
1380  * free a param_opts structure.
1381  * param_opts handling should be moved to talloc;
1382  * then this whole functions reduces to a TALLOC_FREE().
1383  */
1384
1385 static void free_param_opts(struct parmlist_entry **popts)
1386 {
1387         struct parmlist_entry *opt, *next_opt;
1388
1389         if (*popts != NULL) {
1390                 DEBUG(5, ("Freeing parametrics:\n"));
1391         }
1392         opt = *popts;
1393         while (opt != NULL) {
1394                 string_free(&opt->key);
1395                 string_free(&opt->value);
1396                 TALLOC_FREE(opt->list);
1397                 next_opt = opt->next;
1398                 TALLOC_FREE(opt);
1399                 opt = next_opt;
1400         }
1401         *popts = NULL;
1402 }
1403
1404 /***************************************************************************
1405  Free the dynamically allocated parts of a service struct.
1406 ***************************************************************************/
1407
1408 static void free_service(struct loadparm_service *pservice)
1409 {
1410         if (!pservice)
1411                 return;
1412
1413         if (pservice->szService)
1414                 DEBUG(5, ("free_service: Freeing service %s\n",
1415                        pservice->szService));
1416
1417         free_parameters(pservice);
1418
1419         string_free(&pservice->szService);
1420         TALLOC_FREE(pservice->copymap);
1421
1422         free_param_opts(&pservice->param_opt);
1423
1424         ZERO_STRUCTP(pservice);
1425 }
1426
1427
1428 /***************************************************************************
1429  remove a service indexed in the ServicePtrs array from the ServiceHash
1430  and free the dynamically allocated parts
1431 ***************************************************************************/
1432
1433 static void free_service_byindex(int idx)
1434 {
1435         if ( !LP_SNUM_OK(idx) ) 
1436                 return;
1437
1438         ServicePtrs[idx]->valid = false;
1439
1440         /* we have to cleanup the hash record */
1441
1442         if (ServicePtrs[idx]->szService) {
1443                 char *canon_name = canonicalize_servicename(
1444                         talloc_tos(),
1445                         ServicePtrs[idx]->szService );
1446
1447                 dbwrap_delete_bystring(ServiceHash, canon_name );
1448                 TALLOC_FREE(canon_name);
1449         }
1450
1451         free_service(ServicePtrs[idx]);
1452         talloc_free_children(ServicePtrs[idx]);
1453 }
1454
1455 /***************************************************************************
1456  Add a new service to the services array initialising it with the given 
1457  service. 
1458 ***************************************************************************/
1459
1460 static int add_a_service(const struct loadparm_service *pservice, const char *name)
1461 {
1462         int i;
1463         int num_to_alloc = iNumServices + 1;
1464         struct loadparm_service **tsp = NULL;
1465
1466         /* it might already exist */
1467         if (name) {
1468                 i = getservicebyname(name, NULL);
1469                 if (i >= 0) {
1470                         return (i);
1471                 }
1472         }
1473
1474         /* if not, then create one */
1475         i = iNumServices;
1476         tsp = talloc_realloc(NULL, ServicePtrs, struct loadparm_service *, num_to_alloc);
1477         if (tsp == NULL) {
1478                 DEBUG(0,("add_a_service: failed to enlarge ServicePtrs!\n"));
1479                 return (-1);
1480         }
1481         ServicePtrs = tsp;
1482         ServicePtrs[iNumServices] = talloc_zero(NULL, struct loadparm_service);
1483         if (!ServicePtrs[iNumServices]) {
1484                 DEBUG(0,("add_a_service: out of memory!\n"));
1485                 return (-1);
1486         }
1487         iNumServices++;
1488
1489         ServicePtrs[i]->valid = true;
1490
1491         copy_service(ServicePtrs[i], pservice, NULL);
1492         if (name)
1493                 string_set(ServicePtrs[i], &ServicePtrs[i]->szService, name);
1494
1495         DEBUG(8,("add_a_service: Creating snum = %d for %s\n", 
1496                 i, ServicePtrs[i]->szService));
1497
1498         if (!hash_a_service(ServicePtrs[i]->szService, i)) {
1499                 return (-1);
1500         }
1501
1502         return (i);
1503 }
1504
1505 /***************************************************************************
1506   Convert a string to uppercase and remove whitespaces.
1507 ***************************************************************************/
1508
1509 char *canonicalize_servicename(TALLOC_CTX *ctx, const char *src)
1510 {
1511         char *result;
1512
1513         if ( !src ) {
1514                 DEBUG(0,("canonicalize_servicename: NULL source name!\n"));
1515                 return NULL;
1516         }
1517
1518         result = talloc_strdup(ctx, src);
1519         SMB_ASSERT(result != NULL);
1520
1521         if (!strlower_m(result)) {
1522                 TALLOC_FREE(result);
1523                 return NULL;
1524         }
1525         return result;
1526 }
1527
1528 /***************************************************************************
1529   Add a name/index pair for the services array to the hash table.
1530 ***************************************************************************/
1531
1532 static bool hash_a_service(const char *name, int idx)
1533 {
1534         char *canon_name;
1535
1536         if ( !ServiceHash ) {
1537                 DEBUG(10,("hash_a_service: creating servicehash\n"));
1538                 ServiceHash = db_open_rbt(NULL);
1539                 if ( !ServiceHash ) {
1540                         DEBUG(0,("hash_a_service: open tdb servicehash failed!\n"));
1541                         return false;
1542                 }
1543         }
1544
1545         DEBUG(10,("hash_a_service: hashing index %d for service name %s\n",
1546                 idx, name));
1547
1548         canon_name = canonicalize_servicename(talloc_tos(), name );
1549
1550         dbwrap_store_bystring(ServiceHash, canon_name,
1551                               make_tdb_data((uint8 *)&idx, sizeof(idx)),
1552                               TDB_REPLACE);
1553
1554         TALLOC_FREE(canon_name);
1555
1556         return true;
1557 }
1558
1559 /***************************************************************************
1560  Add a new home service, with the specified home directory, defaults coming
1561  from service ifrom.
1562 ***************************************************************************/
1563
1564 bool lp_add_home(const char *pszHomename, int iDefaultService,
1565                  const char *user, const char *pszHomedir)
1566 {
1567         int i;
1568
1569         if (pszHomename == NULL || user == NULL || pszHomedir == NULL ||
1570                         pszHomedir[0] == '\0') {
1571                 return false;
1572         }
1573
1574         i = add_a_service(ServicePtrs[iDefaultService], pszHomename);
1575
1576         if (i < 0)
1577                 return false;
1578
1579         if (!(*(ServicePtrs[iDefaultService]->path))
1580             || strequal(ServicePtrs[iDefaultService]->path,
1581                         lp_path(talloc_tos(), GLOBAL_SECTION_SNUM))) {
1582                 string_set(ServicePtrs[i], &ServicePtrs[i]->path, pszHomedir);
1583         }
1584
1585         if (!(*(ServicePtrs[i]->comment))) {
1586                 char *comment = talloc_asprintf(talloc_tos(), "Home directory of %s", user);
1587                 if (comment == NULL) {
1588                         return false;
1589                 }
1590                 string_set(ServicePtrs[i], &ServicePtrs[i]->comment, comment);
1591                 TALLOC_FREE(comment);
1592         }
1593
1594         /* set the browseable flag from the global default */
1595
1596         ServicePtrs[i]->browseable = sDefault.browseable;
1597         ServicePtrs[i]->access_based_share_enum = sDefault.access_based_share_enum;
1598
1599         ServicePtrs[i]->autoloaded = true;
1600
1601         DEBUG(3, ("adding home's share [%s] for user '%s' at '%s'\n", pszHomename, 
1602                user, ServicePtrs[i]->path ));
1603
1604         return true;
1605 }
1606
1607 /***************************************************************************
1608  Add a new service, based on an old one.
1609 ***************************************************************************/
1610
1611 int lp_add_service(const char *pszService, int iDefaultService)
1612 {
1613         if (iDefaultService < 0) {
1614                 return add_a_service(&sDefault, pszService);
1615         }
1616
1617         return (add_a_service(ServicePtrs[iDefaultService], pszService));
1618 }
1619
1620 /***************************************************************************
1621  Add the IPC service.
1622 ***************************************************************************/
1623
1624 static bool lp_add_ipc(const char *ipc_name, bool guest_ok)
1625 {
1626         char *comment = NULL;
1627         int i = add_a_service(&sDefault, ipc_name);
1628
1629         if (i < 0)
1630                 return false;
1631
1632         comment = talloc_asprintf(talloc_tos(), "IPC Service (%s)",
1633                                   Globals.server_string);
1634         if (comment == NULL) {
1635                 return false;
1636         }
1637
1638         string_set(ServicePtrs[i], &ServicePtrs[i]->path, tmpdir());
1639         string_set(ServicePtrs[i], &ServicePtrs[i]->username, "");
1640         string_set(ServicePtrs[i], &ServicePtrs[i]->comment, comment);
1641         string_set(ServicePtrs[i], &ServicePtrs[i]->fstype, "IPC");
1642         ServicePtrs[i]->max_connections = 0;
1643         ServicePtrs[i]->bAvailable = true;
1644         ServicePtrs[i]->read_only = true;
1645         ServicePtrs[i]->guest_only = false;
1646         ServicePtrs[i]->administrative_share = true;
1647         ServicePtrs[i]->guest_ok = guest_ok;
1648         ServicePtrs[i]->printable = false;
1649         ServicePtrs[i]->browseable = sDefault.browseable;
1650
1651         DEBUG(3, ("adding IPC service\n"));
1652
1653         TALLOC_FREE(comment);
1654         return true;
1655 }
1656
1657 /***************************************************************************
1658  Add a new printer service, with defaults coming from service iFrom.
1659 ***************************************************************************/
1660
1661 bool lp_add_printer(const char *pszPrintername, int iDefaultService)
1662 {
1663         const char *comment = "From Printcap";
1664         int i = add_a_service(ServicePtrs[iDefaultService], pszPrintername);
1665
1666         if (i < 0)
1667                 return false;
1668
1669         /* note that we do NOT default the availability flag to true - */
1670         /* we take it from the default service passed. This allows all */
1671         /* dynamic printers to be disabled by disabling the [printers] */
1672         /* entry (if/when the 'available' keyword is implemented!).    */
1673
1674         /* the printer name is set to the service name. */
1675         string_set(ServicePtrs[i], &ServicePtrs[i]->_printername, pszPrintername);
1676         string_set(ServicePtrs[i], &ServicePtrs[i]->comment, comment);
1677
1678         /* set the browseable flag from the gloabl default */
1679         ServicePtrs[i]->browseable = sDefault.browseable;
1680
1681         /* Printers cannot be read_only. */
1682         ServicePtrs[i]->read_only = false;
1683         /* No oplocks on printer services. */
1684         ServicePtrs[i]->oplocks = false;
1685         /* Printer services must be printable. */
1686         ServicePtrs[i]->printable = true;
1687
1688         DEBUG(3, ("adding printer service %s\n", pszPrintername));
1689
1690         return true;
1691 }
1692
1693
1694 /***************************************************************************
1695  Check whether the given parameter name is valid.
1696  Parametric options (names containing a colon) are considered valid.
1697 ***************************************************************************/
1698
1699 bool lp_parameter_is_valid(const char *pszParmName)
1700 {
1701         return ((lpcfg_map_parameter(pszParmName) != -1) ||
1702                 (strchr(pszParmName, ':') != NULL));
1703 }
1704
1705 /***************************************************************************
1706  Check whether the given name is the name of a global parameter.
1707  Returns true for strings belonging to parameters of class
1708  P_GLOBAL, false for all other strings, also for parametric options
1709  and strings not belonging to any option.
1710 ***************************************************************************/
1711
1712 bool lp_parameter_is_global(const char *pszParmName)
1713 {
1714         int num = lpcfg_map_parameter(pszParmName);
1715
1716         if (num >= 0) {
1717                 return (parm_table[num].p_class == P_GLOBAL);
1718         }
1719
1720         return false;
1721 }
1722
1723 /**************************************************************************
1724  Check whether the given name is the canonical name of a parameter.
1725  Returns false if it is not a valid parameter Name.
1726  For parametric options, true is returned.
1727 **************************************************************************/
1728
1729 bool lp_parameter_is_canonical(const char *parm_name)
1730 {
1731         if (!lp_parameter_is_valid(parm_name)) {
1732                 return false;
1733         }
1734
1735         return (lpcfg_map_parameter(parm_name) ==
1736                 map_parameter_canonical(parm_name, NULL));
1737 }
1738
1739 /**************************************************************************
1740  Determine the canonical name for a parameter.
1741  Indicate when it is an inverse (boolean) synonym instead of a
1742  "usual" synonym.
1743 **************************************************************************/
1744
1745 bool lp_canonicalize_parameter(const char *parm_name, const char **canon_parm,
1746                                bool *inverse)
1747 {
1748         int num;
1749
1750         if (!lp_parameter_is_valid(parm_name)) {
1751                 *canon_parm = NULL;
1752                 return false;
1753         }
1754
1755         num = map_parameter_canonical(parm_name, inverse);
1756         if (num < 0) {
1757                 /* parametric option */
1758                 *canon_parm = parm_name;
1759         } else {
1760                 *canon_parm = parm_table[num].label;
1761         }
1762
1763         return true;
1764
1765 }
1766
1767 /**************************************************************************
1768  Determine the canonical name for a parameter.
1769  Turn the value given into the inverse boolean expression when
1770  the synonym is an invers boolean synonym.
1771
1772  Return true if parm_name is a valid parameter name and
1773  in case it is an invers boolean synonym, if the val string could
1774  successfully be converted to the reverse bool.
1775  Return false in all other cases.
1776 **************************************************************************/
1777
1778 bool lp_canonicalize_parameter_with_value(const char *parm_name,
1779                                           const char *val,
1780                                           const char **canon_parm,
1781                                           const char **canon_val)
1782 {
1783         int num;
1784         bool inverse;
1785
1786         if (!lp_parameter_is_valid(parm_name)) {
1787                 *canon_parm = NULL;
1788                 *canon_val = NULL;
1789                 return false;
1790         }
1791
1792         num = map_parameter_canonical(parm_name, &inverse);
1793         if (num < 0) {
1794                 /* parametric option */
1795                 *canon_parm = parm_name;
1796                 *canon_val = val;
1797         } else {
1798                 *canon_parm = parm_table[num].label;
1799                 if (inverse) {
1800                         if (!lp_invert_boolean(val, canon_val)) {
1801                                 *canon_val = NULL;
1802                                 return false;
1803                         }
1804                 } else {
1805                         *canon_val = val;
1806                 }
1807         }
1808
1809         return true;
1810 }
1811
1812 /***************************************************************************
1813  Map a parameter's string representation to the index of the canonical
1814  form of the parameter (it might be a synonym).
1815  Returns -1 if the parameter string is not recognised.
1816 ***************************************************************************/
1817
1818 static int map_parameter_canonical(const char *pszParmName, bool *inverse)
1819 {
1820         int parm_num, canon_num;
1821         bool loc_inverse = false;
1822
1823         parm_num = lpcfg_map_parameter(pszParmName);
1824         if ((parm_num < 0) || !(parm_table[parm_num].flags & FLAG_HIDE)) {
1825                 /* invalid, parametric or no canidate for synonyms ... */
1826                 goto done;
1827         }
1828
1829         for (canon_num = 0; parm_table[canon_num].label; canon_num++) {
1830                 if (is_synonym_of(parm_num, canon_num, &loc_inverse)) {
1831                         parm_num = canon_num;
1832                         goto done;
1833                 }
1834         }
1835
1836 done:
1837         if (inverse != NULL) {
1838                 *inverse = loc_inverse;
1839         }
1840         return parm_num;
1841 }
1842
1843 /***************************************************************************
1844  return true if parameter number parm1 is a synonym of parameter
1845  number parm2 (parm2 being the principal name).
1846  set inverse to true if parm1 is P_BOOLREV and parm2 is P_BOOL,
1847  false otherwise.
1848 ***************************************************************************/
1849
1850 static bool is_synonym_of(int parm1, int parm2, bool *inverse)
1851 {
1852         if ((parm_table[parm1].offset == parm_table[parm2].offset) &&
1853             (parm_table[parm1].p_class == parm_table[parm2].p_class) &&
1854             (parm_table[parm1].flags & FLAG_HIDE) &&
1855             !(parm_table[parm2].flags & FLAG_HIDE))
1856         {
1857                 if (inverse != NULL) {
1858                         if ((parm_table[parm1].type == P_BOOLREV) &&
1859                             (parm_table[parm2].type == P_BOOL))
1860                         {
1861                                 *inverse = true;
1862                         } else {
1863                                 *inverse = false;
1864                         }
1865                 }
1866                 return true;
1867         }
1868         return false;
1869 }
1870
1871 /***************************************************************************
1872  Show one parameter's name, type, [values,] and flags.
1873  (helper functions for show_parameter_list)
1874 ***************************************************************************/
1875
1876 static void show_parameter(int parmIndex)
1877 {
1878         int enumIndex, flagIndex;
1879         int parmIndex2;
1880         bool hadFlag;
1881         bool hadSyn;
1882         bool inverse;
1883         const char *type[] = { "P_BOOL", "P_BOOLREV", "P_CHAR", "P_INTEGER",
1884                 "P_OCTAL", "P_LIST", "P_STRING", "P_USTRING",
1885                 "P_ENUM", "P_SEP"};
1886         unsigned flags[] = { FLAG_BASIC, FLAG_SHARE, FLAG_PRINT, FLAG_GLOBAL,
1887                 FLAG_WIZARD, FLAG_ADVANCED, FLAG_DEVELOPER, FLAG_DEPRECATED,
1888                 FLAG_HIDE};
1889         const char *flag_names[] = { "FLAG_BASIC", "FLAG_SHARE", "FLAG_PRINT",
1890                 "FLAG_GLOBAL", "FLAG_WIZARD", "FLAG_ADVANCED", "FLAG_DEVELOPER",
1891                 "FLAG_DEPRECATED", "FLAG_HIDE", NULL};
1892
1893         printf("%s=%s", parm_table[parmIndex].label,
1894                type[parm_table[parmIndex].type]);
1895         if (parm_table[parmIndex].type == P_ENUM) {
1896                 printf(",");
1897                 for (enumIndex=0;
1898                      parm_table[parmIndex].enum_list[enumIndex].name;
1899                      enumIndex++)
1900                 {
1901                         printf("%s%s",
1902                                enumIndex ? "|" : "",
1903                                parm_table[parmIndex].enum_list[enumIndex].name);
1904                 }
1905         }
1906         printf(",");
1907         hadFlag = false;
1908         for (flagIndex=0; flag_names[flagIndex]; flagIndex++) {
1909                 if (parm_table[parmIndex].flags & flags[flagIndex]) {
1910                         printf("%s%s",
1911                                 hadFlag ? "|" : "",
1912                                 flag_names[flagIndex]);
1913                         hadFlag = true;
1914                 }
1915         }
1916
1917         /* output synonyms */
1918         hadSyn = false;
1919         for (parmIndex2=0; parm_table[parmIndex2].label; parmIndex2++) {
1920                 if (is_synonym_of(parmIndex, parmIndex2, &inverse)) {
1921                         printf(" (%ssynonym of %s)", inverse ? "inverse " : "",
1922                                parm_table[parmIndex2].label);
1923                 } else if (is_synonym_of(parmIndex2, parmIndex, &inverse)) {
1924                         if (!hadSyn) {
1925                                 printf(" (synonyms: ");
1926                                 hadSyn = true;
1927                         } else {
1928                                 printf(", ");
1929                         }
1930                         printf("%s%s", parm_table[parmIndex2].label,
1931                                inverse ? "[i]" : "");
1932                 }
1933         }
1934         if (hadSyn) {
1935                 printf(")");
1936         }
1937
1938         printf("\n");
1939 }
1940
1941 /***************************************************************************
1942  Show all parameter's name, type, [values,] and flags.
1943 ***************************************************************************/
1944
1945 void show_parameter_list(void)
1946 {
1947         int classIndex, parmIndex;
1948         const char *section_names[] = { "local", "global", NULL};
1949
1950         for (classIndex=0; section_names[classIndex]; classIndex++) {
1951                 printf("[%s]\n", section_names[classIndex]);
1952                 for (parmIndex = 0; parm_table[parmIndex].label; parmIndex++) {
1953                         if (parm_table[parmIndex].p_class == classIndex) {
1954                                 show_parameter(parmIndex);
1955                         }
1956                 }
1957         }
1958 }
1959
1960 /***************************************************************************
1961  Get the standard string representation of a boolean value ("yes" or "no")
1962 ***************************************************************************/
1963
1964 static const char *get_boolean(bool bool_value)
1965 {
1966         static const char *yes_str = "yes";
1967         static const char *no_str = "no";
1968
1969         return (bool_value ? yes_str : no_str);
1970 }
1971
1972 /***************************************************************************
1973  Provide the string of the negated boolean value associated to the boolean
1974  given as a string. Returns false if the passed string does not correctly
1975  represent a boolean.
1976 ***************************************************************************/
1977
1978 bool lp_invert_boolean(const char *str, const char **inverse_str)
1979 {
1980         bool val;
1981
1982         if (!set_boolean(str, &val)) {
1983                 return false;
1984         }
1985
1986         *inverse_str = get_boolean(!val);
1987         return true;
1988 }
1989
1990 /***************************************************************************
1991  Provide the canonical string representation of a boolean value given
1992  as a string. Return true on success, false if the string given does
1993  not correctly represent a boolean.
1994 ***************************************************************************/
1995
1996 bool lp_canonicalize_boolean(const char *str, const char**canon_str)
1997 {
1998         bool val;
1999
2000         if (!set_boolean(str, &val)) {
2001                 return false;
2002         }
2003
2004         *canon_str = get_boolean(val);
2005         return true;
2006 }
2007
2008 /***************************************************************************
2009 Find a service by name. Otherwise works like get_service.
2010 ***************************************************************************/
2011
2012 int getservicebyname(const char *pszServiceName, struct loadparm_service *pserviceDest)
2013 {
2014         int iService = -1;
2015         char *canon_name;
2016         TDB_DATA data;
2017         NTSTATUS status;
2018
2019         if (ServiceHash == NULL) {
2020                 return -1;
2021         }
2022
2023         canon_name = canonicalize_servicename(talloc_tos(), pszServiceName);
2024
2025         status = dbwrap_fetch_bystring(ServiceHash, canon_name, canon_name,
2026                                        &data);
2027
2028         if (NT_STATUS_IS_OK(status) &&
2029             (data.dptr != NULL) &&
2030             (data.dsize == sizeof(iService)))
2031         {
2032                 iService = *(int *)data.dptr;
2033         }
2034
2035         TALLOC_FREE(canon_name);
2036
2037         if ((iService != -1) && (LP_SNUM_OK(iService))
2038             && (pserviceDest != NULL)) {
2039                 copy_service(pserviceDest, ServicePtrs[iService], NULL);
2040         }
2041
2042         return (iService);
2043 }
2044
2045 /* Return a pointer to a service by name.  Unlike getservicebyname, it does not copy the service */
2046 struct loadparm_service *lp_service(const char *pszServiceName)
2047 {
2048         int iService = getservicebyname(pszServiceName, NULL);
2049         if (iService == -1 || !LP_SNUM_OK(iService)) {
2050                 return NULL;
2051         }
2052         return ServicePtrs[iService];
2053 }
2054
2055 struct loadparm_service *lp_servicebynum(int snum)
2056 {
2057         if ((snum == -1) || !LP_SNUM_OK(snum)) {
2058                 return NULL;
2059         }
2060         return ServicePtrs[snum];
2061 }
2062
2063 struct loadparm_service *lp_default_loadparm_service()
2064 {
2065         return &sDefault;
2066 }
2067
2068 /***************************************************************************
2069 Check a service for consistency. Return false if the service is in any way
2070 incomplete or faulty, else true.
2071 ***************************************************************************/
2072
2073 bool service_ok(int iService)
2074 {
2075         bool bRetval;
2076
2077         bRetval = true;
2078         if (ServicePtrs[iService]->szService[0] == '\0') {
2079                 DEBUG(0, ("The following message indicates an internal error:\n"));
2080                 DEBUG(0, ("No service name in service entry.\n"));
2081                 bRetval = false;
2082         }
2083
2084         /* The [printers] entry MUST be printable. I'm all for flexibility, but */
2085         /* I can't see why you'd want a non-printable printer service...        */
2086         if (strwicmp(ServicePtrs[iService]->szService, PRINTERS_NAME) == 0) {
2087                 if (!ServicePtrs[iService]->printable) {
2088                         DEBUG(0, ("WARNING: [%s] service MUST be printable!\n",
2089                                ServicePtrs[iService]->szService));
2090                         ServicePtrs[iService]->printable = true;
2091                 }
2092                 /* [printers] service must also be non-browsable. */
2093                 if (ServicePtrs[iService]->browseable)
2094                         ServicePtrs[iService]->browseable = false;
2095         }
2096
2097         if (ServicePtrs[iService]->path[0] == '\0' &&
2098             strwicmp(ServicePtrs[iService]->szService, HOMES_NAME) != 0 &&
2099             ServicePtrs[iService]->msdfs_proxy[0] == '\0'
2100             ) {
2101                 DEBUG(0, ("WARNING: No path in service %s - making it unavailable!\n",
2102                         ServicePtrs[iService]->szService));
2103                 ServicePtrs[iService]->bAvailable = false;
2104         }
2105
2106         /* If a service is flagged unavailable, log the fact at level 1. */
2107         if (!ServicePtrs[iService]->bAvailable)
2108                 DEBUG(1, ("NOTE: Service %s is flagged unavailable.\n",
2109                           ServicePtrs[iService]->szService));
2110
2111         return (bRetval);
2112 }
2113
2114 static struct smbconf_ctx *lp_smbconf_ctx(void)
2115 {
2116         sbcErr err;
2117         static struct smbconf_ctx *conf_ctx = NULL;
2118
2119         if (conf_ctx == NULL) {
2120                 err = smbconf_init(NULL, &conf_ctx, "registry:");
2121                 if (!SBC_ERROR_IS_OK(err)) {
2122                         DEBUG(1, ("error initializing registry configuration: "
2123                                   "%s\n", sbcErrorString(err)));
2124                         conf_ctx = NULL;
2125                 }
2126         }
2127
2128         return conf_ctx;
2129 }
2130
2131 static bool process_smbconf_service(struct smbconf_service *service)
2132 {
2133         uint32_t count;
2134         bool ret;
2135
2136         if (service == NULL) {
2137                 return false;
2138         }
2139
2140         ret = do_section(service->name, NULL);
2141         if (ret != true) {
2142                 return false;
2143         }
2144         for (count = 0; count < service->num_params; count++) {
2145                 ret = do_parameter(service->param_names[count],
2146                                    service->param_values[count],
2147                                    NULL);
2148                 if (ret != true) {
2149                         return false;
2150                 }
2151         }
2152         if (iServiceIndex >= 0) {
2153                 return service_ok(iServiceIndex);
2154         }
2155         return true;
2156 }
2157
2158 /**
2159  * load a service from registry and activate it
2160  */
2161 bool process_registry_service(const char *service_name)
2162 {
2163         sbcErr err;
2164         struct smbconf_service *service = NULL;
2165         TALLOC_CTX *mem_ctx = talloc_stackframe();
2166         struct smbconf_ctx *conf_ctx = lp_smbconf_ctx();
2167         bool ret = false;
2168
2169         if (conf_ctx == NULL) {
2170                 goto done;
2171         }
2172
2173         DEBUG(5, ("process_registry_service: service name %s\n", service_name));
2174
2175         if (!smbconf_share_exists(conf_ctx, service_name)) {
2176                 /*
2177                  * Registry does not contain data for this service (yet),
2178                  * but make sure lp_load doesn't return false.
2179                  */
2180                 ret = true;
2181                 goto done;
2182         }
2183
2184         err = smbconf_get_share(conf_ctx, mem_ctx, service_name, &service);
2185         if (!SBC_ERROR_IS_OK(err)) {
2186                 goto done;
2187         }
2188
2189         ret = process_smbconf_service(service);
2190         if (!ret) {
2191                 goto done;
2192         }
2193
2194         /* store the csn */
2195         smbconf_changed(conf_ctx, &conf_last_csn, NULL, NULL);
2196
2197 done:
2198         TALLOC_FREE(mem_ctx);
2199         return ret;
2200 }
2201
2202 /*
2203  * process_registry_globals
2204  */
2205 static bool process_registry_globals(void)
2206 {
2207         bool ret;
2208
2209         add_to_file_list(NULL, &file_lists, INCLUDE_REGISTRY_NAME, INCLUDE_REGISTRY_NAME);
2210
2211         ret = do_parameter("registry shares", "yes", NULL);
2212         if (!ret) {
2213                 return ret;
2214         }
2215
2216         return process_registry_service(GLOBAL_NAME);
2217 }
2218
2219 bool process_registry_shares(void)
2220 {
2221         sbcErr err;
2222         uint32_t count;
2223         struct smbconf_service **service = NULL;
2224         uint32_t num_shares = 0;
2225         TALLOC_CTX *mem_ctx = talloc_stackframe();
2226         struct smbconf_ctx *conf_ctx = lp_smbconf_ctx();
2227         bool ret = false;
2228
2229         if (conf_ctx == NULL) {
2230                 goto done;
2231         }
2232
2233         err = smbconf_get_config(conf_ctx, mem_ctx, &num_shares, &service);
2234         if (!SBC_ERROR_IS_OK(err)) {
2235                 goto done;
2236         }
2237
2238         ret = true;
2239
2240         for (count = 0; count < num_shares; count++) {
2241                 if (strequal(service[count]->name, GLOBAL_NAME)) {
2242                         continue;
2243                 }
2244                 ret = process_smbconf_service(service[count]);
2245                 if (!ret) {
2246                         goto done;
2247                 }
2248         }
2249
2250         /* store the csn */
2251         smbconf_changed(conf_ctx, &conf_last_csn, NULL, NULL);
2252
2253 done:
2254         TALLOC_FREE(mem_ctx);
2255         return ret;
2256 }
2257
2258 /**
2259  * reload those shares from registry that are already
2260  * activated in the services array.
2261  */
2262 static bool reload_registry_shares(void)
2263 {
2264         int i;
2265         bool ret = true;
2266
2267         for (i = 0; i < iNumServices; i++) {
2268                 if (!VALID(i)) {
2269                         continue;
2270                 }
2271
2272                 if (ServicePtrs[i]->usershare == USERSHARE_VALID) {
2273                         continue;
2274                 }
2275
2276                 ret = process_registry_service(ServicePtrs[i]->szService);
2277                 if (!ret) {
2278                         goto done;
2279                 }
2280         }
2281
2282 done:
2283         return ret;
2284 }
2285
2286
2287 #define MAX_INCLUDE_DEPTH 100
2288
2289 static uint8_t include_depth;
2290
2291 /**
2292  * Free the file lists
2293  */
2294 static void free_file_list(void)
2295 {
2296         struct file_lists *f;
2297         struct file_lists *next;
2298
2299         f = file_lists;
2300         while( f ) {
2301                 next = f->next;
2302                 TALLOC_FREE( f );
2303                 f = next;
2304         }
2305         file_lists = NULL;
2306 }
2307
2308
2309 /**
2310  * Utility function for outsiders to check if we're running on registry.
2311  */
2312 bool lp_config_backend_is_registry(void)
2313 {
2314         return (lp_config_backend() == CONFIG_BACKEND_REGISTRY);
2315 }
2316
2317 /**
2318  * Utility function to check if the config backend is FILE.
2319  */
2320 bool lp_config_backend_is_file(void)
2321 {
2322         return (lp_config_backend() == CONFIG_BACKEND_FILE);
2323 }
2324
2325 /*******************************************************************
2326  Check if a config file has changed date.
2327 ********************************************************************/
2328
2329 bool lp_file_list_changed(void)
2330 {
2331         struct file_lists *f = file_lists;
2332
2333         DEBUG(6, ("lp_file_list_changed()\n"));
2334
2335         while (f) {
2336                 time_t mod_time;
2337
2338                 if (strequal(f->name, INCLUDE_REGISTRY_NAME)) {
2339                         struct smbconf_ctx *conf_ctx = lp_smbconf_ctx();
2340
2341                         if (conf_ctx == NULL) {
2342                                 return false;
2343                         }
2344                         if (smbconf_changed(conf_ctx, &conf_last_csn, NULL,
2345                                             NULL))
2346                         {
2347                                 DEBUGADD(6, ("registry config changed\n"));
2348                                 return true;
2349                         }
2350                 } else {
2351                         char *n2 = NULL;
2352                         n2 = talloc_sub_basic(talloc_tos(),
2353                                               get_current_username(),
2354                                               current_user_info.domain,
2355                                               f->name);
2356                         if (!n2) {
2357                                 return false;
2358                         }
2359                         DEBUGADD(6, ("file %s -> %s  last mod_time: %s\n",
2360                                      f->name, n2, ctime(&f->modtime)));
2361
2362                         mod_time = file_modtime(n2);
2363
2364                         if (mod_time &&
2365                             ((f->modtime != mod_time) ||
2366                              (f->subfname == NULL) ||
2367                              (strcmp(n2, f->subfname) != 0)))
2368                         {
2369                                 DEBUGADD(6,
2370                                          ("file %s modified: %s\n", n2,
2371                                           ctime(&mod_time)));
2372                                 f->modtime = mod_time;
2373                                 TALLOC_FREE(f->subfname);
2374                                 f->subfname = talloc_strdup(f, n2);
2375                                 if (f->subfname == NULL) {
2376                                         smb_panic("talloc_strdup failed");
2377                                 }
2378                                 TALLOC_FREE(n2);
2379                                 return true;
2380                         }
2381                         TALLOC_FREE(n2);
2382                 }
2383                 f = f->next;
2384         }
2385         return false;
2386 }
2387
2388
2389 /**
2390  * Initialize iconv conversion descriptors.
2391  *
2392  * This is called the first time it is needed, and also called again
2393  * every time the configuration is reloaded, because the charset or
2394  * codepage might have changed.
2395  **/
2396 static void init_iconv(void)
2397 {
2398         global_iconv_handle = smb_iconv_handle_reinit(NULL, lp_dos_charset(),
2399                                                       lp_unix_charset(),
2400                                                       true, global_iconv_handle);
2401 }
2402
2403 /***************************************************************************
2404  Handle the include operation.
2405 ***************************************************************************/
2406 static bool bAllowIncludeRegistry = true;
2407
2408 bool lp_include(struct loadparm_context *unused, int snum, const char *pszParmValue, char **ptr)
2409 {
2410         char *fname;
2411
2412         if (include_depth >= MAX_INCLUDE_DEPTH) {
2413                 DEBUG(0, ("Error: Maximum include depth (%u) exceeded!\n",
2414                           include_depth));
2415                 return false;
2416         }
2417
2418         if (strequal(pszParmValue, INCLUDE_REGISTRY_NAME)) {
2419                 if (!bAllowIncludeRegistry) {
2420                         return true;
2421                 }
2422                 if (bInGlobalSection) {
2423                         bool ret;
2424                         include_depth++;
2425                         ret = process_registry_globals();
2426                         include_depth--;
2427                         return ret;
2428                 } else {
2429                         DEBUG(1, ("\"include = registry\" only effective "
2430                                   "in %s section\n", GLOBAL_NAME));
2431                         return false;
2432                 }
2433         }
2434
2435         fname = talloc_sub_basic(talloc_tos(), get_current_username(),
2436                                  current_user_info.domain,
2437                                  pszParmValue);
2438
2439         add_to_file_list(NULL, &file_lists, pszParmValue, fname);
2440
2441         if (snum < 0) {
2442                 string_set(Globals.ctx, ptr, fname);
2443         } else {
2444                 string_set(ServicePtrs[snum], ptr, fname);
2445         }
2446
2447         if (file_exist(fname)) {
2448                 bool ret;
2449                 include_depth++;
2450                 ret = pm_process(fname, do_section, do_parameter, NULL);
2451                 include_depth--;
2452                 TALLOC_FREE(fname);
2453                 return ret;
2454         }
2455
2456         DEBUG(2, ("Can't find include file %s\n", fname));
2457         TALLOC_FREE(fname);
2458         return true;
2459 }
2460
2461 bool lp_idmap_range(const char *domain_name, uint32_t *low, uint32_t *high)
2462 {
2463         char *config_option = NULL;
2464         const char *range = NULL;
2465         bool ret = false;
2466
2467         SMB_ASSERT(low != NULL);
2468         SMB_ASSERT(high != NULL);
2469
2470         if ((domain_name == NULL) || (domain_name[0] == '\0')) {
2471                 domain_name = "*";
2472         }
2473
2474         config_option = talloc_asprintf(talloc_tos(), "idmap config %s",
2475                                         domain_name);
2476         if (config_option == NULL) {
2477                 DEBUG(0, ("out of memory\n"));
2478                 return false;
2479         }
2480
2481         range = lp_parm_const_string(-1, config_option, "range", NULL);
2482         if (range == NULL) {
2483                 DEBUG(1, ("idmap range not specified for domain '%s'\n", domain_name));
2484                 goto done;
2485         }
2486
2487         if (sscanf(range, "%u - %u", low, high) != 2) {
2488                 DEBUG(1, ("error parsing idmap range '%s' for domain '%s'\n",
2489                           range, domain_name));
2490                 goto done;
2491         }
2492
2493         ret = true;
2494
2495 done:
2496         talloc_free(config_option);
2497         return ret;
2498
2499 }
2500
2501 bool lp_idmap_default_range(uint32_t *low, uint32_t *high)
2502 {
2503         return lp_idmap_range("*", low, high);
2504 }
2505
2506 const char *lp_idmap_backend(const char *domain_name)
2507 {
2508         char *config_option = NULL;
2509         const char *backend = NULL;
2510
2511         if ((domain_name == NULL) || (domain_name[0] == '\0')) {
2512                 domain_name = "*";
2513         }
2514
2515         config_option = talloc_asprintf(talloc_tos(), "idmap config %s",
2516                                         domain_name);
2517         if (config_option == NULL) {
2518                 DEBUG(0, ("out of memory\n"));
2519                 return false;
2520         }
2521
2522         backend = lp_parm_const_string(-1, config_option, "backend", NULL);
2523         if (backend == NULL) {
2524                 DEBUG(1, ("idmap backend not specified for domain '%s'\n", domain_name));
2525                 goto done;
2526         }
2527
2528 done:
2529         talloc_free(config_option);
2530         return backend;
2531 }
2532
2533 const char *lp_idmap_default_backend(void)
2534 {
2535         return lp_idmap_backend("*");
2536 }
2537
2538 /***************************************************************************
2539  Handle ldap suffixes - default to ldapsuffix if sub-suffixes are not defined.
2540 ***************************************************************************/
2541
2542 static const char *append_ldap_suffix(TALLOC_CTX *ctx, const char *str )
2543 {
2544         const char *suffix_string;
2545
2546         suffix_string = talloc_asprintf(ctx, "%s,%s", str,
2547                                         Globals.ldap_suffix );
2548         if ( !suffix_string ) {
2549                 DEBUG(0,("append_ldap_suffix: talloc_asprintf() failed!\n"));
2550                 return "";
2551         }
2552
2553         return suffix_string;
2554 }
2555
2556 const char *lp_ldap_machine_suffix(TALLOC_CTX *ctx)
2557 {
2558         if (Globals.szLdapMachineSuffix[0])
2559                 return append_ldap_suffix(ctx, Globals.szLdapMachineSuffix);
2560
2561         return lp_string(ctx, Globals.ldap_suffix);
2562 }
2563
2564 const char *lp_ldap_user_suffix(TALLOC_CTX *ctx)
2565 {
2566         if (Globals.szLdapUserSuffix[0])
2567                 return append_ldap_suffix(ctx, Globals.szLdapUserSuffix);
2568
2569         return lp_string(ctx, Globals.ldap_suffix);
2570 }
2571
2572 const char *lp_ldap_group_suffix(TALLOC_CTX *ctx)
2573 {
2574         if (Globals.szLdapGroupSuffix[0])
2575                 return append_ldap_suffix(ctx, Globals.szLdapGroupSuffix);
2576
2577         return lp_string(ctx, Globals.ldap_suffix);
2578 }
2579
2580 const char *lp_ldap_idmap_suffix(TALLOC_CTX *ctx)
2581 {
2582         if (Globals.szLdapIdmapSuffix[0])
2583                 return append_ldap_suffix(ctx, Globals.szLdapIdmapSuffix);
2584
2585         return lp_string(ctx, Globals.ldap_suffix);
2586 }
2587
2588 /**
2589   return the parameter pointer for a parameter
2590 */
2591 void *lp_parm_ptr(struct loadparm_service *service, struct parm_struct *parm)
2592 {
2593         if (service == NULL) {
2594                 if (parm->p_class == P_LOCAL)
2595                         return (void *)(((char *)&sDefault)+parm->offset);
2596                 else if (parm->p_class == P_GLOBAL)
2597                         return (void *)(((char *)&Globals)+parm->offset);
2598                 else return NULL;
2599         } else {
2600                 return (void *)(((char *)service) + parm->offset);
2601         }
2602 }
2603
2604 /***************************************************************************
2605  Return the local pointer to a parameter given the service number and parameter
2606 ***************************************************************************/
2607
2608 void *lp_local_ptr_by_snum(int snum, struct parm_struct *parm)
2609 {
2610         return lp_parm_ptr(ServicePtrs[snum], parm);
2611 }
2612
2613 /***************************************************************************
2614  Process a parameter for a particular service number. If snum < 0
2615  then assume we are in the globals.
2616 ***************************************************************************/
2617
2618 bool lp_do_parameter(int snum, const char *pszParmName, const char *pszParmValue)
2619 {
2620         int parmnum, i;
2621         void *parm_ptr = NULL;  /* where we are going to store the result */
2622         struct parmlist_entry **opt_list;
2623         TALLOC_CTX *mem_ctx;
2624
2625         parmnum = lpcfg_map_parameter(pszParmName);
2626
2627         if (parmnum < 0) {
2628                 if (strchr(pszParmName, ':') == NULL) {
2629                         DEBUG(0, ("Ignoring unknown parameter \"%s\"\n",
2630                                   pszParmName));
2631                         return true;
2632                 }
2633
2634                 /*
2635                  * We've got a parametric option
2636                  */
2637
2638                 if (snum < 0) {
2639                         opt_list = &Globals.param_opt;
2640                         set_param_opt(NULL, opt_list, pszParmName, pszParmValue, 0);
2641                 } else {
2642                         opt_list = &ServicePtrs[snum]->param_opt;
2643                         set_param_opt(ServicePtrs[snum], opt_list, pszParmName, pszParmValue, 0);
2644                 }
2645
2646                 return true;
2647         }
2648
2649         /* if it's already been set by the command line, then we don't
2650            override here */
2651         if (parm_table[parmnum].flags & FLAG_CMDLINE) {
2652                 return true;
2653         }
2654
2655         if (parm_table[parmnum].flags & FLAG_DEPRECATED) {
2656                 DEBUG(1, ("WARNING: The \"%s\" option is deprecated\n",
2657                           pszParmName));
2658         }
2659
2660         /* we might point at a service, the default service or a global */
2661         if (snum < 0) {
2662                 parm_ptr = lp_parm_ptr(NULL, &parm_table[parmnum]);
2663         } else {
2664                 if (parm_table[parmnum].p_class == P_GLOBAL) {
2665                         DEBUG(0,
2666                               ("Global parameter %s found in service section!\n",
2667                                pszParmName));
2668                         return true;
2669                 }
2670                 parm_ptr = lp_local_ptr_by_snum(snum, &parm_table[parmnum]);
2671         }
2672
2673         if (snum >= 0) {
2674                 if (!ServicePtrs[snum]->copymap)
2675                         init_copymap(ServicePtrs[snum]);
2676
2677                 /* this handles the aliases - set the copymap for other entries with
2678                    the same data pointer */
2679                 for (i = 0; parm_table[i].label; i++) {
2680                         if ((parm_table[i].offset == parm_table[parmnum].offset)
2681                             && (parm_table[i].p_class == parm_table[parmnum].p_class)) {
2682                                 bitmap_clear(ServicePtrs[snum]->copymap, i);
2683                         }
2684                 }
2685                 mem_ctx = ServicePtrs[snum];
2686         } else {
2687                 mem_ctx = Globals.ctx;
2688         }
2689
2690         /* if it is a special case then go ahead */
2691         if (parm_table[parmnum].special) {
2692                 bool ok;
2693                 struct loadparm_context *lp_ctx = loadparm_init_s3(talloc_tos(),
2694                                                                    loadparm_s3_helpers());
2695                 lp_ctx->sDefault = &sDefault;
2696                 lp_ctx->services = ServicePtrs;
2697                 ok = parm_table[parmnum].special(lp_ctx, snum, pszParmValue,
2698                                                   (char **)parm_ptr);
2699                 TALLOC_FREE(lp_ctx);
2700
2701                 return ok;
2702         }
2703
2704         /* now switch on the type of variable it is */
2705         switch (parm_table[parmnum].type)
2706         {
2707                 case P_BOOL:
2708                         *(bool *)parm_ptr = lp_bool(pszParmValue);
2709                         break;
2710
2711                 case P_BOOLREV:
2712                         *(bool *)parm_ptr = !lp_bool(pszParmValue);
2713                         break;
2714
2715                 case P_INTEGER:
2716                         *(int *)parm_ptr = lp_int(pszParmValue);
2717                         break;
2718
2719                 case P_CHAR:
2720                         *(char *)parm_ptr = *pszParmValue;
2721                         break;
2722
2723                 case P_OCTAL:
2724                         i = sscanf(pszParmValue, "%o", (int *)parm_ptr);
2725                         if ( i != 1 ) {
2726                             DEBUG ( 0, ("Invalid octal number %s\n", pszParmName ));
2727                         }
2728                         break;
2729
2730                 case P_BYTES:
2731                 {
2732                         uint64_t val;
2733                         if (conv_str_size_error(pszParmValue, &val)) {
2734                                 if (val <= INT_MAX) {
2735                                         *(int *)parm_ptr = (int)val;
2736                                         break;
2737                                 }
2738                         }
2739
2740                         DEBUG(0,("lp_do_parameter(%s): value is not "
2741                             "a valid size specifier!\n", pszParmValue));
2742                         return false;
2743                 }
2744
2745                 case P_LIST:
2746                 case P_CMDLIST:
2747                         TALLOC_FREE(*((char ***)parm_ptr));
2748                         *(char ***)parm_ptr = str_list_make_v3(
2749                                 NULL, pszParmValue, NULL);
2750                         break;
2751
2752                 case P_STRING:
2753                         string_set(mem_ctx, (char **)parm_ptr, pszParmValue);
2754                         break;
2755
2756                 case P_USTRING:
2757                 {
2758                         char *upper_string = strupper_talloc(talloc_tos(), 
2759                                                              pszParmValue);
2760                         string_set(mem_ctx, (char **)parm_ptr, upper_string);
2761                         TALLOC_FREE(upper_string);
2762                         break;
2763                 }
2764                 case P_ENUM:
2765                         if (!lp_set_enum_parm(&parm_table[parmnum], pszParmValue, (int*)parm_ptr)) {
2766                                 return false;
2767                         }
2768                         break;
2769                 case P_SEP:
2770                         break;
2771         }
2772
2773         return true;
2774 }
2775
2776 /***************************************************************************
2777 set a parameter, marking it with FLAG_CMDLINE. Parameters marked as
2778 FLAG_CMDLINE won't be overridden by loads from smb.conf.
2779 ***************************************************************************/
2780
2781 static bool lp_set_cmdline_helper(const char *pszParmName, const char *pszParmValue)
2782 {
2783         int parmnum, i;
2784         parmnum = lpcfg_map_parameter(pszParmName);
2785         if (parmnum >= 0) {
2786                 parm_table[parmnum].flags &= ~FLAG_CMDLINE;
2787                 if (!lp_do_parameter(-1, pszParmName, pszParmValue)) {
2788                         return false;
2789                 }
2790                 parm_table[parmnum].flags |= FLAG_CMDLINE;
2791
2792                 /* we have to also set FLAG_CMDLINE on aliases.  Aliases must
2793                  * be grouped in the table, so we don't have to search the
2794                  * whole table */
2795                 for (i=parmnum-1;
2796                      i>=0 && parm_table[i].offset == parm_table[parmnum].offset
2797                              && parm_table[i].p_class == parm_table[parmnum].p_class;
2798                      i--) {
2799                         parm_table[i].flags |= FLAG_CMDLINE;
2800                 }
2801                 for (i=parmnum+1;i<num_parameters() && parm_table[i].offset == parm_table[parmnum].offset
2802                              && parm_table[i].p_class == parm_table[parmnum].p_class;i++) {
2803                         parm_table[i].flags |= FLAG_CMDLINE;
2804                 }
2805
2806                 return true;
2807         }
2808
2809         /* it might be parametric */
2810         if (strchr(pszParmName, ':') != NULL) {
2811                 set_param_opt(NULL, &Globals.param_opt, pszParmName, pszParmValue, FLAG_CMDLINE);
2812                 return true;
2813         }
2814
2815         DEBUG(0, ("Ignoring unknown parameter \"%s\"\n",  pszParmName));
2816         return false;
2817 }
2818
2819 bool lp_set_cmdline(const char *pszParmName, const char *pszParmValue)
2820 {
2821         bool ret;
2822         TALLOC_CTX *frame = talloc_stackframe();
2823
2824         ret = lp_set_cmdline_helper(pszParmName, pszParmValue);
2825         if (ret) {
2826                 store_lp_set_cmdline(pszParmName, pszParmValue);
2827         }
2828
2829         TALLOC_FREE(frame);
2830         return ret;
2831 }
2832
2833 /***************************************************************************
2834  Process a parameter.
2835 ***************************************************************************/
2836
2837 static bool do_parameter(const char *pszParmName, const char *pszParmValue,
2838                          void *userdata)
2839 {
2840         if (!bInGlobalSection && bGlobalOnly)
2841                 return true;
2842
2843         DEBUGADD(4, ("doing parameter %s = %s\n", pszParmName, pszParmValue));
2844
2845         return (lp_do_parameter(bInGlobalSection ? -2 : iServiceIndex,
2846                                 pszParmName, pszParmValue));
2847 }
2848
2849 /***************************************************************************
2850  Initialize any local variables in the sDefault table, after parsing a
2851  [globals] section.
2852 ***************************************************************************/
2853
2854 static void init_locals(void)
2855 {
2856         /*
2857          * We run this check once the [globals] is parsed, to force
2858          * the VFS objects and other per-share settings we need for
2859          * the standard way a AD DC is operated.  We may change these
2860          * as our code evolves, which is why we force these settings.
2861          *
2862          * We can't do this at the end of lp_load_ex(), as by that
2863          * point the services have been loaded and they will already
2864          * have "" as their vfs objects.
2865          */
2866         if (lp_server_role() == ROLE_ACTIVE_DIRECTORY_DC) {
2867                 const char **vfs_objects = lp_vfs_objects(-1);
2868                 if (!vfs_objects || !vfs_objects[0]) {
2869                         if (lp_parm_const_string(-1, "xattr_tdb", "file", NULL)) {
2870                                 lp_do_parameter(-1, "vfs objects", "dfs_samba4 acl_xattr xattr_tdb");
2871                         } else if (lp_parm_const_string(-1, "posix", "eadb", NULL)) {
2872                                 lp_do_parameter(-1, "vfs objects", "dfs_samba4 acl_xattr posix_eadb");
2873                         } else {
2874                                 lp_do_parameter(-1, "vfs objects", "dfs_samba4 acl_xattr");
2875                         }
2876                 }
2877
2878                 lp_do_parameter(-1, "map hidden", "no");
2879                 lp_do_parameter(-1, "map system", "no");
2880                 lp_do_parameter(-1, "map readonly", "no");
2881                 lp_do_parameter(-1, "map archive", "no");
2882                 lp_do_parameter(-1, "store dos attributes", "yes");
2883         }
2884 }
2885
2886 /***************************************************************************
2887  Process a new section (service). At this stage all sections are services.
2888  Later we'll have special sections that permit server parameters to be set.
2889  Returns true on success, false on failure.
2890 ***************************************************************************/
2891
2892 static bool do_section(const char *pszSectionName, void *userdata)
2893 {
2894         bool bRetval;
2895         bool isglobal = ((strwicmp(pszSectionName, GLOBAL_NAME) == 0) ||
2896                          (strwicmp(pszSectionName, GLOBAL_NAME2) == 0));
2897         bRetval = false;
2898
2899         /* if we were in a global section then do the local inits */
2900         if (bInGlobalSection && !isglobal)
2901                 init_locals();
2902
2903         /* if we've just struck a global section, note the fact. */
2904         bInGlobalSection = isglobal;
2905
2906         /* check for multiple global sections */
2907         if (bInGlobalSection) {
2908                 DEBUG(3, ("Processing section \"[%s]\"\n", pszSectionName));
2909                 return true;
2910         }
2911
2912         if (!bInGlobalSection && bGlobalOnly)
2913                 return true;
2914
2915         /* if we have a current service, tidy it up before moving on */
2916         bRetval = true;
2917
2918         if (iServiceIndex >= 0)
2919                 bRetval = service_ok(iServiceIndex);
2920
2921         /* if all is still well, move to the next record in the services array */
2922         if (bRetval) {
2923                 /* We put this here to avoid an odd message order if messages are */
2924                 /* issued by the post-processing of a previous section. */
2925                 DEBUG(2, ("Processing section \"[%s]\"\n", pszSectionName));
2926
2927                 iServiceIndex = add_a_service(&sDefault, pszSectionName);
2928                 if (iServiceIndex < 0) {
2929                         DEBUG(0, ("Failed to add a new service\n"));
2930                         return false;
2931                 }
2932                 /* Clean all parametric options for service */
2933                 /* They will be added during parsing again */
2934                 free_param_opts(&ServicePtrs[iServiceIndex]->param_opt);
2935         }
2936
2937         return bRetval;
2938 }
2939
2940
2941 /***************************************************************************
2942  Determine if a partcular base parameter is currentl set to the default value.
2943 ***************************************************************************/
2944
2945 static bool is_default(int i)
2946 {
2947         switch (parm_table[i].type) {
2948                 case P_LIST:
2949                 case P_CMDLIST:
2950                         return str_list_equal((const char * const *)parm_table[i].def.lvalue,
2951                                               *(const char ***)lp_parm_ptr(NULL, 
2952                                                                            &parm_table[i]));
2953                 case P_STRING:
2954                 case P_USTRING:
2955                         return strequal(parm_table[i].def.svalue,
2956                                         *(char **)lp_parm_ptr(NULL, 
2957                                                               &parm_table[i]));
2958                 case P_BOOL:
2959                 case P_BOOLREV:
2960                         return parm_table[i].def.bvalue ==
2961                                 *(bool *)lp_parm_ptr(NULL, 
2962                                                      &parm_table[i]);
2963                 case P_CHAR:
2964                         return parm_table[i].def.cvalue ==
2965                                 *(char *)lp_parm_ptr(NULL, 
2966                                                      &parm_table[i]);
2967                 case P_INTEGER:
2968                 case P_OCTAL:
2969                 case P_ENUM:
2970                 case P_BYTES:
2971                         return parm_table[i].def.ivalue ==
2972                                 *(int *)lp_parm_ptr(NULL, 
2973                                                     &parm_table[i]);
2974                 case P_SEP:
2975                         break;
2976         }
2977         return false;
2978 }
2979
2980 /***************************************************************************
2981 Display the contents of the global structure.
2982 ***************************************************************************/
2983
2984 static void dump_globals(FILE *f)
2985 {
2986         int i;
2987         struct parmlist_entry *data;
2988
2989         fprintf(f, "[global]\n");
2990
2991         for (i = 0; parm_table[i].label; i++)
2992                 if (parm_table[i].p_class == P_GLOBAL &&
2993                     !(parm_table[i].flags & FLAG_META) &&
2994                     (i == 0 || (parm_table[i].offset != parm_table[i - 1].offset))) {
2995                         if (defaults_saved && is_default(i))
2996                                 continue;
2997                         fprintf(f, "\t%s = ", parm_table[i].label);
2998                         lpcfg_print_parameter(&parm_table[i], lp_parm_ptr(NULL,
2999                                                                           &parm_table[i]),
3000                                         f);
3001                         fprintf(f, "\n");
3002         }
3003         if (Globals.param_opt != NULL) {
3004                 data = Globals.param_opt;
3005                 while(data) {
3006                         fprintf(f, "\t%s = %s\n", data->key, data->value);
3007                         data = data->next;
3008                 }
3009         }
3010
3011 }
3012
3013 /***************************************************************************
3014  Display the contents of a single services record.
3015 ***************************************************************************/
3016
3017 static void dump_a_service(struct loadparm_service *pService, FILE * f, bool show_defaults)
3018 {
3019         return lpcfg_dump_a_service(pService, &sDefault, f, NULL, show_defaults);
3020 }
3021
3022 /***************************************************************************
3023  Display the contents of a parameter of a single services record.
3024 ***************************************************************************/
3025
3026 bool dump_a_parameter(int snum, char *parm_name, FILE * f, bool isGlobal)
3027 {
3028         bool result = false;
3029
3030         struct loadparm_context *lp_ctx;
3031
3032         lp_ctx = loadparm_init_s3(talloc_tos(), loadparm_s3_helpers());
3033         if (lp_ctx == NULL) {
3034                 return false;
3035         }
3036
3037         if (isGlobal) {
3038                 result = lpcfg_dump_a_parameter(lp_ctx, NULL, parm_name, f);
3039         } else {
3040                 result = lpcfg_dump_a_parameter(lp_ctx, ServicePtrs[snum], parm_name, f);
3041         }
3042         TALLOC_FREE(lp_ctx);
3043         return result;
3044 }
3045
3046 /***************************************************************************
3047  Return info about the requested parameter (given as a string).
3048  Return NULL when the string is not a valid parameter name.
3049 ***************************************************************************/
3050
3051 struct parm_struct *lp_get_parameter(const char *param_name)
3052 {
3053         int num = lpcfg_map_parameter(param_name);
3054
3055         if (num < 0) {
3056                 return NULL;
3057         }
3058
3059         return &parm_table[num];
3060 }
3061
3062 #if 0
3063 /***************************************************************************
3064  Display the contents of a single copy structure.
3065 ***************************************************************************/
3066 static void dump_copy_map(bool *pcopymap)
3067 {
3068         int i;
3069         if (!pcopymap)
3070                 return;
3071
3072         printf("\n\tNon-Copied parameters:\n");
3073
3074         for (i = 0; parm_table[i].label; i++)
3075                 if (parm_table[i].p_class == P_LOCAL &&
3076                     parm_table[i].ptr && !pcopymap[i] &&
3077                     (i == 0 || (parm_table[i].ptr != parm_table[i - 1].ptr)))
3078                 {
3079                         printf("\t\t%s\n", parm_table[i].label);
3080                 }
3081 }
3082 #endif
3083
3084 /***************************************************************************
3085  Return TRUE if the passed service number is within range.
3086 ***************************************************************************/
3087
3088 bool lp_snum_ok(int iService)
3089 {
3090         return (LP_SNUM_OK(iService) && ServicePtrs[iService]->bAvailable);
3091 }
3092
3093 /***************************************************************************
3094  Auto-load some home services.
3095 ***************************************************************************/
3096
3097 static void lp_add_auto_services(char *str)
3098 {
3099         char *s;
3100         char *p;
3101         int homes;
3102         char *saveptr;
3103
3104         if (!str)
3105                 return;
3106
3107         s = talloc_strdup(talloc_tos(), str);
3108         if (!s) {
3109                 smb_panic("talloc_strdup failed");
3110                 return;
3111         }
3112
3113         homes = lp_servicenumber(HOMES_NAME);
3114
3115         for (p = strtok_r(s, LIST_SEP, &saveptr); p;
3116              p = strtok_r(NULL, LIST_SEP, &saveptr)) {
3117                 char *home;
3118
3119                 if (lp_servicenumber(p) >= 0)
3120                         continue;
3121
3122                 home = get_user_home_dir(talloc_tos(), p);
3123
3124                 if (home && home[0] && homes >= 0)
3125                         lp_add_home(p, homes, p, home);
3126
3127                 TALLOC_FREE(home);
3128         }
3129         TALLOC_FREE(s);
3130 }
3131
3132 /***************************************************************************
3133  Auto-load one printer.
3134 ***************************************************************************/
3135
3136 void lp_add_one_printer(const char *name, const char *comment,
3137                         const char *location, void *pdata)
3138 {
3139         int printers = lp_servicenumber(PRINTERS_NAME);
3140         int i;
3141
3142         if (lp_servicenumber(name) < 0) {
3143                 lp_add_printer(name, printers);
3144                 if ((i = lp_servicenumber(name)) >= 0) {
3145                         string_set(ServicePtrs[i], &ServicePtrs[i]->comment, comment);
3146                         ServicePtrs[i]->autoloaded = true;
3147                 }
3148         }
3149 }
3150
3151 /***************************************************************************
3152  Have we loaded a services file yet?
3153 ***************************************************************************/
3154
3155 bool lp_loaded(void)
3156 {
3157         return (bLoaded);
3158 }
3159
3160 /***************************************************************************
3161  Unload unused services.
3162 ***************************************************************************/
3163
3164 void lp_killunused(struct smbd_server_connection *sconn,
3165                    bool (*snumused) (struct smbd_server_connection *, int))
3166 {
3167         int i;
3168         for (i = 0; i < iNumServices; i++) {
3169                 if (!VALID(i))
3170                         continue;
3171
3172                 /* don't kill autoloaded or usershare services */
3173                 if ( ServicePtrs[i]->autoloaded ||
3174                                 ServicePtrs[i]->usershare == USERSHARE_VALID) {
3175                         continue;
3176                 }
3177
3178                 if (!snumused || !snumused(sconn, i)) {
3179                         free_service_byindex(i);
3180                 }
3181         }
3182 }
3183
3184 /**
3185  * Kill all except autoloaded and usershare services - convenience wrapper
3186  */
3187 void lp_kill_all_services(void)
3188 {
3189         lp_killunused(NULL, NULL);
3190 }
3191
3192 /***************************************************************************
3193  Unload a service.
3194 ***************************************************************************/
3195
3196 void lp_killservice(int iServiceIn)
3197 {
3198         if (VALID(iServiceIn)) {
3199                 free_service_byindex(iServiceIn);
3200         }
3201 }
3202
3203 /***************************************************************************
3204  Save the curent values of all global and sDefault parameters into the 
3205  defaults union. This allows testparm to show only the
3206  changed (ie. non-default) parameters.
3207 ***************************************************************************/
3208
3209 static void lp_save_defaults(void)
3210 {
3211         int i;
3212         for (i = 0; parm_table[i].label; i++) {
3213                 if (i > 0 && parm_table[i].offset == parm_table[i - 1].offset
3214                     && parm_table[i].p_class == parm_table[i - 1].p_class)
3215                         continue;
3216                 switch (parm_table[i].type) {
3217                         case P_LIST:
3218                         case P_CMDLIST:
3219                                 parm_table[i].def.lvalue = str_list_copy(
3220                                         NULL, *(const char ***)lp_parm_ptr(NULL, &parm_table[i]));
3221                                 break;
3222                         case P_STRING:
3223                         case P_USTRING:
3224                                 parm_table[i].def.svalue = talloc_strdup(Globals.ctx, *(char **)lp_parm_ptr(NULL, &parm_table[i]));
3225                                 if (parm_table[i].def.svalue == NULL) {
3226                                         smb_panic("talloc_strdup failed");
3227                                 }
3228                                 break;
3229                         case P_BOOL:
3230                         case P_BOOLREV:
3231                                 parm_table[i].def.bvalue =
3232                                         *(bool *)lp_parm_ptr(NULL, &parm_table[i]);
3233                                 break;
3234                         case P_CHAR:
3235                                 parm_table[i].def.cvalue =
3236                                         *(char *)lp_parm_ptr(NULL, &parm_table[i]);
3237                                 break;
3238                         case P_INTEGER:
3239                         case P_OCTAL:
3240                         case P_ENUM:
3241                         case P_BYTES:
3242                                 parm_table[i].def.ivalue =
3243                                         *(int *)lp_parm_ptr(NULL, &parm_table[i]);
3244                                 break;
3245                         case P_SEP:
3246                                 break;
3247                 }
3248         }
3249         defaults_saved = true;
3250 }
3251
3252 /***********************************************************
3253  If we should send plaintext/LANMAN passwords in the clinet
3254 ************************************************************/
3255
3256 static void set_allowed_client_auth(void)
3257 {
3258         if (Globals.client_ntlmv2_auth) {
3259                 Globals.client_lanman_auth = false;
3260         }
3261         if (!Globals.client_lanman_auth) {
3262                 Globals.client_plaintext_auth = false;
3263         }
3264 }
3265
3266 /***************************************************************************
3267  JRA.
3268  The following code allows smbd to read a user defined share file.
3269  Yes, this is my intent. Yes, I'm comfortable with that...
3270
3271  THE FOLLOWING IS SECURITY CRITICAL CODE.
3272
3273  It washes your clothes, it cleans your house, it guards you while you sleep...
3274  Do not f%^k with it....
3275 ***************************************************************************/
3276
3277 #define MAX_USERSHARE_FILE_SIZE (10*1024)
3278
3279 /***************************************************************************
3280  Check allowed stat state of a usershare file.
3281  Ensure we print out who is dicking with us so the admin can
3282  get their sorry ass fired.
3283 ***************************************************************************/
3284
3285 static bool check_usershare_stat(const char *fname,
3286                                  const SMB_STRUCT_STAT *psbuf)
3287 {
3288         if (!S_ISREG(psbuf->st_ex_mode)) {
3289                 DEBUG(0,("check_usershare_stat: file %s owned by uid %u is "
3290                         "not a regular file\n",
3291                         fname, (unsigned int)psbuf->st_ex_uid ));
3292                 return false;
3293         }
3294
3295         /* Ensure this doesn't have the other write bit set. */
3296         if (psbuf->st_ex_mode & S_IWOTH) {
3297                 DEBUG(0,("check_usershare_stat: file %s owned by uid %u allows "
3298                         "public write. Refusing to allow as a usershare file.\n",
3299                         fname, (unsigned int)psbuf->st_ex_uid ));
3300                 return false;
3301         }
3302
3303         /* Should be 10k or less. */
3304         if (psbuf->st_ex_size > MAX_USERSHARE_FILE_SIZE) {
3305                 DEBUG(0,("check_usershare_stat: file %s owned by uid %u is "
3306                         "too large (%u) to be a user share file.\n",
3307                         fname, (unsigned int)psbuf->st_ex_uid,
3308                         (unsigned int)psbuf->st_ex_size ));
3309                 return false;
3310         }
3311
3312         return true;
3313 }
3314
3315 /***************************************************************************
3316  Parse the contents of a usershare file.
3317 ***************************************************************************/
3318
3319 enum usershare_err parse_usershare_file(TALLOC_CTX *ctx,
3320                         SMB_STRUCT_STAT *psbuf,
3321                         const char *servicename,
3322                         int snum,
3323                         char **lines,
3324                         int numlines,
3325                         char **pp_sharepath,
3326                         char **pp_comment,
3327                         char **pp_cp_servicename,
3328                         struct security_descriptor **ppsd,
3329                         bool *pallow_guest)
3330 {
3331         const char **prefixallowlist = lp_usershare_prefix_allow_list();
3332         const char **prefixdenylist = lp_usershare_prefix_deny_list();
3333         int us_vers;
3334         DIR *dp;
3335         SMB_STRUCT_STAT sbuf;
3336         char *sharepath = NULL;
3337         char *comment = NULL;
3338
3339         *pp_sharepath = NULL;
3340         *pp_comment = NULL;
3341
3342         *pallow_guest = false;
3343
3344         if (numlines < 4) {
3345                 return USERSHARE_MALFORMED_FILE;
3346         }
3347
3348         if (strcmp(lines[0], "#VERSION 1") == 0) {
3349                 us_vers = 1;
3350         } else if (strcmp(lines[0], "#VERSION 2") == 0) {
3351                 us_vers = 2;
3352                 if (numlines < 5) {
3353                         return USERSHARE_MALFORMED_FILE;
3354                 }
3355         } else {
3356                 return USERSHARE_BAD_VERSION;
3357         }
3358
3359         if (strncmp(lines[1], "path=", 5) != 0) {
3360                 return USERSHARE_MALFORMED_PATH;
3361         }
3362
3363         sharepath = talloc_strdup(ctx, &lines[1][5]);
3364         if (!sharepath) {
3365                 return USERSHARE_POSIX_ERR;
3366         }
3367         trim_string(sharepath, " ", " ");
3368
3369         if (strncmp(lines[2], "comment=", 8) != 0) {
3370                 return USERSHARE_MALFORMED_COMMENT_DEF;
3371         }
3372
3373         comment = talloc_strdup(ctx, &lines[2][8]);
3374         if (!comment) {
3375                 return USERSHARE_POSIX_ERR;
3376         }
3377         trim_string(comment, " ", " ");
3378         trim_char(comment, '"', '"');
3379
3380         if (strncmp(lines[3], "usershare_acl=", 14) != 0) {
3381                 return USERSHARE_MALFORMED_ACL_DEF;
3382         }
3383
3384         if (!parse_usershare_acl(ctx, &lines[3][14], ppsd)) {
3385                 return USERSHARE_ACL_ERR;
3386         }
3387
3388         if (us_vers == 2) {
3389                 if (strncmp(lines[4], "guest_ok=", 9) != 0) {
3390                         return USERSHARE_MALFORMED_ACL_DEF;
3391                 }
3392                 if (lines[4][9] == 'y') {
3393                         *pallow_guest = true;
3394                 }
3395
3396                 /* Backwards compatible extension to file version #2. */
3397                 if (numlines > 5) {
3398                         if (strncmp(lines[5], "sharename=", 10) != 0) {
3399                                 return USERSHARE_MALFORMED_SHARENAME_DEF;
3400                         }
3401                         if (!strequal(&lines[5][10], servicename)) {
3402                                 return USERSHARE_BAD_SHARENAME;
3403                         }
3404                         *pp_cp_servicename = talloc_strdup(ctx, &lines[5][10]);
3405                         if (!*pp_cp_servicename) {
3406                                 return USERSHARE_POSIX_ERR;
3407                         }
3408                 }
3409         }
3410
3411         if (*pp_cp_servicename == NULL) {
3412                 *pp_cp_servicename = talloc_strdup(ctx, servicename);
3413                 if (!*pp_cp_servicename) {
3414                         return USERSHARE_POSIX_ERR;
3415                 }
3416         }
3417
3418         if (snum != -1 && (strcmp(sharepath, ServicePtrs[snum]->path) == 0)) {
3419                 /* Path didn't change, no checks needed. */
3420                 *pp_sharepath = sharepath;
3421                 *pp_comment = comment;
3422                 return USERSHARE_OK;
3423         }
3424
3425         /* The path *must* be absolute. */
3426         if (sharepath[0] != '/') {
3427                 DEBUG(2,("parse_usershare_file: share %s: path %s is not an absolute path.\n",
3428                         servicename, sharepath));
3429                 return USERSHARE_PATH_NOT_ABSOLUTE;
3430         }
3431
3432         /* If there is a usershare prefix deny list ensure one of these paths
3433            doesn't match the start of the user given path. */
3434         if (prefixdenylist) {
3435                 int i;
3436                 for ( i=0; prefixdenylist[i]; i++ ) {
3437                         DEBUG(10,("parse_usershare_file: share %s : checking prefixdenylist[%d]='%s' against %s\n",
3438                                 servicename, i, prefixdenylist[i], sharepath ));
3439                         if (memcmp( sharepath, prefixdenylist[i], strlen(prefixdenylist[i])) == 0) {
3440                                 DEBUG(2,("parse_usershare_file: share %s path %s starts with one of the "
3441                                         "usershare prefix deny list entries.\n",
3442                                         servicename, sharepath));
3443                                 return USERSHARE_PATH_IS_DENIED;
3444                         }
3445                 }
3446         }
3447
3448         /* If there is a usershare prefix allow list ensure one of these paths
3449            does match the start of the user given path. */
3450
3451         if (prefixallowlist) {
3452                 int i;
3453                 for ( i=0; prefixallowlist[i]; i++ ) {
3454                         DEBUG(10,("parse_usershare_file: share %s checking prefixallowlist[%d]='%s' against %s\n",
3455                                 servicename, i, prefixallowlist[i], sharepath ));
3456                         if (memcmp( sharepath, prefixallowlist[i], strlen(prefixallowlist[i])) == 0) {
3457                                 break;
3458                         }
3459                 }
3460                 if (prefixallowlist[i] == NULL) {
3461                         DEBUG(2,("parse_usershare_file: share %s path %s doesn't start with one of the "
3462                                 "usershare prefix allow list entries.\n",
3463                                 servicename, sharepath));
3464                         return USERSHARE_PATH_NOT_ALLOWED;
3465                 }
3466         }
3467
3468         /* Ensure this is pointing to a directory. */
3469         dp = opendir(sharepath);
3470
3471         if (!dp) {
3472                 DEBUG(2,("parse_usershare_file: share %s path %s is not a directory.\n",
3473                         servicename, sharepath));
3474                 return USERSHARE_PATH_NOT_DIRECTORY;
3475         }
3476
3477         /* Ensure the owner of the usershare file has permission to share
3478            this directory. */
3479
3480         if (sys_stat(sharepath, &sbuf, false) == -1) {
3481                 DEBUG(2,("parse_usershare_file: share %s : stat failed on path %s. %s\n",
3482                         servicename, sharepath, strerror(errno) ));
3483                 closedir(dp);
3484                 return USERSHARE_POSIX_ERR;
3485         }
3486
3487         closedir(dp);
3488
3489         if (!S_ISDIR(sbuf.st_ex_mode)) {
3490                 DEBUG(2,("parse_usershare_file: share %s path %s is not a directory.\n",
3491                         servicename, sharepath ));
3492                 return USERSHARE_PATH_NOT_DIRECTORY;
3493         }
3494
3495         /* Check if sharing is restricted to owner-only. */
3496         /* psbuf is the stat of the usershare definition file,
3497            sbuf is the stat of the target directory to be shared. */
3498
3499         if (lp_usershare_owner_only()) {
3500                 /* root can share anything. */
3501                 if ((psbuf->st_ex_uid != 0) && (sbuf.st_ex_uid != psbuf->st_ex_uid)) {
3502                         return USERSHARE_PATH_NOT_ALLOWED;
3503                 }
3504         }
3505
3506         *pp_sharepath = sharepath;
3507         *pp_comment = comment;
3508         return USERSHARE_OK;
3509 }
3510
3511 /***************************************************************************
3512  Deal with a usershare file.
3513  Returns:
3514         >= 0 - snum
3515         -1 - Bad name, invalid contents.
3516            - service name already existed and not a usershare, problem
3517             with permissions to share directory etc.
3518 ***************************************************************************/
3519
3520 static int process_usershare_file(const char *dir_name, const char *file_name, int snum_template)
3521 {
3522         SMB_STRUCT_STAT sbuf;
3523         SMB_STRUCT_STAT lsbuf;
3524         char *fname = NULL;
3525         char *sharepath = NULL;
3526         char *comment = NULL;
3527         char *cp_service_name = NULL;
3528         char **lines = NULL;
3529         int numlines = 0;
3530         int fd = -1;
3531         int iService = -1;
3532         TALLOC_CTX *ctx = talloc_stackframe();
3533         struct security_descriptor *psd = NULL;
3534         bool guest_ok = false;
3535         char *canon_name = NULL;
3536         bool added_service = false;
3537         int ret = -1;
3538
3539         /* Ensure share name doesn't contain invalid characters. */
3540         if (!validate_net_name(file_name, INVALID_SHARENAME_CHARS, strlen(file_name))) {
3541                 DEBUG(0,("process_usershare_file: share name %s contains "
3542                         "invalid characters (any of %s)\n",
3543                         file_name, INVALID_SHARENAME_CHARS ));
3544                 goto out;
3545         }
3546
3547         canon_name = canonicalize_servicename(ctx, file_name);
3548         if (!canon_name) {
3549                 goto out;
3550         }
3551
3552         fname = talloc_asprintf(ctx, "%s/%s", dir_name, file_name);
3553         if (!fname) {
3554                 goto out;
3555         }
3556
3557         /* Minimize the race condition by doing an lstat before we
3558            open and fstat. Ensure this isn't a symlink link. */
3559
3560         if (sys_lstat(fname, &lsbuf, false) != 0) {
3561                 DEBUG(0,("process_usershare_file: stat of %s failed. %s\n",
3562                         fname, strerror(errno) ));
3563                 goto out;
3564         }
3565
3566         /* This must be a regular file, not a symlink, directory or
3567            other strange filetype. */
3568         if (!check_usershare_stat(fname, &lsbuf)) {
3569                 goto out;
3570         }
3571
3572         {
3573                 TDB_DATA data;
3574                 NTSTATUS status;
3575
3576                 status = dbwrap_fetch_bystring(ServiceHash, canon_name,
3577                                                canon_name, &data);
3578
3579                 iService = -1;
3580
3581                 if (NT_STATUS_IS_OK(status) &&
3582                     (data.dptr != NULL) &&
3583                     (data.dsize == sizeof(iService))) {
3584                         memcpy(&iService, data.dptr, sizeof(iService));
3585                 }
3586         }
3587
3588         if (iService != -1 &&
3589             timespec_compare(&ServicePtrs[iService]->usershare_last_mod,
3590                              &lsbuf.st_ex_mtime) == 0) {
3591                 /* Nothing changed - Mark valid and return. */
3592                 DEBUG(10,("process_usershare_file: service %s not changed.\n",
3593                         canon_name ));
3594                 ServicePtrs[iService]->usershare = USERSHARE_VALID;
3595                 ret = iService;
3596                 goto out;
3597         }
3598
3599         /* Try and open the file read only - no symlinks allowed. */
3600 #ifdef O_NOFOLLOW
3601         fd = open(fname, O_RDONLY|O_NOFOLLOW, 0);
3602 #else
3603         fd = open(fname, O_RDONLY, 0);
3604 #endif
3605
3606         if (fd == -1) {
3607                 DEBUG(0,("process_usershare_file: unable to open %s. %s\n",
3608                         fname, strerror(errno) ));
3609                 goto out;
3610         }
3611
3612         /* Now fstat to be *SURE* it's a regular file. */
3613         if (sys_fstat(fd, &sbuf, false) != 0) {
3614                 close(fd);
3615                 DEBUG(0,("process_usershare_file: fstat of %s failed. %s\n",
3616                         fname, strerror(errno) ));
3617                 goto out;
3618         }
3619
3620         /* Is it the same dev/inode as was lstated ? */
3621         if (!check_same_stat(&lsbuf, &sbuf)) {
3622                 close(fd);
3623                 DEBUG(0,("process_usershare_file: fstat of %s is a different file from lstat. "
3624                         "Symlink spoofing going on ?\n", fname ));
3625                 goto out;
3626         }
3627
3628         /* This must be a regular file, not a symlink, directory or
3629            other strange filetype. */
3630         if (!check_usershare_stat(fname, &sbuf)) {
3631                 close(fd);
3632                 goto out;
3633         }
3634
3635         lines = fd_lines_load(fd, &numlines, MAX_USERSHARE_FILE_SIZE, NULL);
3636
3637         close(fd);
3638         if (lines == NULL) {
3639                 DEBUG(0,("process_usershare_file: loading file %s owned by %u failed.\n",
3640                         fname, (unsigned int)sbuf.st_ex_uid ));
3641                 goto out;
3642         }
3643
3644         if (parse_usershare_file(ctx, &sbuf, file_name,
3645                         iService, lines, numlines, &sharepath,
3646                         &comment, &cp_service_name,
3647                         &psd, &guest_ok) != USERSHARE_OK) {
3648                 goto out;
3649         }
3650
3651         /* Everything ok - add the service possibly using a template. */
3652         if (iService < 0) {
3653                 const struct loadparm_service *sp = &sDefault;
3654                 if (snum_template != -1) {
3655                         sp = ServicePtrs[snum_template];
3656                 }
3657
3658                 if ((iService = add_a_service(sp, cp_service_name)) < 0) {
3659                         DEBUG(0, ("process_usershare_file: Failed to add "
3660                                 "new service %s\n", cp_service_name));
3661                         goto out;
3662                 }
3663
3664                 added_service = true;
3665
3666                 /* Read only is controlled by usershare ACL below. */
3667                 ServicePtrs[iService]->read_only = false;
3668         }
3669
3670         /* Write the ACL of the new/modified share. */
3671         if (!set_share_security(canon_name, psd)) {
3672                  DEBUG(0, ("process_usershare_file: Failed to set share "
3673                         "security for user share %s\n",
3674                         canon_name ));
3675                 goto out;
3676         }
3677
3678         /* If from a template it may be marked invalid. */
3679         ServicePtrs[iService]->valid = true;
3680
3681         /* Set the service as a valid usershare. */
3682         ServicePtrs[iService]->usershare = USERSHARE_VALID;
3683
3684         /* Set guest access. */
3685         if (lp_usershare_allow_guests()) {
3686                 ServicePtrs[iService]->guest_ok = guest_ok;
3687         }
3688
3689         /* And note when it was loaded. */
3690         ServicePtrs[iService]->usershare_last_mod = sbuf.st_ex_mtime;
3691         string_set(ServicePtrs[iService], &ServicePtrs[iService]->path, sharepath);
3692         string_set(ServicePtrs[iService], &ServicePtrs[iService]->comment, comment);
3693
3694         ret = iService;
3695
3696   out:
3697
3698         if (ret == -1 && iService != -1 && added_service) {
3699                 lp_remove_service(iService);
3700         }
3701
3702         TALLOC_FREE(lines);
3703         TALLOC_FREE(ctx);
3704         return ret;
3705 }
3706
3707 /***************************************************************************
3708  Checks if a usershare entry has been modified since last load.
3709 ***************************************************************************/
3710
3711 static bool usershare_exists(int iService, struct timespec *last_mod)
3712 {
3713         SMB_STRUCT_STAT lsbuf;
3714         const char *usersharepath = Globals.usershare_path;
3715         char *fname;
3716
3717         fname = talloc_asprintf(talloc_tos(),
3718                                 "%s/%s",
3719                                 usersharepath,
3720                                 ServicePtrs[iService]->szService);
3721         if (fname == NULL) {
3722                 return false;
3723         }
3724
3725         if (sys_lstat(fname, &lsbuf, false) != 0) {
3726                 TALLOC_FREE(fname);
3727                 return false;
3728         }
3729
3730         if (!S_ISREG(lsbuf.st_ex_mode)) {
3731                 TALLOC_FREE(fname);
3732                 return false;
3733         }
3734
3735         TALLOC_FREE(fname);
3736         *last_mod = lsbuf.st_ex_mtime;
3737         return true;
3738 }
3739
3740 /***************************************************************************
3741  Load a usershare service by name. Returns a valid servicenumber or -1.
3742 ***************************************************************************/
3743
3744 int load_usershare_service(const char *servicename)
3745 {
3746         SMB_STRUCT_STAT sbuf;
3747         const char *usersharepath = Globals.usershare_path;
3748         int max_user_shares = Globals.usershare_max_shares;
3749         int snum_template = -1;
3750
3751         if (*usersharepath == 0 ||  max_user_shares == 0) {
3752                 return -1;
3753         }
3754
3755         if (sys_stat(usersharepath, &sbuf, false) != 0) {
3756                 DEBUG(0,("load_usershare_service: stat of %s failed. %s\n",
3757                         usersharepath, strerror(errno) ));
3758                 return -1;
3759         }
3760
3761         if (!S_ISDIR(sbuf.st_ex_mode)) {
3762                 DEBUG(0,("load_usershare_service: %s is not a directory.\n",
3763                         usersharepath ));
3764                 return -1;
3765         }
3766
3767         /*
3768          * This directory must be owned by root, and have the 't' bit set.
3769          * It also must not be writable by "other".
3770          */
3771
3772 #ifdef S_ISVTX
3773         if (sbuf.st_ex_uid != 0 || !(sbuf.st_ex_mode & S_ISVTX) || (sbuf.st_ex_mode & S_IWOTH)) {
3774 #else
3775         if (sbuf.st_ex_uid != 0 || (sbuf.st_ex_mode & S_IWOTH)) {
3776 #endif
3777                 DEBUG(0,("load_usershare_service: directory %s is not owned by root "
3778                         "or does not have the sticky bit 't' set or is writable by anyone.\n",
3779                         usersharepath ));
3780                 return -1;
3781         }
3782
3783         /* Ensure the template share exists if it's set. */
3784         if (Globals.usershare_template_share[0]) {
3785                 /* We can't use lp_servicenumber here as we are recommending that
3786                    template shares have -valid=false set. */
3787                 for (snum_template = iNumServices - 1; snum_template >= 0; snum_template--) {
3788                         if (ServicePtrs[snum_template]->szService &&
3789                                         strequal(ServicePtrs[snum_template]->szService,
3790                                                 Globals.usershare_template_share)) {
3791                                 break;
3792                         }
3793                 }
3794
3795                 if (snum_template == -1) {
3796                         DEBUG(0,("load_usershare_service: usershare template share %s "
3797                                 "does not exist.\n",
3798                                 Globals.usershare_template_share ));
3799                         return -1;
3800                 }
3801         }
3802
3803         return process_usershare_file(usersharepath, servicename, snum_template);
3804 }
3805
3806 /***************************************************************************
3807  Load all user defined shares from the user share directory.
3808  We only do this if we're enumerating the share list.
3809  This is the function that can delete usershares that have
3810  been removed.
3811 ***************************************************************************/
3812
3813 int load_usershare_shares(struct smbd_server_connection *sconn,
3814                           bool (*snumused) (struct smbd_server_connection *, int))
3815 {
3816         DIR *dp;
3817         SMB_STRUCT_STAT sbuf;
3818         struct dirent *de;
3819         int num_usershares = 0;
3820         int max_user_shares = Globals.usershare_max_shares;
3821         unsigned int num_dir_entries, num_bad_dir_entries, num_tmp_dir_entries;
3822         unsigned int allowed_bad_entries = ((2*max_user_shares)/10);
3823         unsigned int allowed_tmp_entries = ((2*max_user_shares)/10);
3824         int iService;
3825         int snum_template = -1;
3826         const char *usersharepath = Globals.usershare_path;
3827         int ret = lp_numservices();
3828         TALLOC_CTX *tmp_ctx;
3829
3830         if (max_user_shares == 0 || *usersharepath == '\0') {
3831                 return lp_numservices();
3832         }
3833
3834         if (sys_stat(usersharepath, &sbuf, false) != 0) {
3835                 DEBUG(0,("load_usershare_shares: stat of %s failed. %s\n",
3836                         usersharepath, strerror(errno) ));
3837                 return ret;
3838         }
3839
3840         /*
3841          * This directory must be owned by root, and have the 't' bit set.
3842          * It also must not be writable by "other".
3843          */
3844
3845 #ifdef S_ISVTX
3846         if (sbuf.st_ex_uid != 0 || !(sbuf.st_ex_mode & S_ISVTX) || (sbuf.st_ex_mode & S_IWOTH)) {
3847 #else
3848         if (sbuf.st_ex_uid != 0 || (sbuf.st_ex_mode & S_IWOTH)) {
3849 #endif
3850                 DEBUG(0,("load_usershare_shares: directory %s is not owned by root "
3851                         "or does not have the sticky bit 't' set or is writable by anyone.\n",
3852                         usersharepath ));
3853                 return ret;
3854         }
3855
3856         /* Ensure the template share exists if it's set. */
3857         if (Globals.usershare_template_share[0]) {
3858                 /* We can't use lp_servicenumber here as we are recommending that
3859                    template shares have -valid=false set. */
3860                 for (snum_template = iNumServices - 1; snum_template >= 0; snum_template--) {
3861                         if (ServicePtrs[snum_template]->szService &&
3862                                         strequal(ServicePtrs[snum_template]->szService,
3863                                                 Globals.usershare_template_share)) {
3864                                 break;
3865                         }
3866                 }
3867
3868                 if (snum_template == -1) {
3869                         DEBUG(0,("load_usershare_shares: usershare template share %s "
3870                                 "does not exist.\n",
3871                                 Globals.usershare_template_share ));
3872                         return ret;
3873                 }
3874         }
3875
3876         /* Mark all existing usershares as pending delete. */
3877         for (iService = iNumServices - 1; iService >= 0; iService--) {
3878                 if (VALID(iService) && ServicePtrs[iService]->usershare) {
3879                         ServicePtrs[iService]->usershare = USERSHARE_PENDING_DELETE;
3880                 }
3881         }
3882
3883         dp = opendir(usersharepath);
3884         if (!dp) {
3885                 DEBUG(0,("load_usershare_shares:: failed to open directory %s. %s\n",
3886                         usersharepath, strerror(errno) ));
3887                 return ret;
3888         }
3889
3890         for (num_dir_entries = 0, num_bad_dir_entries = 0, num_tmp_dir_entries = 0;
3891                         (de = readdir(dp));
3892                         num_dir_entries++ ) {
3893                 int r;
3894                 const char *n = de->d_name;
3895
3896                 /* Ignore . and .. */
3897                 if (*n == '.') {
3898                         if ((n[1] == '\0') || (n[1] == '.' && n[2] == '\0')) {
3899                                 continue;
3900                         }
3901                 }
3902
3903                 if (n[0] == ':') {
3904                         /* Temporary file used when creating a share. */
3905                         num_tmp_dir_entries++;
3906                 }
3907
3908                 /* Allow 20% tmp entries. */
3909                 if (num_tmp_dir_entries > allowed_tmp_entries) {
3910                         DEBUG(0,("load_usershare_shares: too many temp entries (%u) "
3911                                 "in directory %s\n",
3912                                 num_tmp_dir_entries, usersharepath));
3913                         break;
3914                 }
3915
3916                 r = process_usershare_file(usersharepath, n, snum_template);
3917                 if (r == 0) {
3918                         /* Update the services count. */
3919                         num_usershares++;
3920                         if (num_usershares >= max_user_shares) {
3921                                 DEBUG(0,("load_usershare_shares: max user shares reached "
3922                                         "on file %s in directory %s\n",
3923                                         n, usersharepath ));
3924                                 break;
3925                         }
3926                 } else if (r == -1) {
3927                         num_bad_dir_entries++;
3928                 }
3929
3930                 /* Allow 20% bad entries. */
3931                 if (num_bad_dir_entries > allowed_bad_entries) {
3932                         DEBUG(0,("load_usershare_shares: too many bad entries (%u) "
3933                                 "in directory %s\n",
3934                                 num_bad_dir_entries, usersharepath));
3935                         break;
3936                 }
3937
3938                 /* Allow 20% bad entries. */
3939                 if (num_dir_entries > max_user_shares + allowed_bad_entries) {
3940                         DEBUG(0,("load_usershare_shares: too many total entries (%u) "
3941                         "in directory %s\n",
3942                         num_dir_entries, usersharepath));
3943                         break;
3944                 }
3945         }
3946
3947         closedir(dp);
3948
3949         /* Sweep through and delete any non-refreshed usershares that are
3950            not currently in use. */
3951         tmp_ctx = talloc_stackframe();
3952         for (iService = iNumServices - 1; iService >= 0; iService--) {
3953                 if (VALID(iService) && (ServicePtrs[iService]->usershare == USERSHARE_PENDING_DELETE)) {
3954                         char *servname;
3955
3956                         if (snumused && snumused(sconn, iService)) {
3957                                 continue;
3958                         }
3959
3960                         servname = lp_servicename(tmp_ctx, iService);
3961
3962                         /* Remove from the share ACL db. */
3963                         DEBUG(10,("load_usershare_shares: Removing deleted usershare %s\n",
3964                                   servname ));
3965                         delete_share_security(servname);
3966                         free_service_byindex(iService);
3967                 }
3968         }
3969         talloc_free(tmp_ctx);
3970
3971         return lp_numservices();
3972 }
3973
3974 /********************************************************
3975  Destroy global resources allocated in this file
3976 ********************************************************/
3977
3978 void gfree_loadparm(void)
3979 {
3980         int i;
3981
3982         free_file_list();
3983
3984         /* Free resources allocated to services */
3985
3986         for ( i = 0; i < iNumServices; i++ ) {
3987                 if ( VALID(i) ) {
3988                         free_service_byindex(i);
3989                 }
3990         }
3991
3992         TALLOC_FREE( ServicePtrs );
3993         iNumServices = 0;
3994
3995         /* Now release all resources allocated to global
3996            parameters and the default service */
3997
3998         free_global_parameters();
3999 }
4000
4001
4002 /***************************************************************************
4003  Allow client apps to specify that they are a client
4004 ***************************************************************************/
4005 static void lp_set_in_client(bool b)
4006 {
4007     in_client = b;
4008 }
4009
4010
4011 /***************************************************************************
4012  Determine if we're running in a client app
4013 ***************************************************************************/
4014 static bool lp_is_in_client(void)
4015 {
4016     return in_client;
4017 }
4018
4019 /***************************************************************************
4020  Load the services array from the services file. Return true on success,
4021  false on failure.
4022 ***************************************************************************/
4023
4024 static bool lp_load_ex(const char *pszFname,
4025                        bool global_only,
4026                        bool save_defaults,
4027                        bool add_ipc,
4028                        bool initialize_globals,
4029                        bool allow_include_registry,
4030                        bool load_all_shares)
4031 {
4032         char *n2 = NULL;
4033         bool bRetval;
4034
4035         bRetval = false;
4036
4037         DEBUG(3, ("lp_load_ex: refreshing parameters\n"));
4038
4039         bInGlobalSection = true;
4040         bGlobalOnly = global_only;
4041         bAllowIncludeRegistry = allow_include_registry;
4042
4043         init_globals(initialize_globals);
4044
4045         free_file_list();
4046
4047         if (save_defaults) {
4048                 init_locals();
4049                 lp_save_defaults();
4050         }
4051
4052         if (!initialize_globals) {
4053                 free_param_opts(&Globals.param_opt);
4054                 apply_lp_set_cmdline();
4055         }
4056
4057         lp_do_parameter(-1, "idmap config * : backend", Globals.szIdmapBackend);
4058
4059         /* We get sections first, so have to start 'behind' to make up */
4060         iServiceIndex = -1;
4061
4062         if (lp_config_backend_is_file()) {
4063                 n2 = talloc_sub_basic(talloc_tos(), get_current_username(),
4064                                         current_user_info.domain,
4065                                         pszFname);
4066                 if (!n2) {
4067                         smb_panic("lp_load_ex: out of memory");
4068                 }
4069
4070                 add_to_file_list(NULL, &file_lists, pszFname, n2);
4071
4072                 bRetval = pm_process(n2, do_section, do_parameter, NULL);
4073                 TALLOC_FREE(n2);
4074
4075                 /* finish up the last section */
4076                 DEBUG(4, ("pm_process() returned %s\n", BOOLSTR(bRetval)));
4077                 if (bRetval) {
4078                         if (iServiceIndex >= 0) {
4079                                 bRetval = service_ok(iServiceIndex);
4080                         }
4081                 }
4082
4083                 if (lp_config_backend_is_registry()) {
4084                         /* config backend changed to registry in config file */
4085                         /*
4086                          * We need to use this extra global variable here to
4087                          * survive restart: init_globals uses this as a default
4088                          * for config_backend. Otherwise, init_globals would
4089                          *  send us into an endless loop here.
4090                          */
4091                         config_backend = CONFIG_BACKEND_REGISTRY;
4092                         /* start over */
4093                         DEBUG(1, ("lp_load_ex: changing to config backend "
4094                                   "registry\n"));
4095                         init_globals(true);
4096                         lp_kill_all_services();
4097                         return lp_load_ex(pszFname, global_only, save_defaults,
4098                                           add_ipc, initialize_globals,
4099                                           allow_include_registry,
4100                                           load_all_shares);
4101                 }
4102         } else if (lp_config_backend_is_registry()) {
4103                 bRetval = process_registry_globals();
4104         } else {
4105                 DEBUG(0, ("Illegal config  backend given: %d\n",
4106                           lp_config_backend()));
4107                 bRetval = false;
4108         }
4109
4110         if (bRetval && lp_registry_shares()) {
4111                 if (load_all_shares) {
4112                         bRetval = process_registry_shares();
4113                 } else {
4114                         bRetval = reload_registry_shares();
4115                 }
4116         }
4117
4118         {
4119                 char *serv = lp_auto_services(talloc_tos());
4120                 lp_add_auto_services(serv);
4121                 TALLOC_FREE(serv);
4122         }
4123
4124         if (add_ipc) {
4125                 /* When 'restrict anonymous = 2' guest connections to ipc$
4126                    are denied */
4127                 lp_add_ipc("IPC$", (lp_restrict_anonymous() < 2));
4128                 if ( lp_enable_asu_support() ) {
4129                         lp_add_ipc("ADMIN$", false);
4130                 }
4131         }
4132
4133         set_allowed_client_auth();
4134
4135         if (lp_security() == SEC_ADS && strchr(lp_password_server(), ':')) {
4136                 DEBUG(1, ("WARNING: The optional ':port' in password server = %s is deprecated\n",
4137                           lp_password_server()));
4138         }
4139
4140         bLoaded = true;
4141
4142         /* Now we check we_are_a_wins_server and set szWINSserver to 127.0.0.1 */
4143         /* if we_are_a_wins_server is true and we are in the client            */
4144         if (lp_is_in_client() && Globals.we_are_a_wins_server) {
4145                 lp_do_parameter(GLOBAL_SECTION_SNUM, "wins server", "127.0.0.1");
4146         }
4147
4148         init_iconv();
4149
4150         fault_configure(smb_panic_s3);
4151
4152         /*
4153          * We run this check once the whole smb.conf is parsed, to
4154          * force some settings for the standard way a AD DC is
4155          * operated.  We may changed these as our code evolves, which
4156          * is why we force these settings.
4157          */
4158         if (lp_server_role() == ROLE_ACTIVE_DIRECTORY_DC) {
4159                 lp_do_parameter(-1, "passdb backend", "samba_dsdb");
4160
4161                 lp_do_parameter(-1, "rpc_server:default", "external");
4162                 lp_do_parameter(-1, "rpc_server:svcctl", "embedded");
4163                 lp_do_parameter(-1, "rpc_server:srvsvc", "embedded");
4164                 lp_do_parameter(-1, "rpc_server:eventlog", "embedded");
4165                 lp_do_parameter(-1, "rpc_server:ntsvcs", "embedded");
4166                 lp_do_parameter(-1, "rpc_server:winreg", "embedded");
4167                 lp_do_parameter(-1, "rpc_server:spoolss", "embedded");
4168                 lp_do_parameter(-1, "rpc_daemon:spoolssd", "embedded");
4169                 lp_do_parameter(-1, "rpc_server:tcpip", "no");
4170         }
4171
4172         bAllowIncludeRegistry = true;
4173
4174         return (bRetval);
4175 }
4176
4177 bool lp_load(const char *pszFname,
4178              bool global_only,
4179              bool save_defaults,
4180              bool add_ipc,
4181              bool initialize_globals)
4182 {
4183         return lp_load_ex(pszFname,
4184                           global_only,
4185                           save_defaults,
4186                           add_ipc,
4187                           initialize_globals,
4188                           true,   /* allow_include_registry */
4189                           false); /* load_all_shares*/
4190 }
4191
4192 bool lp_load_initial_only(const char *pszFname)
4193 {
4194         return lp_load_ex(pszFname,
4195                           true,   /* global only */
4196                           false,  /* save_defaults */
4197                           false,  /* add_ipc */
4198                           true,   /* initialize_globals */
4199                           false,  /* allow_include_registry */
4200                           false); /* load_all_shares*/
4201 }
4202
4203 /**
4204  * most common lp_load wrapper, loading only the globals
4205  */
4206 bool lp_load_global(const char *file_name)
4207 {
4208         return lp_load_ex(file_name,
4209                           true,   /* global_only */
4210                           false,  /* save_defaults */
4211                           false,  /* add_ipc */
4212                           true,   /* initialize_globals */
4213                           true,   /* allow_include_registry */
4214                           false); /* load_all_shares*/
4215 }
4216
4217 /**
4218  * lp_load wrapper, especially for clients
4219  */
4220 bool lp_load_client(const char *file_name)
4221 {
4222         lp_set_in_client(true);
4223
4224         return lp_load_global(file_name);
4225 }
4226
4227 /**
4228  * lp_load wrapper, loading only globals, but intended
4229  * for subsequent calls, not reinitializing the globals
4230  * to default values
4231  */
4232 bool lp_load_global_no_reinit(const char *file_name)
4233 {
4234         return lp_load_ex(file_name,
4235                           true,   /* global_only */
4236                           false,  /* save_defaults */
4237                           false,  /* add_ipc */
4238                           false,  /* initialize_globals */
4239                           true,   /* allow_include_registry */
4240                           false); /* load_all_shares*/
4241 }
4242
4243 /**
4244  * lp_load wrapper, especially for clients, no reinitialization
4245  */
4246 bool lp_load_client_no_reinit(const char *file_name)
4247 {
4248         lp_set_in_client(true);
4249
4250         return lp_load_global_no_reinit(file_name);
4251 }
4252
4253 bool lp_load_with_registry_shares(const char *pszFname,
4254                                   bool global_only,
4255                                   bool save_defaults,
4256                                   bool add_ipc,
4257                                   bool initialize_globals)
4258 {
4259         return lp_load_ex(pszFname,
4260                           global_only,
4261                           save_defaults,
4262                           add_ipc,
4263                           initialize_globals,
4264                           true,  /* allow_include_registry */
4265                           true); /* load_all_shares*/
4266 }
4267
4268 /***************************************************************************
4269  Return the max number of services.
4270 ***************************************************************************/
4271
4272 int lp_numservices(void)
4273 {
4274         return (iNumServices);
4275 }
4276
4277 /***************************************************************************
4278 Display the contents of the services array in human-readable form.
4279 ***************************************************************************/
4280
4281 void lp_dump(FILE *f, bool show_defaults, int maxtoprint)
4282 {
4283         int iService;
4284
4285         if (show_defaults)
4286                 defaults_saved = false;
4287
4288         dump_globals(f);
4289
4290         dump_a_service(&sDefault, f, show_defaults);
4291
4292         for (iService = 0; iService < maxtoprint; iService++) {
4293                 fprintf(f,"\n");
4294                 lp_dump_one(f, show_defaults, iService);
4295         }
4296 }
4297
4298 /***************************************************************************
4299 Display the contents of one service in human-readable form.
4300 ***************************************************************************/
4301
4302 void lp_dump_one(FILE * f, bool show_defaults, int snum)
4303 {
4304         if (VALID(snum)) {
4305                 if (ServicePtrs[snum]->szService[0] == '\0')
4306                         return;
4307                 dump_a_service(ServicePtrs[snum], f, show_defaults);
4308         }
4309 }
4310
4311 /***************************************************************************
4312 Return the number of the service with the given name, or -1 if it doesn't
4313 exist. Note that this is a DIFFERENT ANIMAL from the internal function
4314 getservicebyname()! This works ONLY if all services have been loaded, and
4315 does not copy the found service.
4316 ***************************************************************************/
4317
4318 int lp_servicenumber(const char *pszServiceName)
4319 {
4320         int iService;
4321         fstring serviceName;
4322
4323         if (!pszServiceName) {
4324                 return GLOBAL_SECTION_SNUM;
4325         }
4326
4327         for (iService = iNumServices - 1; iService >= 0; iService--) {
4328                 if (VALID(iService) && ServicePtrs[iService]->szService) {
4329                         /*
4330                          * The substitution here is used to support %U is
4331                          * service names
4332                          */
4333                         fstrcpy(serviceName, ServicePtrs[iService]->szService);
4334                         standard_sub_basic(get_current_username(),
4335                                            current_user_info.domain,
4336                                            serviceName,sizeof(serviceName));
4337                         if (strequal(serviceName, pszServiceName)) {
4338                                 break;
4339                         }
4340                 }
4341         }
4342
4343         if (iService >= 0 && ServicePtrs[iService]->usershare == USERSHARE_VALID) {
4344                 struct timespec last_mod;
4345
4346                 if (!usershare_exists(iService, &last_mod)) {
4347                         /* Remove the share security tdb entry for it. */
4348                         delete_share_security(lp_servicename(talloc_tos(), iService));
4349                         /* Remove it from the array. */
4350                         free_service_byindex(iService);
4351                         /* Doesn't exist anymore. */
4352                         return GLOBAL_SECTION_SNUM;
4353                 }
4354
4355                 /* Has it been modified ? If so delete and reload. */
4356                 if (timespec_compare(&ServicePtrs[iService]->usershare_last_mod,
4357                                      &last_mod) < 0) {
4358                         /* Remove it from the array. */
4359                         free_service_byindex(iService);
4360                         /* and now reload it. */
4361                         iService = load_usershare_service(pszServiceName);
4362                 }
4363         }
4364
4365         if (iService < 0) {
4366                 DEBUG(7,("lp_servicenumber: couldn't find %s\n", pszServiceName));
4367                 return GLOBAL_SECTION_SNUM;
4368         }
4369
4370         return (iService);
4371 }
4372
4373 /*******************************************************************
4374  A useful volume label function. 
4375 ********************************************************************/
4376
4377 const char *volume_label(TALLOC_CTX *ctx, int snum)
4378 {
4379         char *ret;
4380         const char *label = lp_volume(ctx, snum);
4381         if (!*label) {
4382                 label = lp_servicename(ctx, snum);
4383         }
4384
4385         /* This returns a 33 byte guarenteed null terminated string. */
4386         ret = talloc_strndup(ctx, label, 32);
4387         if (!ret) {
4388                 return "";
4389         }               
4390         return ret;
4391 }
4392
4393 /*******************************************************************
4394  Get the default server type we will announce as via nmbd.
4395 ********************************************************************/
4396
4397 int lp_default_server_announce(void)
4398 {
4399         int default_server_announce = 0;
4400         default_server_announce |= SV_TYPE_WORKSTATION;
4401         default_server_announce |= SV_TYPE_SERVER;
4402         default_server_announce |= SV_TYPE_SERVER_UNIX;
4403
4404         /* note that the flag should be set only if we have a 
4405            printer service but nmbd doesn't actually load the 
4406            services so we can't tell   --jerry */
4407
4408         default_server_announce |= SV_TYPE_PRINTQ_SERVER;
4409
4410         default_server_announce |= SV_TYPE_SERVER_NT;
4411         default_server_announce |= SV_TYPE_NT;
4412
4413         switch (lp_server_role()) {
4414                 case ROLE_DOMAIN_MEMBER:
4415                         default_server_announce |= SV_TYPE_DOMAIN_MEMBER;
4416                         break;
4417                 case ROLE_DOMAIN_PDC:
4418                         default_server_announce |= SV_TYPE_DOMAIN_CTRL;
4419                         break;
4420                 case ROLE_DOMAIN_BDC:
4421                         default_server_announce |= SV_TYPE_DOMAIN_BAKCTRL;
4422                         break;
4423                 case ROLE_STANDALONE:
4424                 default:
4425                         break;
4426         }
4427         if (lp_time_server())
4428                 default_server_announce |= SV_TYPE_TIME_SOURCE;
4429
4430         if (lp_host_msdfs())
4431                 default_server_announce |= SV_TYPE_DFS_SERVER;
4432
4433         return default_server_announce;
4434 }
4435
4436 /***********************************************************
4437  If we are PDC then prefer us as DMB
4438 ************************************************************/
4439
4440 bool lp_domain_master(void)
4441 {
4442         if (Globals._domain_master == Auto)
4443                 return (lp_server_role() == ROLE_DOMAIN_PDC);
4444
4445         return (bool)Globals._domain_master;
4446 }
4447
4448 /***********************************************************
4449  If we are PDC then prefer us as DMB
4450 ************************************************************/
4451
4452 static bool lp_domain_master_true_or_auto(void)
4453 {
4454         if (Globals._domain_master) /* auto or yes */
4455                 return true;
4456
4457         return false;
4458 }
4459
4460 /***********************************************************
4461  If we are DMB then prefer us as LMB
4462 ************************************************************/
4463
4464 bool lp_preferred_master(void)
4465 {
4466         if (Globals.iPreferredMaster == Auto)
4467                 return (lp_local_master() && lp_domain_master());
4468
4469         return (bool)Globals.iPreferredMaster;
4470 }
4471
4472 /*******************************************************************
4473  Remove a service.
4474 ********************************************************************/
4475
4476 void lp_remove_service(int snum)
4477 {
4478         ServicePtrs[snum]->valid = false;
4479 }
4480
4481 const char *lp_printername(TALLOC_CTX *ctx, int snum)
4482 {
4483         const char *ret = lp__printername(ctx, snum);
4484         if (ret == NULL || *ret == '\0') {
4485                 ret = lp_const_servicename(snum);
4486         }
4487
4488         return ret;
4489 }
4490
4491
4492 /***********************************************************
4493  Allow daemons such as winbindd to fix their logfile name.
4494 ************************************************************/
4495
4496 void lp_set_logfile(const char *name)
4497 {
4498         string_set(Globals.ctx, &Globals.logfile, name);
4499         debug_set_logfile(name);
4500 }
4501
4502 /*******************************************************************
4503  Return the max print jobs per queue.
4504 ********************************************************************/
4505
4506 int lp_maxprintjobs(int snum)
4507 {
4508         int maxjobs = LP_SNUM_OK(snum) ? ServicePtrs[snum]->iMaxPrintJobs : sDefault.iMaxPrintJobs;
4509         if (maxjobs <= 0 || maxjobs >= PRINT_MAX_JOBID)
4510                 maxjobs = PRINT_MAX_JOBID - 1;
4511
4512         return maxjobs;
4513 }
4514
4515 const char *lp_printcapname(void)
4516 {
4517         if ((Globals.szPrintcapname != NULL) &&
4518             (Globals.szPrintcapname[0] != '\0'))
4519                 return Globals.szPrintcapname;
4520
4521         if (sDefault.printing == PRINT_CUPS) {
4522                 return "cups";
4523         }
4524
4525         if (sDefault.printing == PRINT_BSD)
4526                 return "/etc/printcap";
4527
4528         return PRINTCAP_NAME;
4529 }
4530
4531 static uint32 spoolss_state;
4532
4533 bool lp_disable_spoolss( void )
4534 {
4535         if ( spoolss_state == SVCCTL_STATE_UNKNOWN )
4536                 spoolss_state = lp__disable_spoolss() ? SVCCTL_STOPPED : SVCCTL_RUNNING;
4537
4538         return spoolss_state == SVCCTL_STOPPED ? true : false;
4539 }
4540
4541 void lp_set_spoolss_state( uint32 state )
4542 {
4543         SMB_ASSERT( (state == SVCCTL_STOPPED) || (state == SVCCTL_RUNNING) );
4544
4545         spoolss_state = state;
4546 }
4547
4548 uint32 lp_get_spoolss_state( void )
4549 {
4550         return lp_disable_spoolss() ? SVCCTL_STOPPED : SVCCTL_RUNNING;
4551 }
4552
4553 /*******************************************************************
4554  Ensure we don't use sendfile if server smb signing is active.
4555 ********************************************************************/
4556
4557 bool lp_use_sendfile(int snum, struct smb_signing_state *signing_state)
4558 {
4559         bool sign_active = false;
4560
4561         /* Using sendfile blows the brains out of any DOS or Win9x TCP stack... JRA. */
4562         if (get_Protocol() < PROTOCOL_NT1) {
4563                 return false;
4564         }
4565         if (signing_state) {
4566                 sign_active = smb_signing_is_active(signing_state);
4567         }
4568         return (lp__use_sendfile(snum) &&
4569                         (get_remote_arch() != RA_WIN95) &&
4570                         !sign_active);
4571 }
4572
4573 /*******************************************************************
4574  Turn off sendfile if we find the underlying OS doesn't support it.
4575 ********************************************************************/
4576
4577 void set_use_sendfile(int snum, bool val)
4578 {
4579         if (LP_SNUM_OK(snum))
4580                 ServicePtrs[snum]->_use_sendfile = val;
4581         else
4582                 sDefault._use_sendfile = val;
4583 }
4584
4585 /*******************************************************************
4586  Turn off storing DOS attributes if this share doesn't support it.
4587 ********************************************************************/
4588
4589 void set_store_dos_attributes(int snum, bool val)
4590 {
4591         if (!LP_SNUM_OK(snum))
4592                 return;
4593         ServicePtrs[(snum)]->store_dos_attributes = val;
4594 }
4595
4596 void lp_set_mangling_method(const char *new_method)
4597 {
4598         string_set(Globals.ctx, &Globals.mangling_method, new_method);
4599 }
4600
4601 /*******************************************************************
4602  Global state for POSIX pathname processing.
4603 ********************************************************************/
4604
4605 static bool posix_pathnames;
4606
4607 bool lp_posix_pathnames(void)
4608 {
4609         return posix_pathnames;
4610 }
4611
4612 /*******************************************************************
4613  Change everything needed to ensure POSIX pathname processing (currently
4614  not much).
4615 ********************************************************************/
4616
4617 void lp_set_posix_pathnames(void)
4618 {
4619         posix_pathnames = true;
4620 }
4621
4622 /*******************************************************************
4623  Global state for POSIX lock processing - CIFS unix extensions.
4624 ********************************************************************/
4625
4626 bool posix_default_lock_was_set;
4627 static enum brl_flavour posix_cifsx_locktype; /* By default 0 == WINDOWS_LOCK */
4628
4629 enum brl_flavour lp_posix_cifsu_locktype(files_struct *fsp)
4630 {
4631         if (posix_default_lock_was_set) {
4632                 return posix_cifsx_locktype;
4633         } else {
4634                 return fsp->posix_open ? POSIX_LOCK : WINDOWS_LOCK;
4635         }
4636 }
4637
4638 /*******************************************************************
4639 ********************************************************************/
4640
4641 void lp_set_posix_default_cifsx_readwrite_locktype(enum brl_flavour val)
4642 {
4643         posix_default_lock_was_set = true;
4644         posix_cifsx_locktype = val;
4645 }
4646
4647 int lp_min_receive_file_size(void)
4648 {
4649         if (Globals.iminreceivefile < 0) {
4650                 return 0;
4651         }
4652         return Globals.iminreceivefile;
4653 }
4654
4655 /*******************************************************************
4656  Safe wide links checks.
4657  This helper function always verify the validity of wide links,
4658  even after a configuration file reload.
4659 ********************************************************************/
4660
4661 static bool lp_widelinks_internal(int snum)
4662 {
4663         return (bool)(LP_SNUM_OK(snum)? ServicePtrs[(snum)]->bWidelinks :
4664                         sDefault.bWidelinks);
4665 }
4666
4667 void widelinks_warning(int snum)
4668 {
4669         if (lp_allow_insecure_wide_links()) {
4670                 return;
4671         }
4672
4673         if (lp_unix_extensions() && lp_widelinks_internal(snum)) {
4674                 DEBUG(0,("Share '%s' has wide links and unix extensions enabled. "
4675                         "These parameters are incompatible. "
4676                         "Wide links will be disabled for this share.\n",
4677                          lp_servicename(talloc_tos(), snum) ));
4678         }
4679 }
4680
4681 bool lp_widelinks(int snum)
4682 {
4683         /* wide links is always incompatible with unix extensions */
4684         if (lp_unix_extensions()) {
4685                 /*
4686                  * Unless we have "allow insecure widelinks"
4687                  * turned on.
4688                  */
4689                 if (!lp_allow_insecure_wide_links()) {
4690                         return false;
4691                 }
4692         }
4693
4694         return lp_widelinks_internal(snum);
4695 }
4696
4697 int lp_server_role(void)
4698 {
4699         return lp_find_server_role(lp__server_role(),
4700                                    lp__security(),
4701                                    lp__domain_logons(),
4702                                    lp_domain_master_true_or_auto());
4703 }
4704
4705 int lp_security(void)
4706 {
4707         return lp_find_security(lp__server_role(),
4708                                 lp__security());
4709 }
4710
4711 struct loadparm_global * get_globals(void)
4712 {
4713         return &Globals;
4714 }