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