2 Unix SMB/CIFS implementation.
3 Parameter loading functions
4 Copyright (C) Karl Auer 1993-1998
6 Largely re-written by Andrew Tridgell, September 1994
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
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.
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.
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/>.
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.
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
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
57 #include "system/filesys.h"
59 #include "lib/param/loadparm.h"
60 #include "lib/param/param.h"
62 #include "lib/smbconf/smbconf.h"
63 #include "lib/smbconf/smbconf_init.h"
66 #include "../librpc/gen_ndr/svcctl.h"
68 #include "../libcli/smb/smb_signing.h"
69 #include "dbwrap/dbwrap.h"
70 #include "dbwrap/dbwrap_rbt.h"
71 #include "../lib/util/bitmap.h"
73 #ifdef HAVE_SYS_SYSCTL_H
74 #include <sys/sysctl.h>
77 #ifdef HAVE_HTTPCONNECTENCRYPT
78 #include <cups/http.h>
83 extern userdom_struct current_user_info;
85 /* the special value for the include parameter
86 * to be interpreted not as a file name but to
87 * trigger loading of the global smb.conf options
89 #ifndef INCLUDE_REGISTRY_NAME
90 #define INCLUDE_REGISTRY_NAME "registry"
93 static bool in_client = false; /* Not in the client by default */
94 static struct smbconf_csn conf_last_csn;
96 static int config_backend = CONFIG_BACKEND_FILE;
98 /* some helpful bits */
99 #define LP_SNUM_OK(i) (((i) >= 0) && ((i) < iNumServices) && (ServicePtrs != NULL) && ServicePtrs[(i)]->valid)
100 #define VALID(i) (ServicePtrs != NULL && ServicePtrs[i]->valid)
102 #define USERSHARE_VALID 1
103 #define USERSHARE_PENDING_DELETE 2
105 static bool defaults_saved = false;
107 #include "lib/param/param_global.h"
109 static struct loadparm_global Globals;
111 /* This is a default service used to prime a services structure */
112 static struct loadparm_service sDefault =
117 .usershare_last_mod = {0, 0},
121 .invalid_users = NULL,
128 .root_preexec = NULL,
129 .root_postexec = NULL,
130 .cups_options = NULL,
131 .print_command = NULL,
133 .lprm_command = NULL,
134 .lppause_command = NULL,
135 .lpresume_command = NULL,
136 .queuepause_command = NULL,
137 .queueresume_command = NULL,
138 ._printername = NULL,
139 .printjob_username = NULL,
140 .dont_descend = NULL,
143 .magic_script = NULL,
144 .magic_output = NULL,
147 .veto_oplock_files = NULL,
157 .aio_write_behind = NULL,
158 .dfree_command = NULL,
159 .min_print_space = 0,
160 .iMaxPrintJobs = 1000,
161 .max_reported_print_jobs = 0,
162 .write_cache_size = 0,
164 .force_create_mode = 0,
165 .directory_mask = 0755,
166 .force_directory_mode = 0,
167 .max_connections = 0,
168 .default_case = CASE_LOWER,
169 .printing = DEFAULT_PRINTING,
170 .oplock_contention_limit = 2,
173 .dfree_cache_time = 0,
174 .preexec_close = false,
175 .root_preexec_close = false,
176 .case_sensitive = Auto,
177 .preserve_case = true,
178 .short_preserve_case = true,
179 .hide_dot_files = true,
180 .hide_special_files = false,
181 .hide_unreadable = false,
182 .hide_unwriteable_files = false,
184 .access_based_share_enum = false,
188 .administrative_share = false,
191 .print_notify_backchannel = false,
195 .store_dos_attributes = false,
196 .dmapi_support = false,
198 .strict_locking = Auto,
199 .posix_locking = true,
201 .kernel_oplocks = false,
202 .level2_oplocks = true,
204 .mangled_names = true,
206 .follow_symlinks = true,
207 .sync_always = false,
208 .strict_allocate = false,
209 .strict_sync = false,
210 .mangling_char = '~',
212 .delete_readonly = false,
213 .fake_oplocks = false,
214 .delete_veto_files = false,
215 .dos_filemode = false,
216 .dos_filetimes = true,
217 .dos_filetime_resolution = false,
218 .fake_directory_create_times = false,
219 .blocking_locks = true,
220 .inherit_permissions = false,
221 .inherit_acls = false,
222 .inherit_owner = false,
224 .use_client_driver = false,
225 .default_devmode = true,
226 .force_printername = false,
227 .nt_acl_support = true,
228 .force_unknown_acl_user = false,
229 ._use_sendfile = false,
230 .profile_acls = false,
231 .map_acl_inherit = false,
234 .acl_check_permissions = true,
235 .acl_map_full_control = true,
236 .acl_group_control = false,
237 .acl_allow_execute_always = false,
238 .change_notify = true,
239 .kernel_change_notify = true,
240 .allocation_roundup_size = SMB_ROUNDUP_ALLOCATION_SIZE,
243 .map_readonly = MAP_READONLY_YES,
244 .directory_name_cache_size = 100,
245 .smb_encrypt = SMB_SIGNING_DEFAULT,
246 .kernel_share_modes = true,
247 .durable_handles = true,
252 /* local variables */
253 static struct loadparm_service **ServicePtrs = NULL;
254 static int iNumServices = 0;
255 static int iServiceIndex = 0;
256 static struct db_context *ServiceHash;
257 static bool bInGlobalSection = true;
258 static bool bGlobalOnly = false;
259 static struct file_lists *file_lists = NULL;
260 static unsigned int *flags_list = NULL;
262 static void set_allowed_client_auth(void);
264 static bool lp_set_cmdline_helper(const char *pszParmName, const char *pszParmValue);
265 static void free_param_opts(struct parmlist_entry **popts);
267 /* this is used to prevent lots of mallocs of size 1 */
268 static const char null_string[] = "";
274 static void string_free(char **s)
278 if (*s == null_string)
284 Set a string value, deallocating any existing space, and allocing the space
288 static bool string_set(TALLOC_CTX *mem_ctx, char **dest,const char *src)
296 (*dest) = talloc_strdup(mem_ctx, src);
297 if ((*dest) == NULL) {
298 DEBUG(0,("Out of memory in string_init\n"));
305 bool lp_string_set(char **dest, const char *src) {
306 return string_set(Globals.ctx, dest, src);
309 /***************************************************************************
310 Initialise the sDefault parameter structure for the printer values.
311 ***************************************************************************/
313 void init_printer_values(TALLOC_CTX *ctx, struct loadparm_service *pService)
315 /* choose defaults depending on the type of printing */
316 switch (pService->printing) {
321 lpcfg_string_set(ctx, &pService->lpq_command, "lpq -P'%p'");
322 lpcfg_string_set(ctx, &pService->lprm_command, "lprm -P'%p' %j");
323 lpcfg_string_set(ctx, &pService->print_command, "lpr -r -P'%p' %s");
328 lpcfg_string_set(ctx, &pService->lpq_command, "lpq -P'%p'");
329 lpcfg_string_set(ctx, &pService->lprm_command, "lprm -P'%p' %j");
330 lpcfg_string_set(ctx, &pService->print_command, "lpr -r -P'%p' %s");
331 lpcfg_string_set(ctx, &pService->queuepause_command, "lpc stop '%p'");
332 lpcfg_string_set(ctx, &pService->queueresume_command, "lpc start '%p'");
333 lpcfg_string_set(ctx, &pService->lppause_command, "lpc hold '%p' %j");
334 lpcfg_string_set(ctx, &pService->lpresume_command, "lpc release '%p' %j");
339 /* set the lpq command to contain the destination printer
340 name only. This is used by cups_queue_get() */
341 lpcfg_string_set(ctx, &pService->lpq_command, "%p");
342 lpcfg_string_set(ctx, &pService->lprm_command, "");
343 lpcfg_string_set(ctx, &pService->print_command, "");
344 lpcfg_string_set(ctx, &pService->lppause_command, "");
345 lpcfg_string_set(ctx, &pService->lpresume_command, "");
346 lpcfg_string_set(ctx, &pService->queuepause_command, "");
347 lpcfg_string_set(ctx, &pService->queueresume_command, "");
352 lpcfg_string_set(ctx, &pService->lpq_command, "lpstat -o%p");
353 lpcfg_string_set(ctx, &pService->lprm_command, "cancel %p-%j");
354 lpcfg_string_set(ctx, &pService->print_command, "lp -c -d%p %s; rm %s");
355 lpcfg_string_set(ctx, &pService->queuepause_command, "disable %p");
356 lpcfg_string_set(ctx, &pService->queueresume_command, "enable %p");
358 lpcfg_string_set(ctx, &pService->lppause_command, "lp -i %p-%j -H hold");
359 lpcfg_string_set(ctx, &pService->lpresume_command, "lp -i %p-%j -H resume");
364 lpcfg_string_set(ctx, &pService->lpq_command, "lpq -P%p");
365 lpcfg_string_set(ctx, &pService->lprm_command, "lprm -P%p %j");
366 lpcfg_string_set(ctx, &pService->print_command, "lp -r -P%p %s");
369 #if defined(DEVELOPER) || defined(ENABLE_SELFTEST)
374 TALLOC_CTX *tmp_ctx = talloc_new(ctx);
377 tdbfile = talloc_asprintf(
378 tmp_ctx, "tdbfile=%s",
379 lp_parm_const_string(-1, "vlp", "tdbfile",
381 if (tdbfile == NULL) {
382 tdbfile="tdbfile=/tmp/vlp.tdb";
385 tmp = talloc_asprintf(tmp_ctx, "vlp %s print %%p %%s",
387 lpcfg_string_set(ctx, &pService->print_command,
388 tmp ? tmp : "vlp print %p %s");
390 tmp = talloc_asprintf(tmp_ctx, "vlp %s lpq %%p",
392 lpcfg_string_set(ctx, &pService->lpq_command,
393 tmp ? tmp : "vlp lpq %p");
395 tmp = talloc_asprintf(tmp_ctx, "vlp %s lprm %%p %%j",
397 lpcfg_string_set(ctx, &pService->lprm_command,
398 tmp ? tmp : "vlp lprm %p %j");
400 tmp = talloc_asprintf(tmp_ctx, "vlp %s lppause %%p %%j",
402 lpcfg_string_set(ctx, &pService->lppause_command,
403 tmp ? tmp : "vlp lppause %p %j");
405 tmp = talloc_asprintf(tmp_ctx, "vlp %s lpresume %%p %%j",
407 lpcfg_string_set(ctx, &pService->lpresume_command,
408 tmp ? tmp : "vlp lpresume %p %j");
410 tmp = talloc_asprintf(tmp_ctx, "vlp %s queuepause %%p",
412 lpcfg_string_set(ctx, &pService->queuepause_command,
413 tmp ? tmp : "vlp queuepause %p");
415 tmp = talloc_asprintf(tmp_ctx, "vlp %s queueresume %%p",
417 lpcfg_string_set(ctx, &pService->queueresume_command,
418 tmp ? tmp : "vlp queueresume %p");
419 TALLOC_FREE(tmp_ctx);
423 #endif /* DEVELOPER */
428 * Function to return the default value for the maximum number of open
429 * file descriptors permitted. This function tries to consult the
430 * kernel-level (sysctl) and ulimit (getrlimit()) values and goes
431 * the smaller of those.
433 static int max_open_files(void)
435 int sysctl_max = MAX_OPEN_FILES;
436 int rlimit_max = MAX_OPEN_FILES;
438 #ifdef HAVE_SYSCTLBYNAME
440 size_t size = sizeof(sysctl_max);
441 sysctlbyname("kern.maxfilesperproc", &sysctl_max, &size, NULL,
446 #if (defined(HAVE_GETRLIMIT) && defined(RLIMIT_NOFILE))
452 if (getrlimit(RLIMIT_NOFILE, &rl) == 0)
453 rlimit_max = rl.rlim_cur;
455 #if defined(RLIM_INFINITY)
456 if(rl.rlim_cur == RLIM_INFINITY)
457 rlimit_max = MAX_OPEN_FILES;
462 if (sysctl_max < MIN_OPEN_FILES_WINDOWS) {
463 DEBUG(2,("max_open_files: increasing sysctl_max (%d) to "
464 "minimum Windows limit (%d)\n",
466 MIN_OPEN_FILES_WINDOWS));
467 sysctl_max = MIN_OPEN_FILES_WINDOWS;
470 if (rlimit_max < MIN_OPEN_FILES_WINDOWS) {
471 DEBUG(2,("rlimit_max: increasing rlimit_max (%d) to "
472 "minimum Windows limit (%d)\n",
474 MIN_OPEN_FILES_WINDOWS));
475 rlimit_max = MIN_OPEN_FILES_WINDOWS;
478 return MIN(sysctl_max, rlimit_max);
482 * Common part of freeing allocated data for one parameter.
484 static void free_one_parameter_common(void *parm_ptr,
485 struct parm_struct parm)
487 if ((parm.type == P_STRING) ||
488 (parm.type == P_USTRING))
490 string_free((char**)parm_ptr);
491 } else if (parm.type == P_LIST || parm.type == P_CMDLIST) {
492 TALLOC_FREE(*((char***)parm_ptr));
497 * Free the allocated data for one parameter for a share
498 * given as a service struct.
500 static void free_one_parameter(struct loadparm_service *service,
501 struct parm_struct parm)
505 if (parm.p_class != P_LOCAL) {
509 parm_ptr = lp_parm_ptr(service, &parm);
511 free_one_parameter_common(parm_ptr, parm);
515 * Free the allocated parameter data of a share given
516 * as a service struct.
518 static void free_parameters(struct loadparm_service *service)
522 for (i=0; parm_table[i].label; i++) {
523 free_one_parameter(service, parm_table[i]);
528 * Free the allocated data for one parameter for a given share
529 * specified by an snum.
531 static void free_one_parameter_by_snum(int snum, struct parm_struct parm)
536 parm_ptr = lp_parm_ptr(NULL, &parm);
537 } else if (parm.p_class != P_LOCAL) {
540 parm_ptr = lp_parm_ptr(ServicePtrs[snum], &parm);
543 free_one_parameter_common(parm_ptr, parm);
547 * Free the allocated parameter data for a share specified
550 static void free_parameters_by_snum(int snum)
554 for (i=0; parm_table[i].label; i++) {
555 free_one_parameter_by_snum(snum, parm_table[i]);
560 * Free the allocated global parameters.
562 static void free_global_parameters(void)
564 free_param_opts(&Globals.param_opt);
565 free_parameters_by_snum(GLOBAL_SECTION_SNUM);
566 TALLOC_FREE(Globals.ctx);
569 struct lp_stored_option {
570 struct lp_stored_option *prev, *next;
575 static struct lp_stored_option *stored_options;
578 save options set by lp_set_cmdline() into a list. This list is
579 re-applied when we do a globals reset, so that cmdline set options
580 are sticky across reloads of smb.conf
582 bool store_lp_set_cmdline(const char *pszParmName, const char *pszParmValue)
584 struct lp_stored_option *entry, *entry_next;
585 for (entry = stored_options; entry != NULL; entry = entry_next) {
586 entry_next = entry->next;
587 if (strcmp(pszParmName, entry->label) == 0) {
588 DLIST_REMOVE(stored_options, entry);
594 entry = talloc(NULL, struct lp_stored_option);
599 entry->label = talloc_strdup(entry, pszParmName);
605 entry->value = talloc_strdup(entry, pszParmValue);
611 DLIST_ADD_END(stored_options, entry, struct lp_stored_option);
616 static bool apply_lp_set_cmdline(void)
618 struct lp_stored_option *entry = NULL;
619 for (entry = stored_options; entry != NULL; entry = entry->next) {
620 if (!lp_set_cmdline_helper(entry->label, entry->value)) {
621 DEBUG(0, ("Failed to re-apply cmdline parameter %s = %s\n",
622 entry->label, entry->value));
629 /***************************************************************************
630 Initialise the global parameter structure.
631 ***************************************************************************/
633 static void init_globals(struct loadparm_context *lp_ctx, bool reinit_globals)
635 static bool done_init = false;
639 /* If requested to initialize only once and we've already done it... */
640 if (!reinit_globals && done_init) {
641 /* ... then we have nothing more to do */
646 /* The logfile can be set before this is invoked. Free it if so. */
647 if (Globals.logfile != NULL) {
648 string_free(&Globals.logfile);
649 Globals.logfile = NULL;
653 free_global_parameters();
656 /* This memset and the free_global_parameters() above will
657 * wipe out smb.conf options set with lp_set_cmdline(). The
658 * apply_lp_set_cmdline() call puts these values back in the
659 * table once the defaults are set */
660 ZERO_STRUCT(Globals);
662 Globals.ctx = talloc_pooled_object(NULL, char, 272, 2048);
664 /* Initialize the flags list if necessary */
665 if (flags_list == NULL) {
669 for (i = 0; parm_table[i].label; i++) {
670 if ((parm_table[i].type == P_STRING ||
671 parm_table[i].type == P_USTRING))
673 string_set(Globals.ctx, (char **)lp_parm_ptr(NULL, &parm_table[i]), "");
678 string_set(Globals.ctx, &sDefault.fstype, FSTYPE_STRING);
679 string_set(Globals.ctx, &sDefault.printjob_username, "%U");
681 init_printer_values(Globals.ctx, &sDefault);
683 sDefault.ntvfs_handler = (const char **)str_list_make_v3(NULL, "unixuid default", NULL);
685 DEBUG(3, ("Initialising global parameters\n"));
687 /* Must manually force to upper case here, as this does not go via the handler */
688 string_set(Globals.ctx, &Globals.netbios_name, myhostname_upper());
690 string_set(Globals.ctx, &Globals.smb_passwd_file, get_dyn_SMB_PASSWD_FILE());
691 string_set(Globals.ctx, &Globals.private_dir, get_dyn_PRIVATE_DIR());
693 /* use the new 'hash2' method by default, with a prefix of 1 */
694 string_set(Globals.ctx, &Globals.mangling_method, "hash2");
695 Globals.mangle_prefix = 1;
697 string_set(Globals.ctx, &Globals.guest_account, GUEST_ACCOUNT);
699 /* using UTF8 by default allows us to support all chars */
700 string_set(Globals.ctx, &Globals.unix_charset, DEFAULT_UNIX_CHARSET);
702 /* Use codepage 850 as a default for the dos character set */
703 string_set(Globals.ctx, &Globals.dos_charset, DEFAULT_DOS_CHARSET);
706 * Allow the default PASSWD_CHAT to be overridden in local.h.
708 string_set(Globals.ctx, &Globals.passwd_chat, DEFAULT_PASSWD_CHAT);
710 string_set(Globals.ctx, &Globals.workgroup, DEFAULT_WORKGROUP);
712 string_set(Globals.ctx, &Globals.passwd_program, "");
713 string_set(Globals.ctx, &Globals.lock_directory, get_dyn_LOCKDIR());
714 string_set(Globals.ctx, &Globals.state_directory, get_dyn_STATEDIR());
715 string_set(Globals.ctx, &Globals.cache_directory, get_dyn_CACHEDIR());
716 string_set(Globals.ctx, &Globals.pid_directory, get_dyn_PIDDIR());
717 string_set(Globals.ctx, &Globals.nbt_client_socket_address, "0.0.0.0");
719 * By default support explicit binding to broadcast
722 Globals.nmbd_bind_explicit_broadcast = true;
724 s = talloc_asprintf(talloc_tos(), "Samba %s", samba_version_string());
726 smb_panic("init_globals: ENOMEM");
728 string_set(Globals.ctx, &Globals.server_string, s);
731 string_set(Globals.ctx, &Globals.panic_action, "/bin/sleep 999999999");
734 string_set(Globals.ctx, &Globals.socket_options, DEFAULT_SOCKET_OPTIONS);
736 string_set(Globals.ctx, &Globals.logon_drive, "");
737 /* %N is the NIS auto.home server if -DAUTOHOME is used, else same as %L */
738 string_set(Globals.ctx, &Globals.logon_home, "\\\\%N\\%U");
739 string_set(Globals.ctx, &Globals.logon_path, "\\\\%N\\%U\\profile");
741 Globals.name_resolve_order = (const char **)str_list_make_v3(NULL, "lmhosts wins host bcast", NULL);
742 string_set(Globals.ctx, &Globals.password_server, "*");
744 Globals.algorithmic_rid_base = BASE_RID;
746 Globals.load_printers = true;
747 Globals.printcap_cache_time = 750; /* 12.5 minutes */
749 Globals.config_backend = config_backend;
750 Globals._server_role = ROLE_AUTO;
752 /* Was 65535 (0xFFFF). 0x4101 matches W2K and causes major speed improvements... */
753 /* Discovered by 2 days of pain by Don McCall @ HP :-). */
754 Globals.max_xmit = 0x4104;
755 Globals.max_mux = 50; /* This is *needed* for profile support. */
756 Globals.lpq_cache_time = 30; /* changed to handle large print servers better -- jerry */
757 Globals._disable_spoolss = false;
758 Globals.max_smbd_processes = 0;/* no limit specified */
759 Globals.username_level = 0;
760 Globals.deadtime = 0;
761 Globals.getwd_cache = true;
762 Globals.large_readwrite = true;
763 Globals.max_log_size = 5000;
764 Globals.max_open_files = max_open_files();
765 Globals.server_max_protocol = PROTOCOL_SMB3_00;
766 Globals.server_min_protocol = PROTOCOL_LANMAN1;
767 Globals.client_max_protocol = PROTOCOL_NT1;
768 Globals.client_min_protocol = PROTOCOL_CORE;
769 Globals._security = SEC_AUTO;
770 Globals.encrypt_passwords = true;
771 Globals.client_schannel = Auto;
772 Globals.winbind_sealed_pipes = true;
773 Globals.require_strong_key = true;
774 Globals.server_schannel = Auto;
775 Globals.read_raw = true;
776 Globals.write_raw = true;
777 Globals.null_passwords = false;
778 Globals.old_password_allowed_period = 60;
779 Globals.obey_pam_restrictions = false;
781 Globals.syslog_only = false;
782 Globals.timestamp_logs = true;
783 string_set(Globals.ctx, &Globals.log_level, "0");
784 Globals.debug_prefix_timestamp = false;
785 Globals.debug_hires_timestamp = true;
786 Globals.debug_pid = false;
787 Globals.debug_uid = false;
788 Globals.debug_class = false;
789 Globals.enable_core_files = true;
790 Globals.max_ttl = 60 * 60 * 24 * 3; /* 3 days default. */
791 Globals.max_wins_ttl = 60 * 60 * 24 * 6; /* 6 days default. */
792 Globals.min_wins_ttl = 60 * 60 * 6; /* 6 hours default. */
793 Globals.machine_password_timeout = 60 * 60 * 24 * 7; /* 7 days default. */
794 Globals.lm_announce = Auto; /* = Auto: send only if LM clients found */
795 Globals.lm_interval = 60;
796 #if (defined(HAVE_NETGROUP) && defined(WITH_AUTOMOUNT))
797 Globals.nis_homedir = false;
798 #ifdef WITH_NISPLUS_HOME
799 string_set(Globals.ctx, &Globals.homedir_map, "auto_home.org_dir");
801 string_set(Globals.ctx, &Globals.homedir_map, "auto.home");
804 Globals.time_server = false;
805 Globals.bind_interfaces_only = false;
806 Globals.unix_password_sync = false;
807 Globals.pam_password_change = false;
808 Globals.passwd_chat_debug = false;
809 Globals.passwd_chat_timeout = 2; /* 2 second default. */
810 Globals.nt_pipe_support = true; /* Do NT pipes by default. */
811 Globals.nt_status_support = true; /* Use NT status by default. */
812 Globals.stat_cache = true; /* use stat cache by default */
813 Globals.max_stat_cache_size = 256; /* 256k by default */
814 Globals.restrict_anonymous = 0;
815 Globals.client_lanman_auth = false; /* Do NOT use the LanMan hash if it is available */
816 Globals.client_plaintext_auth = false; /* Do NOT use a plaintext password even if is requested by the server */
817 Globals.lanman_auth = false; /* Do NOT use the LanMan hash, even if it is supplied */
818 Globals.ntlm_auth = true; /* Do use NTLMv1 if it is supplied by the client (otherwise NTLMv2) */
819 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 */
820 /* Note, that we will also use NTLM2 session security (which is different), if it is available */
822 Globals.map_to_guest = 0; /* By Default, "Never" */
823 Globals.oplock_break_wait_time = 0; /* By Default, 0 msecs. */
824 Globals.enhanced_browsing = true;
825 Globals.lock_spin_time = WINDOWS_MINIMUM_LOCK_TIMEOUT_MS; /* msec. */
826 #ifdef MMAP_BLACKLIST
827 Globals.use_mmap = false;
829 Globals.use_mmap = true;
831 Globals.unicode = true;
832 Globals.unix_extensions = true;
833 Globals.reset_on_zero_vc = false;
834 Globals.log_writeable_files_on_exit = false;
835 Globals.create_krb5_conf = true;
836 Globals.winbindMaxDomainConnections = 1;
838 /* hostname lookups can be very expensive and are broken on
839 a large number of sites (tridge) */
840 Globals.hostname_lookups = false;
842 string_set(Globals.ctx, &Globals.passdb_backend, "tdbsam");
843 string_set(Globals.ctx, &Globals.ldap_suffix, "");
844 string_set(Globals.ctx, &Globals.szLdapMachineSuffix, "");
845 string_set(Globals.ctx, &Globals.szLdapUserSuffix, "");
846 string_set(Globals.ctx, &Globals.szLdapGroupSuffix, "");
847 string_set(Globals.ctx, &Globals.szLdapIdmapSuffix, "");
849 string_set(Globals.ctx, &Globals.ldap_admin_dn, "");
850 Globals.ldap_ssl = LDAP_SSL_START_TLS;
851 Globals.ldap_ssl_ads = false;
852 Globals.ldap_deref = -1;
853 Globals.ldap_passwd_sync = LDAP_PASSWD_SYNC_OFF;
854 Globals.ldap_delete_dn = false;
855 Globals.ldap_replication_sleep = 1000; /* wait 1 sec for replication */
856 Globals.ldap_follow_referral = Auto;
857 Globals.ldap_timeout = LDAP_DEFAULT_TIMEOUT;
858 Globals.ldap_connection_timeout = LDAP_CONNECTION_DEFAULT_TIMEOUT;
859 Globals.ldap_page_size = LDAP_PAGE_SIZE;
861 Globals.ldap_debug_level = 0;
862 Globals.ldap_debug_threshold = 10;
864 /* This is what we tell the afs client. in reality we set the token
865 * to never expire, though, when this runs out the afs client will
866 * forget the token. Set to 0 to get NEVERDATE.*/
867 Globals.afs_token_lifetime = 604800;
868 Globals.cups_connection_timeout = CUPS_DEFAULT_CONNECTION_TIMEOUT;
870 /* these parameters are set to defaults that are more appropriate
871 for the increasing samba install base:
873 as a member of the workgroup, that will possibly become a
874 _local_ master browser (lm = true). this is opposed to a forced
875 local master browser startup (pm = true).
877 doesn't provide WINS server service by default (wsupp = false),
878 and doesn't provide domain master browser services by default, either.
882 Globals.show_add_printer_wizard = true;
883 Globals.os_level = 20;
884 Globals.local_master = true;
885 Globals._domain_master = Auto; /* depending on _domain_logons */
886 Globals._domain_logons = false;
887 Globals.browse_list = true;
888 Globals.we_are_a_wins_server = false;
889 Globals.wins_proxy = false;
891 TALLOC_FREE(Globals.init_logon_delayed_hosts);
892 Globals.init_logon_delay = 100; /* 100 ms default delay */
894 Globals.wins_dns_proxy = true;
896 Globals.allow_trusted_domains = true;
897 string_set(Globals.ctx, &Globals.szIdmapBackend, "tdb");
899 string_set(Globals.ctx, &Globals.template_shell, "/bin/false");
900 string_set(Globals.ctx, &Globals.template_homedir, "/home/%D/%U");
901 string_set(Globals.ctx, &Globals.winbind_separator, "\\");
902 string_set(Globals.ctx, &Globals.winbindd_socket_directory, dyn_WINBINDD_SOCKET_DIR);
904 string_set(Globals.ctx, &Globals.cups_server, "");
905 string_set(Globals.ctx, &Globals.iprint_server, "");
907 string_set(Globals.ctx, &Globals._ctdbd_socket, "");
909 Globals.cluster_addresses = NULL;
910 Globals.clustering = false;
911 Globals.ctdb_timeout = 0;
912 Globals.ctdb_locktime_warn_threshold = 0;
914 Globals.winbind_cache_time = 300; /* 5 minutes */
915 Globals.winbind_reconnect_delay = 30; /* 30 seconds */
916 Globals.winbind_request_timeout = 60; /* 60 seconds */
917 Globals.winbind_max_clients = 200;
918 Globals.winbind_enum_users = false;
919 Globals.winbind_enum_groups = false;
920 Globals.winbind_use_default_domain = false;
921 Globals.winbind_trusted_domains_only = false;
922 Globals.winbind_nested_groups = true;
923 Globals.winbind_expand_groups = 1;
924 Globals.winbind_nss_info = (const char **)str_list_make_v3(NULL, "template", NULL);
925 Globals.winbind_refresh_tickets = false;
926 Globals.winbind_offline_logon = false;
928 Globals.idmap_cache_time = 86400 * 7; /* a week by default */
929 Globals.idmap_negative_cache_time = 120; /* 2 minutes by default */
931 Globals.passdb_expand_explicit = false;
933 Globals.name_cache_timeout = 660; /* In seconds */
935 Globals.use_spnego = true;
936 Globals.client_use_spnego = true;
938 Globals.client_signing = SMB_SIGNING_DEFAULT;
939 Globals.server_signing = SMB_SIGNING_DEFAULT;
941 Globals.defer_sharing_violations = true;
942 Globals.smb_ports = (const char **)str_list_make_v3(NULL, SMB_PORTS, NULL);
944 Globals.enable_privileges = true;
945 Globals.host_msdfs = true;
946 Globals.enable_asu_support = false;
948 /* User defined shares. */
949 s = talloc_asprintf(talloc_tos(), "%s/usershares", get_dyn_STATEDIR());
951 smb_panic("init_globals: ENOMEM");
953 string_set(Globals.ctx, &Globals.usershare_path, s);
955 string_set(Globals.ctx, &Globals.usershare_template_share, "");
956 Globals.usershare_max_shares = 0;
957 /* By default disallow sharing of directories not owned by the sharer. */
958 Globals.usershare_owner_only = true;
959 /* By default disallow guest access to usershares. */
960 Globals.usershare_allow_guests = false;
962 Globals.keepalive = DEFAULT_KEEPALIVE;
964 /* By default no shares out of the registry */
965 Globals.registry_shares = false;
967 Globals.iminreceivefile = 0;
969 Globals.map_untrusted_to_domain = false;
970 Globals.multicast_dns_register = true;
972 Globals.smb2_max_read = DEFAULT_SMB2_MAX_READ;
973 Globals.smb2_max_write = DEFAULT_SMB2_MAX_WRITE;
974 Globals.smb2_max_trans = DEFAULT_SMB2_MAX_TRANSACT;
975 Globals.ismb2_max_credits = DEFAULT_SMB2_MAX_CREDITS;
977 string_set(Globals.ctx, &Globals.ncalrpc_dir, get_dyn_NCALRPCDIR());
979 Globals.server_services = (const char **)str_list_make_v3(NULL, "s3fs rpc nbt wrepl ldap cldap kdc drepl winbindd ntp_signd kcc dnsupdate dns", NULL);
981 Globals.dcerpc_endpoint_servers = (const char **)str_list_make_v3(NULL, "epmapper wkssvc rpcecho samr netlogon lsarpc spoolss drsuapi dssetup unixinfo browser eventlog6 backupkey dnsserver", NULL);
983 Globals.tls_enabled = true;
985 string_set(Globals.ctx, &Globals._tls_keyfile, "tls/key.pem");
986 string_set(Globals.ctx, &Globals._tls_certfile, "tls/cert.pem");
987 string_set(Globals.ctx, &Globals._tls_cafile, "tls/ca.pem");
989 string_set(Globals.ctx, &Globals.share_backend, "classic");
991 Globals.iPreferredMaster = Auto;
993 Globals.allow_dns_updates = DNS_UPDATE_SIGNED;
995 string_set(Globals.ctx, &Globals.ntp_signd_socket_directory, get_dyn_NTP_SIGND_SOCKET_DIR());
997 string_set(Globals.ctx, &Globals.winbindd_privileged_socket_directory, get_dyn_WINBINDD_PRIVILEGED_SOCKET_DIR());
999 s = talloc_asprintf(talloc_tos(), "%s/samba_kcc", get_dyn_SCRIPTSBINDIR());
1001 smb_panic("init_globals: ENOMEM");
1003 Globals.samba_kcc_command = (const char **)str_list_make_v3(NULL, s, NULL);
1006 s = talloc_asprintf(talloc_tos(), "%s/samba_dnsupdate", get_dyn_SCRIPTSBINDIR());
1008 smb_panic("init_globals: ENOMEM");
1010 Globals.dns_update_command = (const char **)str_list_make_v3(NULL, s, NULL);
1013 s = talloc_asprintf(talloc_tos(), "%s/samba_spnupdate", get_dyn_SCRIPTSBINDIR());
1015 smb_panic("init_globals: ENOMEM");
1017 Globals.spn_update_command = (const char **)str_list_make_v3(NULL, s, NULL);
1020 Globals.nsupdate_command = (const char **)str_list_make_v3(NULL, "/usr/bin/nsupdate -g", NULL);
1022 Globals.rndc_command = (const char **)str_list_make_v3(NULL, "/usr/sbin/rndc", NULL);
1024 Globals.cldap_port = 389;
1026 Globals.dgram_port = 138;
1028 Globals.nbt_port = 137;
1030 Globals.krb5_port = 88;
1032 Globals.kpasswd_port = 464;
1034 Globals.web_port = 901;
1036 /* Now put back the settings that were set with lp_set_cmdline() */
1037 apply_lp_set_cmdline();
1040 /*******************************************************************
1041 Convenience routine to grab string parameters into talloced memory
1042 and run standard_sub_basic on them. The buffers can be written to by
1043 callers without affecting the source string.
1044 ********************************************************************/
1046 char *lp_string(TALLOC_CTX *ctx, const char *s)
1050 /* The follow debug is useful for tracking down memory problems
1051 especially if you have an inner loop that is calling a lp_*()
1052 function that returns a string. Perhaps this debug should be
1053 present all the time? */
1056 DEBUG(10, ("lp_string(%s)\n", s));
1062 ret = talloc_sub_basic(ctx,
1063 get_current_username(),
1064 current_user_info.domain,
1066 if (trim_char(ret, '\"', '\"')) {
1067 if (strchr(ret,'\"') != NULL) {
1069 ret = talloc_sub_basic(ctx,
1070 get_current_username(),
1071 current_user_info.domain,
1079 In this section all the functions that are used to access the
1080 parameters from the rest of the program are defined
1083 #define FN_GLOBAL_STRING(fn_name,ptr) \
1084 char *lp_ ## fn_name(TALLOC_CTX *ctx) {return(lp_string((ctx), *(char **)(&Globals.ptr) ? *(char **)(&Globals.ptr) : ""));}
1085 #define FN_GLOBAL_CONST_STRING(fn_name,ptr) \
1086 const char *lp_ ## fn_name(void) {return(*(const char * const *)(&Globals.ptr) ? *(const char * const *)(&Globals.ptr) : "");}
1087 #define FN_GLOBAL_LIST(fn_name,ptr) \
1088 const char **lp_ ## fn_name(void) {return(*(const char ***)(&Globals.ptr));}
1089 #define FN_GLOBAL_BOOL(fn_name,ptr) \
1090 bool lp_ ## fn_name(void) {return(*(bool *)(&Globals.ptr));}
1091 #define FN_GLOBAL_CHAR(fn_name,ptr) \
1092 char lp_ ## fn_name(void) {return(*(char *)(&Globals.ptr));}
1093 #define FN_GLOBAL_INTEGER(fn_name,ptr) \
1094 int lp_ ## fn_name(void) {return(*(int *)(&Globals.ptr));}
1096 #define FN_LOCAL_STRING(fn_name,val) \
1097 char *lp_ ## fn_name(TALLOC_CTX *ctx,int i) {return(lp_string((ctx), (LP_SNUM_OK(i) && ServicePtrs[(i)]->val) ? ServicePtrs[(i)]->val : sDefault.val));}
1098 #define FN_LOCAL_CONST_STRING(fn_name,val) \
1099 const char *lp_ ## fn_name(int i) {return (const char *)((LP_SNUM_OK(i) && ServicePtrs[(i)]->val) ? ServicePtrs[(i)]->val : sDefault.val);}
1100 #define FN_LOCAL_LIST(fn_name,val) \
1101 const char **lp_ ## fn_name(int i) {return(const char **)(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1102 #define FN_LOCAL_BOOL(fn_name,val) \
1103 bool lp_ ## fn_name(int i) {return(bool)(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1104 #define FN_LOCAL_INTEGER(fn_name,val) \
1105 int lp_ ## fn_name(int i) {return(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1107 #define FN_LOCAL_PARM_BOOL(fn_name,val) \
1108 bool lp_ ## fn_name(const struct share_params *p) {return(bool)(LP_SNUM_OK(p->service)? ServicePtrs[(p->service)]->val : sDefault.val);}
1109 #define FN_LOCAL_PARM_INTEGER(fn_name,val) \
1110 int lp_ ## fn_name(const struct share_params *p) {return(LP_SNUM_OK(p->service)? ServicePtrs[(p->service)]->val : sDefault.val);}
1111 #define FN_LOCAL_PARM_CHAR(fn_name,val) \
1112 char lp_ ## fn_name(const struct share_params *p) {return(LP_SNUM_OK(p->service)? ServicePtrs[(p->service)]->val : sDefault.val);}
1114 static FN_GLOBAL_INTEGER(winbind_max_domain_connections_int,
1115 winbindMaxDomainConnections)
1117 int lp_winbind_max_domain_connections(void)
1119 if (lp_winbind_offline_logon() &&
1120 lp_winbind_max_domain_connections_int() > 1) {
1121 DEBUG(1, ("offline logons active, restricting max domain "
1122 "connections to 1\n"));
1125 return MAX(1, lp_winbind_max_domain_connections_int());
1128 int lp_smb2_max_credits(void)
1130 if (Globals.ismb2_max_credits == 0) {
1131 Globals.ismb2_max_credits = DEFAULT_SMB2_MAX_CREDITS;
1133 return Globals.ismb2_max_credits;
1135 int lp_cups_encrypt(void)
1138 #ifdef HAVE_HTTPCONNECTENCRYPT
1139 switch (Globals.CupsEncrypt) {
1141 result = HTTP_ENCRYPT_REQUIRED;
1144 result = HTTP_ENCRYPT_ALWAYS;
1147 result = HTTP_ENCRYPT_NEVER;
1154 /* These functions remain in source3/param for now */
1156 #include "lib/param/param_functions.c"
1158 FN_LOCAL_STRING(servicename, szService)
1159 FN_LOCAL_CONST_STRING(const_servicename, szService)
1161 /* These functions cannot be auto-generated */
1162 FN_LOCAL_BOOL(autoloaded, autoloaded)
1163 FN_GLOBAL_CONST_STRING(dnsdomain, dnsdomain)
1165 /* local prototypes */
1167 static int map_parameter_canonical(const char *pszParmName, bool *inverse);
1168 static const char *get_boolean(bool bool_value);
1169 static bool do_parameter(const char *pszParmName, const char *pszParmValue,
1171 static bool hash_a_service(const char *name, int number);
1172 static void free_service_byindex(int iService);
1173 static void show_parameter(int parmIndex);
1174 static bool is_synonym_of(int parm1, int parm2, bool *inverse);
1177 * This is a helper function for parametrical options support. It returns a
1178 * pointer to parametrical option value if it exists or NULL otherwise. Actual
1179 * parametrical functions are quite simple
1181 static struct parmlist_entry *get_parametrics(int snum, const char *type,
1184 if (snum >= iNumServices) return NULL;
1187 return get_parametric_helper(NULL, type, option, Globals.param_opt);
1189 return get_parametric_helper(ServicePtrs[snum],
1190 type, option, Globals.param_opt);
1195 #define MISSING_PARAMETER(name) \
1196 DEBUG(0, ("%s(): value is NULL or empty!\n", #name))
1198 /*******************************************************************
1199 convenience routine to return enum parameters.
1200 ********************************************************************/
1201 static int lp_enum(const char *s,const struct enum_list *_enum)
1205 if (!s || !*s || !_enum) {
1206 MISSING_PARAMETER(lp_enum);
1210 for (i=0; _enum[i].name; i++) {
1211 if (strequal(_enum[i].name,s))
1212 return _enum[i].value;
1215 DEBUG(0,("lp_enum(%s,enum): value is not in enum_list!\n",s));
1219 #undef MISSING_PARAMETER
1221 /* Return parametric option from a given service. Type is a part of option before ':' */
1222 /* Parametric option has following syntax: 'Type: option = value' */
1223 char *lp_parm_talloc_string(TALLOC_CTX *ctx, int snum, const char *type, const char *option, const char *def)
1225 struct parmlist_entry *data = get_parametrics(snum, type, option);
1227 if (data == NULL||data->value==NULL) {
1229 return lp_string(ctx, def);
1235 return lp_string(ctx, data->value);
1238 /* Return parametric option from a given service. Type is a part of option before ':' */
1239 /* Parametric option has following syntax: 'Type: option = value' */
1240 const char *lp_parm_const_string(int snum, const char *type, const char *option, const char *def)
1242 struct parmlist_entry *data = get_parametrics(snum, type, option);
1244 if (data == NULL||data->value==NULL)
1251 /* Return parametric option from a given service. Type is a part of option before ':' */
1252 /* Parametric option has following syntax: 'Type: option = value' */
1254 const char **lp_parm_string_list(int snum, const char *type, const char *option, const char **def)
1256 struct parmlist_entry *data = get_parametrics(snum, type, option);
1258 if (data == NULL||data->value==NULL)
1259 return (const char **)def;
1261 if (data->list==NULL) {
1262 data->list = str_list_make_v3(NULL, data->value, NULL);
1265 return (const char **)data->list;
1268 /* Return parametric option from a given service. Type is a part of option before ':' */
1269 /* Parametric option has following syntax: 'Type: option = value' */
1271 int lp_parm_int(int snum, const char *type, const char *option, int def)
1273 struct parmlist_entry *data = get_parametrics(snum, type, option);
1275 if (data && data->value && *data->value)
1276 return lp_int(data->value);
1281 /* Return parametric option from a given service. Type is a part of option before ':' */
1282 /* Parametric option has following syntax: 'Type: option = value' */
1284 unsigned long lp_parm_ulong(int snum, const char *type, const char *option, unsigned long def)
1286 struct parmlist_entry *data = get_parametrics(snum, type, option);
1288 if (data && data->value && *data->value)
1289 return lp_ulong(data->value);
1294 /* Return parametric option from a given service. Type is a part of option before ':' */
1295 /* Parametric option has following syntax: 'Type: option = value' */
1297 bool lp_parm_bool(int snum, const char *type, const char *option, bool def)
1299 struct parmlist_entry *data = get_parametrics(snum, type, option);
1301 if (data && data->value && *data->value)
1302 return lp_bool(data->value);
1307 /* Return parametric option from a given service. Type is a part of option before ':' */
1308 /* Parametric option has following syntax: 'Type: option = value' */
1310 int lp_parm_enum(int snum, const char *type, const char *option,
1311 const struct enum_list *_enum, int def)
1313 struct parmlist_entry *data = get_parametrics(snum, type, option);
1315 if (data && data->value && *data->value && _enum)
1316 return lp_enum(data->value, _enum);
1322 * free a param_opts structure.
1323 * param_opts handling should be moved to talloc;
1324 * then this whole functions reduces to a TALLOC_FREE().
1327 static void free_param_opts(struct parmlist_entry **popts)
1329 struct parmlist_entry *opt, *next_opt;
1331 if (*popts != NULL) {
1332 DEBUG(5, ("Freeing parametrics:\n"));
1335 while (opt != NULL) {
1336 string_free(&opt->key);
1337 string_free(&opt->value);
1338 TALLOC_FREE(opt->list);
1339 next_opt = opt->next;
1346 /***************************************************************************
1347 Free the dynamically allocated parts of a service struct.
1348 ***************************************************************************/
1350 static void free_service(struct loadparm_service *pservice)
1355 if (pservice->szService)
1356 DEBUG(5, ("free_service: Freeing service %s\n",
1357 pservice->szService));
1359 free_parameters(pservice);
1361 string_free(&pservice->szService);
1362 TALLOC_FREE(pservice->copymap);
1364 free_param_opts(&pservice->param_opt);
1366 ZERO_STRUCTP(pservice);
1370 /***************************************************************************
1371 remove a service indexed in the ServicePtrs array from the ServiceHash
1372 and free the dynamically allocated parts
1373 ***************************************************************************/
1375 static void free_service_byindex(int idx)
1377 if ( !LP_SNUM_OK(idx) )
1380 ServicePtrs[idx]->valid = false;
1382 /* we have to cleanup the hash record */
1384 if (ServicePtrs[idx]->szService) {
1385 char *canon_name = canonicalize_servicename(
1387 ServicePtrs[idx]->szService );
1389 dbwrap_delete_bystring(ServiceHash, canon_name );
1390 TALLOC_FREE(canon_name);
1393 free_service(ServicePtrs[idx]);
1394 talloc_free_children(ServicePtrs[idx]);
1397 /***************************************************************************
1398 Add a new service to the services array initialising it with the given
1400 ***************************************************************************/
1402 static int add_a_service(const struct loadparm_service *pservice, const char *name)
1405 int num_to_alloc = iNumServices + 1;
1406 struct loadparm_service **tsp = NULL;
1408 /* it might already exist */
1410 i = getservicebyname(name, NULL);
1416 /* if not, then create one */
1418 tsp = talloc_realloc(NULL, ServicePtrs, struct loadparm_service *, num_to_alloc);
1420 DEBUG(0,("add_a_service: failed to enlarge ServicePtrs!\n"));
1424 ServicePtrs[iNumServices] = talloc_zero(NULL, struct loadparm_service);
1425 if (!ServicePtrs[iNumServices]) {
1426 DEBUG(0,("add_a_service: out of memory!\n"));
1431 ServicePtrs[i]->valid = true;
1433 copy_service(ServicePtrs[i], pservice, NULL);
1435 string_set(ServicePtrs[i], &ServicePtrs[i]->szService, name);
1437 DEBUG(8,("add_a_service: Creating snum = %d for %s\n",
1438 i, ServicePtrs[i]->szService));
1440 if (!hash_a_service(ServicePtrs[i]->szService, i)) {
1447 /***************************************************************************
1448 Convert a string to uppercase and remove whitespaces.
1449 ***************************************************************************/
1451 char *canonicalize_servicename(TALLOC_CTX *ctx, const char *src)
1456 DEBUG(0,("canonicalize_servicename: NULL source name!\n"));
1460 result = talloc_strdup(ctx, src);
1461 SMB_ASSERT(result != NULL);
1463 if (!strlower_m(result)) {
1464 TALLOC_FREE(result);
1470 /***************************************************************************
1471 Add a name/index pair for the services array to the hash table.
1472 ***************************************************************************/
1474 static bool hash_a_service(const char *name, int idx)
1478 if ( !ServiceHash ) {
1479 DEBUG(10,("hash_a_service: creating servicehash\n"));
1480 ServiceHash = db_open_rbt(NULL);
1481 if ( !ServiceHash ) {
1482 DEBUG(0,("hash_a_service: open tdb servicehash failed!\n"));
1487 DEBUG(10,("hash_a_service: hashing index %d for service name %s\n",
1490 canon_name = canonicalize_servicename(talloc_tos(), name );
1492 dbwrap_store_bystring(ServiceHash, canon_name,
1493 make_tdb_data((uint8 *)&idx, sizeof(idx)),
1496 TALLOC_FREE(canon_name);
1501 /***************************************************************************
1502 Add a new home service, with the specified home directory, defaults coming
1504 ***************************************************************************/
1506 bool lp_add_home(const char *pszHomename, int iDefaultService,
1507 const char *user, const char *pszHomedir)
1511 if (pszHomename == NULL || user == NULL || pszHomedir == NULL ||
1512 pszHomedir[0] == '\0') {
1516 i = add_a_service(ServicePtrs[iDefaultService], pszHomename);
1521 if (!(*(ServicePtrs[iDefaultService]->path))
1522 || strequal(ServicePtrs[iDefaultService]->path,
1523 lp_path(talloc_tos(), GLOBAL_SECTION_SNUM))) {
1524 string_set(ServicePtrs[i], &ServicePtrs[i]->path, pszHomedir);
1527 if (!(*(ServicePtrs[i]->comment))) {
1528 char *comment = talloc_asprintf(talloc_tos(), "Home directory of %s", user);
1529 if (comment == NULL) {
1532 string_set(ServicePtrs[i], &ServicePtrs[i]->comment, comment);
1533 TALLOC_FREE(comment);
1536 /* set the browseable flag from the global default */
1538 ServicePtrs[i]->browseable = sDefault.browseable;
1539 ServicePtrs[i]->access_based_share_enum = sDefault.access_based_share_enum;
1541 ServicePtrs[i]->autoloaded = true;
1543 DEBUG(3, ("adding home's share [%s] for user '%s' at '%s'\n", pszHomename,
1544 user, ServicePtrs[i]->path ));
1549 /***************************************************************************
1550 Add a new service, based on an old one.
1551 ***************************************************************************/
1553 int lp_add_service(const char *pszService, int iDefaultService)
1555 if (iDefaultService < 0) {
1556 return add_a_service(&sDefault, pszService);
1559 return (add_a_service(ServicePtrs[iDefaultService], pszService));
1562 /***************************************************************************
1563 Add the IPC service.
1564 ***************************************************************************/
1566 static bool lp_add_ipc(const char *ipc_name, bool guest_ok)
1568 char *comment = NULL;
1569 int i = add_a_service(&sDefault, ipc_name);
1574 comment = talloc_asprintf(talloc_tos(), "IPC Service (%s)",
1575 Globals.server_string);
1576 if (comment == NULL) {
1580 string_set(ServicePtrs[i], &ServicePtrs[i]->path, tmpdir());
1581 string_set(ServicePtrs[i], &ServicePtrs[i]->username, "");
1582 string_set(ServicePtrs[i], &ServicePtrs[i]->comment, comment);
1583 string_set(ServicePtrs[i], &ServicePtrs[i]->fstype, "IPC");
1584 ServicePtrs[i]->max_connections = 0;
1585 ServicePtrs[i]->bAvailable = true;
1586 ServicePtrs[i]->read_only = true;
1587 ServicePtrs[i]->guest_only = false;
1588 ServicePtrs[i]->administrative_share = true;
1589 ServicePtrs[i]->guest_ok = guest_ok;
1590 ServicePtrs[i]->printable = false;
1591 ServicePtrs[i]->browseable = sDefault.browseable;
1593 DEBUG(3, ("adding IPC service\n"));
1595 TALLOC_FREE(comment);
1599 /***************************************************************************
1600 Add a new printer service, with defaults coming from service iFrom.
1601 ***************************************************************************/
1603 bool lp_add_printer(const char *pszPrintername, int iDefaultService)
1605 const char *comment = "From Printcap";
1606 int i = add_a_service(ServicePtrs[iDefaultService], pszPrintername);
1611 /* note that we do NOT default the availability flag to true - */
1612 /* we take it from the default service passed. This allows all */
1613 /* dynamic printers to be disabled by disabling the [printers] */
1614 /* entry (if/when the 'available' keyword is implemented!). */
1616 /* the printer name is set to the service name. */
1617 string_set(ServicePtrs[i], &ServicePtrs[i]->_printername, pszPrintername);
1618 string_set(ServicePtrs[i], &ServicePtrs[i]->comment, comment);
1620 /* set the browseable flag from the gloabl default */
1621 ServicePtrs[i]->browseable = sDefault.browseable;
1623 /* Printers cannot be read_only. */
1624 ServicePtrs[i]->read_only = false;
1625 /* No oplocks on printer services. */
1626 ServicePtrs[i]->oplocks = false;
1627 /* Printer services must be printable. */
1628 ServicePtrs[i]->printable = true;
1630 DEBUG(3, ("adding printer service %s\n", pszPrintername));
1636 /***************************************************************************
1637 Check whether the given parameter name is valid.
1638 Parametric options (names containing a colon) are considered valid.
1639 ***************************************************************************/
1641 bool lp_parameter_is_valid(const char *pszParmName)
1643 return ((lpcfg_map_parameter(pszParmName) != -1) ||
1644 (strchr(pszParmName, ':') != NULL));
1647 /***************************************************************************
1648 Check whether the given name is the name of a global parameter.
1649 Returns true for strings belonging to parameters of class
1650 P_GLOBAL, false for all other strings, also for parametric options
1651 and strings not belonging to any option.
1652 ***************************************************************************/
1654 bool lp_parameter_is_global(const char *pszParmName)
1656 int num = lpcfg_map_parameter(pszParmName);
1659 return (parm_table[num].p_class == P_GLOBAL);
1665 /**************************************************************************
1666 Check whether the given name is the canonical name of a parameter.
1667 Returns false if it is not a valid parameter Name.
1668 For parametric options, true is returned.
1669 **************************************************************************/
1671 bool lp_parameter_is_canonical(const char *parm_name)
1673 if (!lp_parameter_is_valid(parm_name)) {
1677 return (lpcfg_map_parameter(parm_name) ==
1678 map_parameter_canonical(parm_name, NULL));
1681 /**************************************************************************
1682 Determine the canonical name for a parameter.
1683 Indicate when it is an inverse (boolean) synonym instead of a
1685 **************************************************************************/
1687 bool lp_canonicalize_parameter(const char *parm_name, const char **canon_parm,
1692 if (!lp_parameter_is_valid(parm_name)) {
1697 num = map_parameter_canonical(parm_name, inverse);
1699 /* parametric option */
1700 *canon_parm = parm_name;
1702 *canon_parm = parm_table[num].label;
1709 /**************************************************************************
1710 Determine the canonical name for a parameter.
1711 Turn the value given into the inverse boolean expression when
1712 the synonym is an invers boolean synonym.
1714 Return true if parm_name is a valid parameter name and
1715 in case it is an invers boolean synonym, if the val string could
1716 successfully be converted to the reverse bool.
1717 Return false in all other cases.
1718 **************************************************************************/
1720 bool lp_canonicalize_parameter_with_value(const char *parm_name,
1722 const char **canon_parm,
1723 const char **canon_val)
1728 if (!lp_parameter_is_valid(parm_name)) {
1734 num = map_parameter_canonical(parm_name, &inverse);
1736 /* parametric option */
1737 *canon_parm = parm_name;
1740 *canon_parm = parm_table[num].label;
1742 if (!lp_invert_boolean(val, canon_val)) {
1754 /***************************************************************************
1755 Map a parameter's string representation to the index of the canonical
1756 form of the parameter (it might be a synonym).
1757 Returns -1 if the parameter string is not recognised.
1758 ***************************************************************************/
1760 static int map_parameter_canonical(const char *pszParmName, bool *inverse)
1762 int parm_num, canon_num;
1763 bool loc_inverse = false;
1765 parm_num = lpcfg_map_parameter(pszParmName);
1766 if ((parm_num < 0) || !(parm_table[parm_num].flags & FLAG_HIDE)) {
1767 /* invalid, parametric or no canidate for synonyms ... */
1771 for (canon_num = 0; parm_table[canon_num].label; canon_num++) {
1772 if (is_synonym_of(parm_num, canon_num, &loc_inverse)) {
1773 parm_num = canon_num;
1779 if (inverse != NULL) {
1780 *inverse = loc_inverse;
1785 /***************************************************************************
1786 return true if parameter number parm1 is a synonym of parameter
1787 number parm2 (parm2 being the principal name).
1788 set inverse to true if parm1 is P_BOOLREV and parm2 is P_BOOL,
1790 ***************************************************************************/
1792 static bool is_synonym_of(int parm1, int parm2, bool *inverse)
1794 if ((parm_table[parm1].offset == parm_table[parm2].offset) &&
1795 (parm_table[parm1].p_class == parm_table[parm2].p_class) &&
1796 (parm_table[parm1].flags & FLAG_HIDE) &&
1797 !(parm_table[parm2].flags & FLAG_HIDE))
1799 if (inverse != NULL) {
1800 if ((parm_table[parm1].type == P_BOOLREV) &&
1801 (parm_table[parm2].type == P_BOOL))
1813 /***************************************************************************
1814 Show one parameter's name, type, [values,] and flags.
1815 (helper functions for show_parameter_list)
1816 ***************************************************************************/
1818 static void show_parameter(int parmIndex)
1820 int enumIndex, flagIndex;
1825 const char *type[] = { "P_BOOL", "P_BOOLREV", "P_CHAR", "P_INTEGER",
1826 "P_OCTAL", "P_LIST", "P_STRING", "P_USTRING",
1828 unsigned flags[] = { FLAG_BASIC, FLAG_SHARE, FLAG_PRINT, FLAG_GLOBAL,
1829 FLAG_WIZARD, FLAG_ADVANCED, FLAG_DEVELOPER, FLAG_DEPRECATED,
1831 const char *flag_names[] = { "FLAG_BASIC", "FLAG_SHARE", "FLAG_PRINT",
1832 "FLAG_GLOBAL", "FLAG_WIZARD", "FLAG_ADVANCED", "FLAG_DEVELOPER",
1833 "FLAG_DEPRECATED", "FLAG_HIDE", NULL};
1835 printf("%s=%s", parm_table[parmIndex].label,
1836 type[parm_table[parmIndex].type]);
1837 if (parm_table[parmIndex].type == P_ENUM) {
1840 parm_table[parmIndex].enum_list[enumIndex].name;
1844 enumIndex ? "|" : "",
1845 parm_table[parmIndex].enum_list[enumIndex].name);
1850 for (flagIndex=0; flag_names[flagIndex]; flagIndex++) {
1851 if (parm_table[parmIndex].flags & flags[flagIndex]) {
1854 flag_names[flagIndex]);
1859 /* output synonyms */
1861 for (parmIndex2=0; parm_table[parmIndex2].label; parmIndex2++) {
1862 if (is_synonym_of(parmIndex, parmIndex2, &inverse)) {
1863 printf(" (%ssynonym of %s)", inverse ? "inverse " : "",
1864 parm_table[parmIndex2].label);
1865 } else if (is_synonym_of(parmIndex2, parmIndex, &inverse)) {
1867 printf(" (synonyms: ");
1872 printf("%s%s", parm_table[parmIndex2].label,
1873 inverse ? "[i]" : "");
1883 /***************************************************************************
1884 Show all parameter's name, type, [values,] and flags.
1885 ***************************************************************************/
1887 void show_parameter_list(void)
1889 int classIndex, parmIndex;
1890 const char *section_names[] = { "local", "global", NULL};
1892 for (classIndex=0; section_names[classIndex]; classIndex++) {
1893 printf("[%s]\n", section_names[classIndex]);
1894 for (parmIndex = 0; parm_table[parmIndex].label; parmIndex++) {
1895 if (parm_table[parmIndex].p_class == classIndex) {
1896 show_parameter(parmIndex);
1902 /***************************************************************************
1903 Get the standard string representation of a boolean value ("yes" or "no")
1904 ***************************************************************************/
1906 static const char *get_boolean(bool bool_value)
1908 static const char *yes_str = "yes";
1909 static const char *no_str = "no";
1911 return (bool_value ? yes_str : no_str);
1914 /***************************************************************************
1915 Provide the string of the negated boolean value associated to the boolean
1916 given as a string. Returns false if the passed string does not correctly
1917 represent a boolean.
1918 ***************************************************************************/
1920 bool lp_invert_boolean(const char *str, const char **inverse_str)
1924 if (!set_boolean(str, &val)) {
1928 *inverse_str = get_boolean(!val);
1932 /***************************************************************************
1933 Provide the canonical string representation of a boolean value given
1934 as a string. Return true on success, false if the string given does
1935 not correctly represent a boolean.
1936 ***************************************************************************/
1938 bool lp_canonicalize_boolean(const char *str, const char**canon_str)
1942 if (!set_boolean(str, &val)) {
1946 *canon_str = get_boolean(val);
1950 /***************************************************************************
1951 Find a service by name. Otherwise works like get_service.
1952 ***************************************************************************/
1954 int getservicebyname(const char *pszServiceName, struct loadparm_service *pserviceDest)
1961 if (ServiceHash == NULL) {
1965 canon_name = canonicalize_servicename(talloc_tos(), pszServiceName);
1967 status = dbwrap_fetch_bystring(ServiceHash, canon_name, canon_name,
1970 if (NT_STATUS_IS_OK(status) &&
1971 (data.dptr != NULL) &&
1972 (data.dsize == sizeof(iService)))
1974 iService = *(int *)data.dptr;
1977 TALLOC_FREE(canon_name);
1979 if ((iService != -1) && (LP_SNUM_OK(iService))
1980 && (pserviceDest != NULL)) {
1981 copy_service(pserviceDest, ServicePtrs[iService], NULL);
1987 /* Return a pointer to a service by name. Unlike getservicebyname, it does not copy the service */
1988 struct loadparm_service *lp_service(const char *pszServiceName)
1990 int iService = getservicebyname(pszServiceName, NULL);
1991 if (iService == -1 || !LP_SNUM_OK(iService)) {
1994 return ServicePtrs[iService];
1997 struct loadparm_service *lp_servicebynum(int snum)
1999 if ((snum == -1) || !LP_SNUM_OK(snum)) {
2002 return ServicePtrs[snum];
2005 struct loadparm_service *lp_default_loadparm_service()
2010 /***************************************************************************
2011 Check a service for consistency. Return false if the service is in any way
2012 incomplete or faulty, else true.
2013 ***************************************************************************/
2015 bool service_ok(int iService)
2020 if (ServicePtrs[iService]->szService[0] == '\0') {
2021 DEBUG(0, ("The following message indicates an internal error:\n"));
2022 DEBUG(0, ("No service name in service entry.\n"));
2026 /* The [printers] entry MUST be printable. I'm all for flexibility, but */
2027 /* I can't see why you'd want a non-printable printer service... */
2028 if (strwicmp(ServicePtrs[iService]->szService, PRINTERS_NAME) == 0) {
2029 if (!ServicePtrs[iService]->printable) {
2030 DEBUG(0, ("WARNING: [%s] service MUST be printable!\n",
2031 ServicePtrs[iService]->szService));
2032 ServicePtrs[iService]->printable = true;
2034 /* [printers] service must also be non-browsable. */
2035 if (ServicePtrs[iService]->browseable)
2036 ServicePtrs[iService]->browseable = false;
2039 if (ServicePtrs[iService]->path[0] == '\0' &&
2040 strwicmp(ServicePtrs[iService]->szService, HOMES_NAME) != 0 &&
2041 ServicePtrs[iService]->msdfs_proxy[0] == '\0'
2043 DEBUG(0, ("WARNING: No path in service %s - making it unavailable!\n",
2044 ServicePtrs[iService]->szService));
2045 ServicePtrs[iService]->bAvailable = false;
2048 /* If a service is flagged unavailable, log the fact at level 1. */
2049 if (!ServicePtrs[iService]->bAvailable)
2050 DEBUG(1, ("NOTE: Service %s is flagged unavailable.\n",
2051 ServicePtrs[iService]->szService));
2056 static struct smbconf_ctx *lp_smbconf_ctx(void)
2059 static struct smbconf_ctx *conf_ctx = NULL;
2061 if (conf_ctx == NULL) {
2062 err = smbconf_init(NULL, &conf_ctx, "registry:");
2063 if (!SBC_ERROR_IS_OK(err)) {
2064 DEBUG(1, ("error initializing registry configuration: "
2065 "%s\n", sbcErrorString(err)));
2073 static bool process_smbconf_service(struct smbconf_service *service)
2078 if (service == NULL) {
2082 ret = lp_do_section(service->name, NULL);
2086 for (count = 0; count < service->num_params; count++) {
2088 if (!bInGlobalSection && bGlobalOnly) {
2091 const char *pszParmName = service->param_names[count];
2092 const char *pszParmValue = service->param_values[count];
2094 DEBUGADD(4, ("doing parameter %s = %s\n", pszParmName, pszParmValue));
2096 ret = lp_do_parameter(bInGlobalSection ? -2 : iServiceIndex,
2097 pszParmName, pszParmValue);
2104 if (iServiceIndex >= 0) {
2105 return lpcfg_service_ok(ServicePtrs[iServiceIndex]);
2111 * load a service from registry and activate it
2113 bool process_registry_service(const char *service_name)
2116 struct smbconf_service *service = NULL;
2117 TALLOC_CTX *mem_ctx = talloc_stackframe();
2118 struct smbconf_ctx *conf_ctx = lp_smbconf_ctx();
2121 if (conf_ctx == NULL) {
2125 DEBUG(5, ("process_registry_service: service name %s\n", service_name));
2127 if (!smbconf_share_exists(conf_ctx, service_name)) {
2129 * Registry does not contain data for this service (yet),
2130 * but make sure lp_load doesn't return false.
2136 err = smbconf_get_share(conf_ctx, mem_ctx, service_name, &service);
2137 if (!SBC_ERROR_IS_OK(err)) {
2141 ret = process_smbconf_service(service);
2147 smbconf_changed(conf_ctx, &conf_last_csn, NULL, NULL);
2150 TALLOC_FREE(mem_ctx);
2155 * process_registry_globals
2157 static bool process_registry_globals(void)
2161 add_to_file_list(NULL, &file_lists, INCLUDE_REGISTRY_NAME, INCLUDE_REGISTRY_NAME);
2163 if (!bInGlobalSection && bGlobalOnly) {
2166 const char *pszParmName = "registry shares";
2167 const char *pszParmValue = "yes";
2169 DEBUGADD(4, ("doing parameter %s = %s\n", pszParmName, pszParmValue));
2171 ret = lp_do_parameter(bInGlobalSection ? -2 : iServiceIndex,
2172 pszParmName, pszParmValue);
2179 return process_registry_service(GLOBAL_NAME);
2182 bool process_registry_shares(void)
2186 struct smbconf_service **service = NULL;
2187 uint32_t num_shares = 0;
2188 TALLOC_CTX *mem_ctx = talloc_stackframe();
2189 struct smbconf_ctx *conf_ctx = lp_smbconf_ctx();
2192 if (conf_ctx == NULL) {
2196 err = smbconf_get_config(conf_ctx, mem_ctx, &num_shares, &service);
2197 if (!SBC_ERROR_IS_OK(err)) {
2203 for (count = 0; count < num_shares; count++) {
2204 if (strequal(service[count]->name, GLOBAL_NAME)) {
2207 ret = process_smbconf_service(service[count]);
2214 smbconf_changed(conf_ctx, &conf_last_csn, NULL, NULL);
2217 TALLOC_FREE(mem_ctx);
2222 * reload those shares from registry that are already
2223 * activated in the services array.
2225 static bool reload_registry_shares(void)
2230 for (i = 0; i < iNumServices; i++) {
2235 if (ServicePtrs[i]->usershare == USERSHARE_VALID) {
2239 ret = process_registry_service(ServicePtrs[i]->szService);
2250 #define MAX_INCLUDE_DEPTH 100
2252 static uint8_t include_depth;
2255 * Free the file lists
2257 static void free_file_list(void)
2259 struct file_lists *f;
2260 struct file_lists *next;
2273 * Utility function for outsiders to check if we're running on registry.
2275 bool lp_config_backend_is_registry(void)
2277 return (lp_config_backend() == CONFIG_BACKEND_REGISTRY);
2281 * Utility function to check if the config backend is FILE.
2283 bool lp_config_backend_is_file(void)
2285 return (lp_config_backend() == CONFIG_BACKEND_FILE);
2288 /*******************************************************************
2289 Check if a config file has changed date.
2290 ********************************************************************/
2292 bool lp_file_list_changed(void)
2294 struct file_lists *f = file_lists;
2296 DEBUG(6, ("lp_file_list_changed()\n"));
2299 if (strequal(f->name, INCLUDE_REGISTRY_NAME)) {
2300 struct smbconf_ctx *conf_ctx = lp_smbconf_ctx();
2302 if (conf_ctx == NULL) {
2305 if (smbconf_changed(conf_ctx, &conf_last_csn, NULL,
2308 DEBUGADD(6, ("registry config changed\n"));
2315 n2 = talloc_sub_basic(talloc_tos(),
2316 get_current_username(),
2317 current_user_info.domain,
2322 DEBUGADD(6, ("file %s -> %s last mod_time: %s\n",
2323 f->name, n2, ctime(&f->modtime)));
2325 mod_time = file_modtime(n2);
2328 ((f->modtime != mod_time) ||
2329 (f->subfname == NULL) ||
2330 (strcmp(n2, f->subfname) != 0)))
2333 ("file %s modified: %s\n", n2,
2335 f->modtime = mod_time;
2336 TALLOC_FREE(f->subfname);
2337 f->subfname = talloc_strdup(f, n2);
2338 if (f->subfname == NULL) {
2339 smb_panic("talloc_strdup failed");
2353 * Initialize iconv conversion descriptors.
2355 * This is called the first time it is needed, and also called again
2356 * every time the configuration is reloaded, because the charset or
2357 * codepage might have changed.
2359 static void init_iconv(void)
2361 global_iconv_handle = smb_iconv_handle_reinit(NULL, lp_dos_charset(),
2363 true, global_iconv_handle);
2366 /***************************************************************************
2367 Handle the include operation.
2368 ***************************************************************************/
2369 static bool bAllowIncludeRegistry = true;
2371 bool lp_include(struct loadparm_context *lp_ctx, struct loadparm_service *service,
2372 const char *pszParmValue, char **ptr)
2376 if (include_depth >= MAX_INCLUDE_DEPTH) {
2377 DEBUG(0, ("Error: Maximum include depth (%u) exceeded!\n",
2382 if (strequal(pszParmValue, INCLUDE_REGISTRY_NAME)) {
2383 if (!bAllowIncludeRegistry) {
2386 if (lp_ctx->bInGlobalSection) {
2389 ret = process_registry_globals();
2393 DEBUG(1, ("\"include = registry\" only effective "
2394 "in %s section\n", GLOBAL_NAME));
2399 fname = talloc_sub_basic(talloc_tos(), get_current_username(),
2400 current_user_info.domain,
2403 add_to_file_list(NULL, &file_lists, pszParmValue, fname);
2405 if (service == NULL) {
2406 string_set(Globals.ctx, ptr, fname);
2408 string_set(service, ptr, fname);
2411 if (file_exist(fname)) {
2414 ret = pm_process(fname, lp_do_section, do_parameter, lp_ctx);
2420 DEBUG(2, ("Can't find include file %s\n", fname));
2425 bool lp_idmap_range(const char *domain_name, uint32_t *low, uint32_t *high)
2427 char *config_option = NULL;
2428 const char *range = NULL;
2431 SMB_ASSERT(low != NULL);
2432 SMB_ASSERT(high != NULL);
2434 if ((domain_name == NULL) || (domain_name[0] == '\0')) {
2438 config_option = talloc_asprintf(talloc_tos(), "idmap config %s",
2440 if (config_option == NULL) {
2441 DEBUG(0, ("out of memory\n"));
2445 range = lp_parm_const_string(-1, config_option, "range", NULL);
2446 if (range == NULL) {
2447 DEBUG(1, ("idmap range not specified for domain '%s'\n", domain_name));
2451 if (sscanf(range, "%u - %u", low, high) != 2) {
2452 DEBUG(1, ("error parsing idmap range '%s' for domain '%s'\n",
2453 range, domain_name));
2460 talloc_free(config_option);
2465 bool lp_idmap_default_range(uint32_t *low, uint32_t *high)
2467 return lp_idmap_range("*", low, high);
2470 const char *lp_idmap_backend(const char *domain_name)
2472 char *config_option = NULL;
2473 const char *backend = NULL;
2475 if ((domain_name == NULL) || (domain_name[0] == '\0')) {
2479 config_option = talloc_asprintf(talloc_tos(), "idmap config %s",
2481 if (config_option == NULL) {
2482 DEBUG(0, ("out of memory\n"));
2486 backend = lp_parm_const_string(-1, config_option, "backend", NULL);
2487 if (backend == NULL) {
2488 DEBUG(1, ("idmap backend not specified for domain '%s'\n", domain_name));
2493 talloc_free(config_option);
2497 const char *lp_idmap_default_backend(void)
2499 return lp_idmap_backend("*");
2502 /***************************************************************************
2503 Handle ldap suffixes - default to ldapsuffix if sub-suffixes are not defined.
2504 ***************************************************************************/
2506 static const char *append_ldap_suffix(TALLOC_CTX *ctx, const char *str )
2508 const char *suffix_string;
2510 suffix_string = talloc_asprintf(ctx, "%s,%s", str,
2511 Globals.ldap_suffix );
2512 if ( !suffix_string ) {
2513 DEBUG(0,("append_ldap_suffix: talloc_asprintf() failed!\n"));
2517 return suffix_string;
2520 const char *lp_ldap_machine_suffix(TALLOC_CTX *ctx)
2522 if (Globals.szLdapMachineSuffix[0])
2523 return append_ldap_suffix(ctx, Globals.szLdapMachineSuffix);
2525 return lp_string(ctx, Globals.ldap_suffix);
2528 const char *lp_ldap_user_suffix(TALLOC_CTX *ctx)
2530 if (Globals.szLdapUserSuffix[0])
2531 return append_ldap_suffix(ctx, Globals.szLdapUserSuffix);
2533 return lp_string(ctx, Globals.ldap_suffix);
2536 const char *lp_ldap_group_suffix(TALLOC_CTX *ctx)
2538 if (Globals.szLdapGroupSuffix[0])
2539 return append_ldap_suffix(ctx, Globals.szLdapGroupSuffix);
2541 return lp_string(ctx, Globals.ldap_suffix);
2544 const char *lp_ldap_idmap_suffix(TALLOC_CTX *ctx)
2546 if (Globals.szLdapIdmapSuffix[0])
2547 return append_ldap_suffix(ctx, Globals.szLdapIdmapSuffix);
2549 return lp_string(ctx, Globals.ldap_suffix);
2553 return the parameter pointer for a parameter
2555 void *lp_parm_ptr(struct loadparm_service *service, struct parm_struct *parm)
2557 if (service == NULL) {
2558 if (parm->p_class == P_LOCAL)
2559 return (void *)(((char *)&sDefault)+parm->offset);
2560 else if (parm->p_class == P_GLOBAL)
2561 return (void *)(((char *)&Globals)+parm->offset);
2564 return (void *)(((char *)service) + parm->offset);
2568 /***************************************************************************
2569 Process a parameter for a particular service number. If snum < 0
2570 then assume we are in the globals.
2571 ***************************************************************************/
2573 bool lp_do_parameter(int snum, const char *pszParmName, const char *pszParmValue)
2575 TALLOC_CTX *frame = talloc_stackframe();
2576 struct loadparm_context *lp_ctx;
2579 lp_ctx = loadparm_init_s3(frame,
2580 loadparm_s3_helpers());
2581 if (lp_ctx == NULL) {
2582 DEBUG(0, ("loadparm_init_s3 failed\n"));
2587 lp_ctx->sDefault = &sDefault;
2588 lp_ctx->services = ServicePtrs;
2589 lp_ctx->bInGlobalSection = bInGlobalSection;
2590 lp_ctx->flags = flags_list;
2593 ok = lpcfg_do_global_parameter(lp_ctx, pszParmName, pszParmValue);
2595 ok = lpcfg_do_service_parameter(lp_ctx, ServicePtrs[snum],
2596 pszParmName, pszParmValue);
2604 /***************************************************************************
2605 set a parameter, marking it with FLAG_CMDLINE. Parameters marked as
2606 FLAG_CMDLINE won't be overridden by loads from smb.conf.
2607 ***************************************************************************/
2609 static bool lp_set_cmdline_helper(const char *pszParmName, const char *pszParmValue)
2612 parmnum = lpcfg_map_parameter(pszParmName);
2614 flags_list[parmnum] &= ~FLAG_CMDLINE;
2615 if (!lp_do_parameter(-1, pszParmName, pszParmValue)) {
2618 flags_list[parmnum] |= FLAG_CMDLINE;
2620 /* we have to also set FLAG_CMDLINE on aliases. Aliases must
2621 * be grouped in the table, so we don't have to search the
2624 i>=0 && parm_table[i].offset == parm_table[parmnum].offset
2625 && parm_table[i].p_class == parm_table[parmnum].p_class;
2627 flags_list[i] |= FLAG_CMDLINE;
2629 for (i=parmnum+1;i<num_parameters() && parm_table[i].offset == parm_table[parmnum].offset
2630 && parm_table[i].p_class == parm_table[parmnum].p_class;i++) {
2631 flags_list[i] |= FLAG_CMDLINE;
2637 /* it might be parametric */
2638 if (strchr(pszParmName, ':') != NULL) {
2639 set_param_opt(NULL, &Globals.param_opt, pszParmName, pszParmValue, FLAG_CMDLINE);
2643 DEBUG(0, ("Ignoring unknown parameter \"%s\"\n", pszParmName));
2647 bool lp_set_cmdline(const char *pszParmName, const char *pszParmValue)
2650 TALLOC_CTX *frame = talloc_stackframe();
2651 struct loadparm_context *lp_ctx;
2653 lp_ctx = loadparm_init_s3(talloc_tos(), loadparm_s3_helpers());
2654 if (lp_ctx == NULL) {
2655 DEBUG(0, ("loadparm_init_s3 failed\n"));
2659 ret = lpcfg_set_cmdline(lp_ctx, pszParmName, pszParmValue);
2665 /***************************************************************************
2666 Process a parameter.
2667 ***************************************************************************/
2669 static bool do_parameter(const char *pszParmName, const char *pszParmValue,
2672 if (!bInGlobalSection && bGlobalOnly)
2675 DEBUGADD(4, ("doing parameter %s = %s\n", pszParmName, pszParmValue));
2677 if (bInGlobalSection) {
2678 return lpcfg_do_global_parameter(userdata, pszParmName, pszParmValue);
2680 return lpcfg_do_service_parameter(userdata, ServicePtrs[iServiceIndex],
2681 pszParmName, pszParmValue);
2685 /***************************************************************************
2686 Initialize any local variables in the sDefault table, after parsing a
2688 ***************************************************************************/
2690 static void init_locals(void)
2693 * We run this check once the [globals] is parsed, to force
2694 * the VFS objects and other per-share settings we need for
2695 * the standard way a AD DC is operated. We may change these
2696 * as our code evolves, which is why we force these settings.
2698 * We can't do this at the end of lp_load_ex(), as by that
2699 * point the services have been loaded and they will already
2700 * have "" as their vfs objects.
2702 if (lp_server_role() == ROLE_ACTIVE_DIRECTORY_DC) {
2703 const char **vfs_objects = lp_vfs_objects(-1);
2704 if (!vfs_objects || !vfs_objects[0]) {
2705 if (lp_parm_const_string(-1, "xattr_tdb", "file", NULL)) {
2706 lp_do_parameter(-1, "vfs objects", "dfs_samba4 acl_xattr xattr_tdb");
2707 } else if (lp_parm_const_string(-1, "posix", "eadb", NULL)) {
2708 lp_do_parameter(-1, "vfs objects", "dfs_samba4 acl_xattr posix_eadb");
2710 lp_do_parameter(-1, "vfs objects", "dfs_samba4 acl_xattr");
2714 lp_do_parameter(-1, "map hidden", "no");
2715 lp_do_parameter(-1, "map system", "no");
2716 lp_do_parameter(-1, "map readonly", "no");
2717 lp_do_parameter(-1, "map archive", "no");
2718 lp_do_parameter(-1, "store dos attributes", "yes");
2722 /***************************************************************************
2723 Process a new section (service). At this stage all sections are services.
2724 Later we'll have special sections that permit server parameters to be set.
2725 Returns true on success, false on failure.
2726 ***************************************************************************/
2728 bool lp_do_section(const char *pszSectionName, void *userdata)
2730 struct loadparm_context *lp_ctx = (struct loadparm_context *)userdata;
2732 bool isglobal = ((strwicmp(pszSectionName, GLOBAL_NAME) == 0) ||
2733 (strwicmp(pszSectionName, GLOBAL_NAME2) == 0));
2736 /* if we were in a global section then do the local inits */
2737 if (bInGlobalSection && !isglobal)
2740 /* if we've just struck a global section, note the fact. */
2741 bInGlobalSection = isglobal;
2742 lp_ctx->bInGlobalSection = isglobal;
2744 /* check for multiple global sections */
2745 if (bInGlobalSection) {
2746 DEBUG(3, ("Processing section \"[%s]\"\n", pszSectionName));
2750 if (!bInGlobalSection && bGlobalOnly)
2753 /* if we have a current service, tidy it up before moving on */
2756 if (iServiceIndex >= 0)
2757 bRetval = lpcfg_service_ok(ServicePtrs[iServiceIndex]);
2759 /* if all is still well, move to the next record in the services array */
2761 /* We put this here to avoid an odd message order if messages are */
2762 /* issued by the post-processing of a previous section. */
2763 DEBUG(2, ("Processing section \"[%s]\"\n", pszSectionName));
2765 iServiceIndex = add_a_service(&sDefault, pszSectionName);
2766 if (iServiceIndex < 0) {
2767 DEBUG(0, ("Failed to add a new service\n"));
2770 /* Clean all parametric options for service */
2771 /* They will be added during parsing again */
2772 free_param_opts(&ServicePtrs[iServiceIndex]->param_opt);
2779 /***************************************************************************
2780 Determine if a partcular base parameter is currentl set to the default value.
2781 ***************************************************************************/
2783 static bool is_default(int i)
2785 switch (parm_table[i].type) {
2788 return str_list_equal((const char * const *)parm_table[i].def.lvalue,
2789 *(const char ***)lp_parm_ptr(NULL,
2793 return strequal(parm_table[i].def.svalue,
2794 *(char **)lp_parm_ptr(NULL,
2798 return parm_table[i].def.bvalue ==
2799 *(bool *)lp_parm_ptr(NULL,
2802 return parm_table[i].def.cvalue ==
2803 *(char *)lp_parm_ptr(NULL,
2809 return parm_table[i].def.ivalue ==
2810 *(int *)lp_parm_ptr(NULL,
2818 /***************************************************************************
2819 Display the contents of the global structure.
2820 ***************************************************************************/
2822 static void dump_globals(FILE *f, bool show_defaults)
2825 struct parmlist_entry *data;
2827 fprintf(f, "[global]\n");
2829 for (i = 0; parm_table[i].label; i++)
2830 if (parm_table[i].p_class == P_GLOBAL &&
2831 !(parm_table[i].flags & FLAG_META) &&
2832 (i == 0 || (parm_table[i].offset != parm_table[i - 1].offset))) {
2833 if (show_defaults && is_default(i))
2835 fprintf(f, "\t%s = ", parm_table[i].label);
2836 lpcfg_print_parameter(&parm_table[i], lp_parm_ptr(NULL,
2841 if (Globals.param_opt != NULL) {
2842 data = Globals.param_opt;
2844 if (!show_defaults && (data->priority & FLAG_DEFAULT)) {
2848 fprintf(f, "\t%s = %s\n", data->key, data->value);
2855 /***************************************************************************
2856 Display the contents of a parameter of a single services record.
2857 ***************************************************************************/
2859 bool dump_a_parameter(int snum, char *parm_name, FILE * f, bool isGlobal)
2861 bool result = false;
2863 struct loadparm_context *lp_ctx;
2865 lp_ctx = loadparm_init_s3(talloc_tos(), loadparm_s3_helpers());
2866 if (lp_ctx == NULL) {
2871 result = lpcfg_dump_a_parameter(lp_ctx, NULL, parm_name, f);
2873 result = lpcfg_dump_a_parameter(lp_ctx, ServicePtrs[snum], parm_name, f);
2875 TALLOC_FREE(lp_ctx);
2879 /***************************************************************************
2880 Return info about the requested parameter (given as a string).
2881 Return NULL when the string is not a valid parameter name.
2882 ***************************************************************************/
2884 struct parm_struct *lp_get_parameter(const char *param_name)
2886 int num = lpcfg_map_parameter(param_name);
2892 return &parm_table[num];
2896 /***************************************************************************
2897 Display the contents of a single copy structure.
2898 ***************************************************************************/
2899 static void dump_copy_map(bool *pcopymap)
2905 printf("\n\tNon-Copied parameters:\n");
2907 for (i = 0; parm_table[i].label; i++)
2908 if (parm_table[i].p_class == P_LOCAL &&
2909 parm_table[i].ptr && !pcopymap[i] &&
2910 (i == 0 || (parm_table[i].ptr != parm_table[i - 1].ptr)))
2912 printf("\t\t%s\n", parm_table[i].label);
2917 /***************************************************************************
2918 Return TRUE if the passed service number is within range.
2919 ***************************************************************************/
2921 bool lp_snum_ok(int iService)
2923 return (LP_SNUM_OK(iService) && ServicePtrs[iService]->bAvailable);
2926 /***************************************************************************
2927 Auto-load some home services.
2928 ***************************************************************************/
2930 static void lp_add_auto_services(char *str)
2940 s = talloc_strdup(talloc_tos(), str);
2942 smb_panic("talloc_strdup failed");
2946 homes = lp_servicenumber(HOMES_NAME);
2948 for (p = strtok_r(s, LIST_SEP, &saveptr); p;
2949 p = strtok_r(NULL, LIST_SEP, &saveptr)) {
2952 if (lp_servicenumber(p) >= 0)
2955 home = get_user_home_dir(talloc_tos(), p);
2957 if (home && home[0] && homes >= 0)
2958 lp_add_home(p, homes, p, home);
2965 /***************************************************************************
2966 Auto-load one printer.
2967 ***************************************************************************/
2969 void lp_add_one_printer(const char *name, const char *comment,
2970 const char *location, void *pdata)
2972 int printers = lp_servicenumber(PRINTERS_NAME);
2975 if (lp_servicenumber(name) < 0) {
2976 lp_add_printer(name, printers);
2977 if ((i = lp_servicenumber(name)) >= 0) {
2978 string_set(ServicePtrs[i], &ServicePtrs[i]->comment, comment);
2979 ServicePtrs[i]->autoloaded = true;
2984 /***************************************************************************
2985 Have we loaded a services file yet?
2986 ***************************************************************************/
2988 bool lp_loaded(void)
2993 /***************************************************************************
2994 Unload unused services.
2995 ***************************************************************************/
2997 void lp_killunused(struct smbd_server_connection *sconn,
2998 bool (*snumused) (struct smbd_server_connection *, int))
3001 for (i = 0; i < iNumServices; i++) {
3005 /* don't kill autoloaded or usershare services */
3006 if ( ServicePtrs[i]->autoloaded ||
3007 ServicePtrs[i]->usershare == USERSHARE_VALID) {
3011 if (!snumused || !snumused(sconn, i)) {
3012 free_service_byindex(i);
3018 * Kill all except autoloaded and usershare services - convenience wrapper
3020 void lp_kill_all_services(void)
3022 lp_killunused(NULL, NULL);
3025 /***************************************************************************
3027 ***************************************************************************/
3029 void lp_killservice(int iServiceIn)
3031 if (VALID(iServiceIn)) {
3032 free_service_byindex(iServiceIn);
3036 /***************************************************************************
3037 Save the curent values of all global and sDefault parameters into the
3038 defaults union. This allows testparm to show only the
3039 changed (ie. non-default) parameters.
3040 ***************************************************************************/
3042 static void lp_save_defaults(void)
3045 struct parmlist_entry * parm;
3046 for (i = 0; parm_table[i].label; i++) {
3047 if (!(flags_list[i] & FLAG_CMDLINE)) {
3048 flags_list[i] |= FLAG_DEFAULT;
3051 if (i > 0 && parm_table[i].offset == parm_table[i - 1].offset
3052 && parm_table[i].p_class == parm_table[i - 1].p_class)
3054 switch (parm_table[i].type) {
3057 parm_table[i].def.lvalue = str_list_copy(
3058 NULL, *(const char ***)lp_parm_ptr(NULL, &parm_table[i]));
3062 parm_table[i].def.svalue = talloc_strdup(Globals.ctx, *(char **)lp_parm_ptr(NULL, &parm_table[i]));
3063 if (parm_table[i].def.svalue == NULL) {
3064 smb_panic("talloc_strdup failed");
3069 parm_table[i].def.bvalue =
3070 *(bool *)lp_parm_ptr(NULL, &parm_table[i]);
3073 parm_table[i].def.cvalue =
3074 *(char *)lp_parm_ptr(NULL, &parm_table[i]);
3080 parm_table[i].def.ivalue =
3081 *(int *)lp_parm_ptr(NULL, &parm_table[i]);
3088 for (parm=Globals.param_opt; parm; parm=parm->next) {
3089 if (!(parm->priority & FLAG_CMDLINE)) {
3090 parm->priority |= FLAG_DEFAULT;
3094 for (parm=sDefault.param_opt; parm; parm=parm->next) {
3095 if (!(parm->priority & FLAG_CMDLINE)) {
3096 parm->priority |= FLAG_DEFAULT;
3100 defaults_saved = true;
3103 /***********************************************************
3104 If we should send plaintext/LANMAN passwords in the clinet
3105 ************************************************************/
3107 static void set_allowed_client_auth(void)
3109 if (Globals.client_ntlmv2_auth) {
3110 Globals.client_lanman_auth = false;
3112 if (!Globals.client_lanman_auth) {
3113 Globals.client_plaintext_auth = false;
3117 /***************************************************************************
3119 The following code allows smbd to read a user defined share file.
3120 Yes, this is my intent. Yes, I'm comfortable with that...
3122 THE FOLLOWING IS SECURITY CRITICAL CODE.
3124 It washes your clothes, it cleans your house, it guards you while you sleep...
3125 Do not f%^k with it....
3126 ***************************************************************************/
3128 #define MAX_USERSHARE_FILE_SIZE (10*1024)
3130 /***************************************************************************
3131 Check allowed stat state of a usershare file.
3132 Ensure we print out who is dicking with us so the admin can
3133 get their sorry ass fired.
3134 ***************************************************************************/
3136 static bool check_usershare_stat(const char *fname,
3137 const SMB_STRUCT_STAT *psbuf)
3139 if (!S_ISREG(psbuf->st_ex_mode)) {
3140 DEBUG(0,("check_usershare_stat: file %s owned by uid %u is "
3141 "not a regular file\n",
3142 fname, (unsigned int)psbuf->st_ex_uid ));
3146 /* Ensure this doesn't have the other write bit set. */
3147 if (psbuf->st_ex_mode & S_IWOTH) {
3148 DEBUG(0,("check_usershare_stat: file %s owned by uid %u allows "
3149 "public write. Refusing to allow as a usershare file.\n",
3150 fname, (unsigned int)psbuf->st_ex_uid ));
3154 /* Should be 10k or less. */
3155 if (psbuf->st_ex_size > MAX_USERSHARE_FILE_SIZE) {
3156 DEBUG(0,("check_usershare_stat: file %s owned by uid %u is "
3157 "too large (%u) to be a user share file.\n",
3158 fname, (unsigned int)psbuf->st_ex_uid,
3159 (unsigned int)psbuf->st_ex_size ));
3166 /***************************************************************************
3167 Parse the contents of a usershare file.
3168 ***************************************************************************/
3170 enum usershare_err parse_usershare_file(TALLOC_CTX *ctx,
3171 SMB_STRUCT_STAT *psbuf,
3172 const char *servicename,
3176 char **pp_sharepath,
3178 char **pp_cp_servicename,
3179 struct security_descriptor **ppsd,
3182 const char **prefixallowlist = lp_usershare_prefix_allow_list();
3183 const char **prefixdenylist = lp_usershare_prefix_deny_list();
3186 SMB_STRUCT_STAT sbuf;
3187 char *sharepath = NULL;
3188 char *comment = NULL;
3190 *pp_sharepath = NULL;
3193 *pallow_guest = false;
3196 return USERSHARE_MALFORMED_FILE;
3199 if (strcmp(lines[0], "#VERSION 1") == 0) {
3201 } else if (strcmp(lines[0], "#VERSION 2") == 0) {
3204 return USERSHARE_MALFORMED_FILE;
3207 return USERSHARE_BAD_VERSION;
3210 if (strncmp(lines[1], "path=", 5) != 0) {
3211 return USERSHARE_MALFORMED_PATH;
3214 sharepath = talloc_strdup(ctx, &lines[1][5]);
3216 return USERSHARE_POSIX_ERR;
3218 trim_string(sharepath, " ", " ");
3220 if (strncmp(lines[2], "comment=", 8) != 0) {
3221 return USERSHARE_MALFORMED_COMMENT_DEF;
3224 comment = talloc_strdup(ctx, &lines[2][8]);
3226 return USERSHARE_POSIX_ERR;
3228 trim_string(comment, " ", " ");
3229 trim_char(comment, '"', '"');
3231 if (strncmp(lines[3], "usershare_acl=", 14) != 0) {
3232 return USERSHARE_MALFORMED_ACL_DEF;
3235 if (!parse_usershare_acl(ctx, &lines[3][14], ppsd)) {
3236 return USERSHARE_ACL_ERR;
3240 if (strncmp(lines[4], "guest_ok=", 9) != 0) {
3241 return USERSHARE_MALFORMED_ACL_DEF;
3243 if (lines[4][9] == 'y') {
3244 *pallow_guest = true;
3247 /* Backwards compatible extension to file version #2. */
3249 if (strncmp(lines[5], "sharename=", 10) != 0) {
3250 return USERSHARE_MALFORMED_SHARENAME_DEF;
3252 if (!strequal(&lines[5][10], servicename)) {
3253 return USERSHARE_BAD_SHARENAME;
3255 *pp_cp_servicename = talloc_strdup(ctx, &lines[5][10]);
3256 if (!*pp_cp_servicename) {
3257 return USERSHARE_POSIX_ERR;
3262 if (*pp_cp_servicename == NULL) {
3263 *pp_cp_servicename = talloc_strdup(ctx, servicename);
3264 if (!*pp_cp_servicename) {
3265 return USERSHARE_POSIX_ERR;
3269 if (snum != -1 && (strcmp(sharepath, ServicePtrs[snum]->path) == 0)) {
3270 /* Path didn't change, no checks needed. */
3271 *pp_sharepath = sharepath;
3272 *pp_comment = comment;
3273 return USERSHARE_OK;
3276 /* The path *must* be absolute. */
3277 if (sharepath[0] != '/') {
3278 DEBUG(2,("parse_usershare_file: share %s: path %s is not an absolute path.\n",
3279 servicename, sharepath));
3280 return USERSHARE_PATH_NOT_ABSOLUTE;
3283 /* If there is a usershare prefix deny list ensure one of these paths
3284 doesn't match the start of the user given path. */
3285 if (prefixdenylist) {
3287 for ( i=0; prefixdenylist[i]; i++ ) {
3288 DEBUG(10,("parse_usershare_file: share %s : checking prefixdenylist[%d]='%s' against %s\n",
3289 servicename, i, prefixdenylist[i], sharepath ));
3290 if (memcmp( sharepath, prefixdenylist[i], strlen(prefixdenylist[i])) == 0) {
3291 DEBUG(2,("parse_usershare_file: share %s path %s starts with one of the "
3292 "usershare prefix deny list entries.\n",
3293 servicename, sharepath));
3294 return USERSHARE_PATH_IS_DENIED;
3299 /* If there is a usershare prefix allow list ensure one of these paths
3300 does match the start of the user given path. */
3302 if (prefixallowlist) {
3304 for ( i=0; prefixallowlist[i]; i++ ) {
3305 DEBUG(10,("parse_usershare_file: share %s checking prefixallowlist[%d]='%s' against %s\n",
3306 servicename, i, prefixallowlist[i], sharepath ));
3307 if (memcmp( sharepath, prefixallowlist[i], strlen(prefixallowlist[i])) == 0) {
3311 if (prefixallowlist[i] == NULL) {
3312 DEBUG(2,("parse_usershare_file: share %s path %s doesn't start with one of the "
3313 "usershare prefix allow list entries.\n",
3314 servicename, sharepath));
3315 return USERSHARE_PATH_NOT_ALLOWED;
3319 /* Ensure this is pointing to a directory. */
3320 dp = opendir(sharepath);
3323 DEBUG(2,("parse_usershare_file: share %s path %s is not a directory.\n",
3324 servicename, sharepath));
3325 return USERSHARE_PATH_NOT_DIRECTORY;
3328 /* Ensure the owner of the usershare file has permission to share
3331 if (sys_stat(sharepath, &sbuf, false) == -1) {
3332 DEBUG(2,("parse_usershare_file: share %s : stat failed on path %s. %s\n",
3333 servicename, sharepath, strerror(errno) ));
3335 return USERSHARE_POSIX_ERR;
3340 if (!S_ISDIR(sbuf.st_ex_mode)) {
3341 DEBUG(2,("parse_usershare_file: share %s path %s is not a directory.\n",
3342 servicename, sharepath ));
3343 return USERSHARE_PATH_NOT_DIRECTORY;
3346 /* Check if sharing is restricted to owner-only. */
3347 /* psbuf is the stat of the usershare definition file,
3348 sbuf is the stat of the target directory to be shared. */
3350 if (lp_usershare_owner_only()) {
3351 /* root can share anything. */
3352 if ((psbuf->st_ex_uid != 0) && (sbuf.st_ex_uid != psbuf->st_ex_uid)) {
3353 return USERSHARE_PATH_NOT_ALLOWED;
3357 *pp_sharepath = sharepath;
3358 *pp_comment = comment;
3359 return USERSHARE_OK;
3362 /***************************************************************************
3363 Deal with a usershare file.
3366 -1 - Bad name, invalid contents.
3367 - service name already existed and not a usershare, problem
3368 with permissions to share directory etc.
3369 ***************************************************************************/
3371 static int process_usershare_file(const char *dir_name, const char *file_name, int snum_template)
3373 SMB_STRUCT_STAT sbuf;
3374 SMB_STRUCT_STAT lsbuf;
3376 char *sharepath = NULL;
3377 char *comment = NULL;
3378 char *cp_service_name = NULL;
3379 char **lines = NULL;
3383 TALLOC_CTX *ctx = talloc_stackframe();
3384 struct security_descriptor *psd = NULL;
3385 bool guest_ok = false;
3386 char *canon_name = NULL;
3387 bool added_service = false;
3390 /* Ensure share name doesn't contain invalid characters. */
3391 if (!validate_net_name(file_name, INVALID_SHARENAME_CHARS, strlen(file_name))) {
3392 DEBUG(0,("process_usershare_file: share name %s contains "
3393 "invalid characters (any of %s)\n",
3394 file_name, INVALID_SHARENAME_CHARS ));
3398 canon_name = canonicalize_servicename(ctx, file_name);
3403 fname = talloc_asprintf(ctx, "%s/%s", dir_name, file_name);
3408 /* Minimize the race condition by doing an lstat before we
3409 open and fstat. Ensure this isn't a symlink link. */
3411 if (sys_lstat(fname, &lsbuf, false) != 0) {
3412 DEBUG(0,("process_usershare_file: stat of %s failed. %s\n",
3413 fname, strerror(errno) ));
3417 /* This must be a regular file, not a symlink, directory or
3418 other strange filetype. */
3419 if (!check_usershare_stat(fname, &lsbuf)) {
3427 status = dbwrap_fetch_bystring(ServiceHash, canon_name,
3432 if (NT_STATUS_IS_OK(status) &&
3433 (data.dptr != NULL) &&
3434 (data.dsize == sizeof(iService))) {
3435 memcpy(&iService, data.dptr, sizeof(iService));
3439 if (iService != -1 &&
3440 timespec_compare(&ServicePtrs[iService]->usershare_last_mod,
3441 &lsbuf.st_ex_mtime) == 0) {
3442 /* Nothing changed - Mark valid and return. */
3443 DEBUG(10,("process_usershare_file: service %s not changed.\n",
3445 ServicePtrs[iService]->usershare = USERSHARE_VALID;
3450 /* Try and open the file read only - no symlinks allowed. */
3452 fd = open(fname, O_RDONLY|O_NOFOLLOW, 0);
3454 fd = open(fname, O_RDONLY, 0);
3458 DEBUG(0,("process_usershare_file: unable to open %s. %s\n",
3459 fname, strerror(errno) ));
3463 /* Now fstat to be *SURE* it's a regular file. */
3464 if (sys_fstat(fd, &sbuf, false) != 0) {
3466 DEBUG(0,("process_usershare_file: fstat of %s failed. %s\n",
3467 fname, strerror(errno) ));
3471 /* Is it the same dev/inode as was lstated ? */
3472 if (!check_same_stat(&lsbuf, &sbuf)) {
3474 DEBUG(0,("process_usershare_file: fstat of %s is a different file from lstat. "
3475 "Symlink spoofing going on ?\n", fname ));
3479 /* This must be a regular file, not a symlink, directory or
3480 other strange filetype. */
3481 if (!check_usershare_stat(fname, &sbuf)) {
3486 lines = fd_lines_load(fd, &numlines, MAX_USERSHARE_FILE_SIZE, NULL);
3489 if (lines == NULL) {
3490 DEBUG(0,("process_usershare_file: loading file %s owned by %u failed.\n",
3491 fname, (unsigned int)sbuf.st_ex_uid ));
3495 if (parse_usershare_file(ctx, &sbuf, file_name,
3496 iService, lines, numlines, &sharepath,
3497 &comment, &cp_service_name,
3498 &psd, &guest_ok) != USERSHARE_OK) {
3502 /* Everything ok - add the service possibly using a template. */
3504 const struct loadparm_service *sp = &sDefault;
3505 if (snum_template != -1) {
3506 sp = ServicePtrs[snum_template];
3509 if ((iService = add_a_service(sp, cp_service_name)) < 0) {
3510 DEBUG(0, ("process_usershare_file: Failed to add "
3511 "new service %s\n", cp_service_name));
3515 added_service = true;
3517 /* Read only is controlled by usershare ACL below. */
3518 ServicePtrs[iService]->read_only = false;
3521 /* Write the ACL of the new/modified share. */
3522 if (!set_share_security(canon_name, psd)) {
3523 DEBUG(0, ("process_usershare_file: Failed to set share "
3524 "security for user share %s\n",
3529 /* If from a template it may be marked invalid. */
3530 ServicePtrs[iService]->valid = true;
3532 /* Set the service as a valid usershare. */
3533 ServicePtrs[iService]->usershare = USERSHARE_VALID;
3535 /* Set guest access. */
3536 if (lp_usershare_allow_guests()) {
3537 ServicePtrs[iService]->guest_ok = guest_ok;
3540 /* And note when it was loaded. */
3541 ServicePtrs[iService]->usershare_last_mod = sbuf.st_ex_mtime;
3542 string_set(ServicePtrs[iService], &ServicePtrs[iService]->path, sharepath);
3543 string_set(ServicePtrs[iService], &ServicePtrs[iService]->comment, comment);
3549 if (ret == -1 && iService != -1 && added_service) {
3550 lp_remove_service(iService);
3558 /***************************************************************************
3559 Checks if a usershare entry has been modified since last load.
3560 ***************************************************************************/
3562 static bool usershare_exists(int iService, struct timespec *last_mod)
3564 SMB_STRUCT_STAT lsbuf;
3565 const char *usersharepath = Globals.usershare_path;
3568 fname = talloc_asprintf(talloc_tos(),
3571 ServicePtrs[iService]->szService);
3572 if (fname == NULL) {
3576 if (sys_lstat(fname, &lsbuf, false) != 0) {
3581 if (!S_ISREG(lsbuf.st_ex_mode)) {
3587 *last_mod = lsbuf.st_ex_mtime;
3591 /***************************************************************************
3592 Load a usershare service by name. Returns a valid servicenumber or -1.
3593 ***************************************************************************/
3595 int load_usershare_service(const char *servicename)
3597 SMB_STRUCT_STAT sbuf;
3598 const char *usersharepath = Globals.usershare_path;
3599 int max_user_shares = Globals.usershare_max_shares;
3600 int snum_template = -1;
3602 if (*usersharepath == 0 || max_user_shares == 0) {
3606 if (sys_stat(usersharepath, &sbuf, false) != 0) {
3607 DEBUG(0,("load_usershare_service: stat of %s failed. %s\n",
3608 usersharepath, strerror(errno) ));
3612 if (!S_ISDIR(sbuf.st_ex_mode)) {
3613 DEBUG(0,("load_usershare_service: %s is not a directory.\n",
3619 * This directory must be owned by root, and have the 't' bit set.
3620 * It also must not be writable by "other".
3624 if (sbuf.st_ex_uid != 0 || !(sbuf.st_ex_mode & S_ISVTX) || (sbuf.st_ex_mode & S_IWOTH)) {
3626 if (sbuf.st_ex_uid != 0 || (sbuf.st_ex_mode & S_IWOTH)) {
3628 DEBUG(0,("load_usershare_service: directory %s is not owned by root "
3629 "or does not have the sticky bit 't' set or is writable by anyone.\n",
3634 /* Ensure the template share exists if it's set. */
3635 if (Globals.usershare_template_share[0]) {
3636 /* We can't use lp_servicenumber here as we are recommending that
3637 template shares have -valid=false set. */
3638 for (snum_template = iNumServices - 1; snum_template >= 0; snum_template--) {
3639 if (ServicePtrs[snum_template]->szService &&
3640 strequal(ServicePtrs[snum_template]->szService,
3641 Globals.usershare_template_share)) {
3646 if (snum_template == -1) {
3647 DEBUG(0,("load_usershare_service: usershare template share %s "
3648 "does not exist.\n",
3649 Globals.usershare_template_share ));
3654 return process_usershare_file(usersharepath, servicename, snum_template);
3657 /***************************************************************************
3658 Load all user defined shares from the user share directory.
3659 We only do this if we're enumerating the share list.
3660 This is the function that can delete usershares that have
3662 ***************************************************************************/
3664 int load_usershare_shares(struct smbd_server_connection *sconn,
3665 bool (*snumused) (struct smbd_server_connection *, int))
3668 SMB_STRUCT_STAT sbuf;
3670 int num_usershares = 0;
3671 int max_user_shares = Globals.usershare_max_shares;
3672 unsigned int num_dir_entries, num_bad_dir_entries, num_tmp_dir_entries;
3673 unsigned int allowed_bad_entries = ((2*max_user_shares)/10);
3674 unsigned int allowed_tmp_entries = ((2*max_user_shares)/10);
3676 int snum_template = -1;
3677 const char *usersharepath = Globals.usershare_path;
3678 int ret = lp_numservices();
3679 TALLOC_CTX *tmp_ctx;
3681 if (max_user_shares == 0 || *usersharepath == '\0') {
3682 return lp_numservices();
3685 if (sys_stat(usersharepath, &sbuf, false) != 0) {
3686 DEBUG(0,("load_usershare_shares: stat of %s failed. %s\n",
3687 usersharepath, strerror(errno) ));
3692 * This directory must be owned by root, and have the 't' bit set.
3693 * It also must not be writable by "other".
3697 if (sbuf.st_ex_uid != 0 || !(sbuf.st_ex_mode & S_ISVTX) || (sbuf.st_ex_mode & S_IWOTH)) {
3699 if (sbuf.st_ex_uid != 0 || (sbuf.st_ex_mode & S_IWOTH)) {
3701 DEBUG(0,("load_usershare_shares: directory %s is not owned by root "
3702 "or does not have the sticky bit 't' set or is writable by anyone.\n",
3707 /* Ensure the template share exists if it's set. */
3708 if (Globals.usershare_template_share[0]) {
3709 /* We can't use lp_servicenumber here as we are recommending that
3710 template shares have -valid=false set. */
3711 for (snum_template = iNumServices - 1; snum_template >= 0; snum_template--) {
3712 if (ServicePtrs[snum_template]->szService &&
3713 strequal(ServicePtrs[snum_template]->szService,
3714 Globals.usershare_template_share)) {
3719 if (snum_template == -1) {
3720 DEBUG(0,("load_usershare_shares: usershare template share %s "
3721 "does not exist.\n",
3722 Globals.usershare_template_share ));
3727 /* Mark all existing usershares as pending delete. */
3728 for (iService = iNumServices - 1; iService >= 0; iService--) {
3729 if (VALID(iService) && ServicePtrs[iService]->usershare) {
3730 ServicePtrs[iService]->usershare = USERSHARE_PENDING_DELETE;
3734 dp = opendir(usersharepath);
3736 DEBUG(0,("load_usershare_shares:: failed to open directory %s. %s\n",
3737 usersharepath, strerror(errno) ));
3741 for (num_dir_entries = 0, num_bad_dir_entries = 0, num_tmp_dir_entries = 0;
3743 num_dir_entries++ ) {
3745 const char *n = de->d_name;
3747 /* Ignore . and .. */
3749 if ((n[1] == '\0') || (n[1] == '.' && n[2] == '\0')) {
3755 /* Temporary file used when creating a share. */
3756 num_tmp_dir_entries++;
3759 /* Allow 20% tmp entries. */
3760 if (num_tmp_dir_entries > allowed_tmp_entries) {
3761 DEBUG(0,("load_usershare_shares: too many temp entries (%u) "
3762 "in directory %s\n",
3763 num_tmp_dir_entries, usersharepath));
3767 r = process_usershare_file(usersharepath, n, snum_template);
3769 /* Update the services count. */
3771 if (num_usershares >= max_user_shares) {
3772 DEBUG(0,("load_usershare_shares: max user shares reached "
3773 "on file %s in directory %s\n",
3774 n, usersharepath ));
3777 } else if (r == -1) {
3778 num_bad_dir_entries++;
3781 /* Allow 20% bad entries. */
3782 if (num_bad_dir_entries > allowed_bad_entries) {
3783 DEBUG(0,("load_usershare_shares: too many bad entries (%u) "
3784 "in directory %s\n",
3785 num_bad_dir_entries, usersharepath));
3789 /* Allow 20% bad entries. */
3790 if (num_dir_entries > max_user_shares + allowed_bad_entries) {
3791 DEBUG(0,("load_usershare_shares: too many total entries (%u) "
3792 "in directory %s\n",
3793 num_dir_entries, usersharepath));
3800 /* Sweep through and delete any non-refreshed usershares that are
3801 not currently in use. */
3802 tmp_ctx = talloc_stackframe();
3803 for (iService = iNumServices - 1; iService >= 0; iService--) {
3804 if (VALID(iService) && (ServicePtrs[iService]->usershare == USERSHARE_PENDING_DELETE)) {
3807 if (snumused && snumused(sconn, iService)) {
3811 servname = lp_servicename(tmp_ctx, iService);
3813 /* Remove from the share ACL db. */
3814 DEBUG(10,("load_usershare_shares: Removing deleted usershare %s\n",
3816 delete_share_security(servname);
3817 free_service_byindex(iService);
3820 talloc_free(tmp_ctx);
3822 return lp_numservices();
3825 /********************************************************
3826 Destroy global resources allocated in this file
3827 ********************************************************/
3829 void gfree_loadparm(void)
3835 /* Free resources allocated to services */
3837 for ( i = 0; i < iNumServices; i++ ) {
3839 free_service_byindex(i);
3843 TALLOC_FREE( ServicePtrs );
3846 /* Now release all resources allocated to global
3847 parameters and the default service */
3849 free_global_parameters();
3853 /***************************************************************************
3854 Allow client apps to specify that they are a client
3855 ***************************************************************************/
3856 static void lp_set_in_client(bool b)
3862 /***************************************************************************
3863 Determine if we're running in a client app
3864 ***************************************************************************/
3865 static bool lp_is_in_client(void)
3870 /***************************************************************************
3871 Load the services array from the services file. Return true on success,
3873 ***************************************************************************/
3875 static bool lp_load_ex(const char *pszFname,
3879 bool initialize_globals,
3880 bool allow_include_registry,
3881 bool load_all_shares)
3885 TALLOC_CTX *frame = talloc_stackframe();
3886 struct loadparm_context *lp_ctx;
3890 DEBUG(3, ("lp_load_ex: refreshing parameters\n"));
3892 bInGlobalSection = true;
3893 bGlobalOnly = global_only;
3894 bAllowIncludeRegistry = allow_include_registry;
3896 lp_ctx = loadparm_init_s3(talloc_tos(),
3897 loadparm_s3_helpers());
3899 lp_ctx->sDefault = &sDefault;
3900 lp_ctx->bInGlobalSection = bInGlobalSection;
3902 init_globals(lp_ctx, initialize_globals);
3906 if (save_defaults) {
3911 if (!initialize_globals) {
3912 free_param_opts(&Globals.param_opt);
3913 apply_lp_set_cmdline();
3916 lp_do_parameter(-1, "idmap config * : backend", Globals.szIdmapBackend);
3918 /* We get sections first, so have to start 'behind' to make up */
3921 if (lp_config_backend_is_file()) {
3922 n2 = talloc_sub_basic(talloc_tos(), get_current_username(),
3923 current_user_info.domain,
3926 smb_panic("lp_load_ex: out of memory");
3929 add_to_file_list(NULL, &file_lists, pszFname, n2);
3931 bRetval = pm_process(n2, lp_do_section, do_parameter, lp_ctx);
3934 /* finish up the last section */
3935 DEBUG(4, ("pm_process() returned %s\n", BOOLSTR(bRetval)));
3937 if (iServiceIndex >= 0) {
3938 bRetval = lpcfg_service_ok(ServicePtrs[iServiceIndex]);
3942 if (lp_config_backend_is_registry()) {
3944 /* config backend changed to registry in config file */
3946 * We need to use this extra global variable here to
3947 * survive restart: init_globals uses this as a default
3948 * for config_backend. Otherwise, init_globals would
3949 * send us into an endless loop here.
3952 config_backend = CONFIG_BACKEND_REGISTRY;
3954 DEBUG(1, ("lp_load_ex: changing to config backend "
3956 init_globals(lp_ctx, true);
3958 TALLOC_FREE(lp_ctx);
3960 lp_kill_all_services();
3961 ok = lp_load_ex(pszFname, global_only, save_defaults,
3962 add_ipc, initialize_globals,
3963 allow_include_registry,
3968 } else if (lp_config_backend_is_registry()) {
3969 bRetval = process_registry_globals();
3971 DEBUG(0, ("Illegal config backend given: %d\n",
3972 lp_config_backend()));
3976 if (bRetval && lp_registry_shares()) {
3977 if (load_all_shares) {
3978 bRetval = process_registry_shares();
3980 bRetval = reload_registry_shares();
3985 char *serv = lp_auto_services(talloc_tos());
3986 lp_add_auto_services(serv);
3991 /* When 'restrict anonymous = 2' guest connections to ipc$
3993 lp_add_ipc("IPC$", (lp_restrict_anonymous() < 2));
3994 if ( lp_enable_asu_support() ) {
3995 lp_add_ipc("ADMIN$", false);
3999 set_allowed_client_auth();
4001 if (lp_security() == SEC_ADS && strchr(lp_password_server(), ':')) {
4002 DEBUG(1, ("WARNING: The optional ':port' in password server = %s is deprecated\n",
4003 lp_password_server()));
4008 /* Now we check we_are_a_wins_server and set szWINSserver to 127.0.0.1 */
4009 /* if we_are_a_wins_server is true and we are in the client */
4010 if (lp_is_in_client() && Globals.we_are_a_wins_server) {
4011 lp_do_parameter(GLOBAL_SECTION_SNUM, "wins server", "127.0.0.1");
4016 fault_configure(smb_panic_s3);
4019 * We run this check once the whole smb.conf is parsed, to
4020 * force some settings for the standard way a AD DC is
4021 * operated. We may changed these as our code evolves, which
4022 * is why we force these settings.
4024 if (lp_server_role() == ROLE_ACTIVE_DIRECTORY_DC) {
4025 lp_do_parameter(-1, "passdb backend", "samba_dsdb");
4027 lp_do_parameter(-1, "winbindd:use external pipes", "true");
4029 lp_do_parameter(-1, "rpc_server:default", "external");
4030 lp_do_parameter(-1, "rpc_server:svcctl", "embedded");
4031 lp_do_parameter(-1, "rpc_server:srvsvc", "embedded");
4032 lp_do_parameter(-1, "rpc_server:eventlog", "embedded");
4033 lp_do_parameter(-1, "rpc_server:ntsvcs", "embedded");
4034 lp_do_parameter(-1, "rpc_server:winreg", "embedded");
4035 lp_do_parameter(-1, "rpc_server:spoolss", "embedded");
4036 lp_do_parameter(-1, "rpc_daemon:spoolssd", "embedded");
4037 lp_do_parameter(-1, "rpc_server:tcpip", "no");
4040 bAllowIncludeRegistry = true;
4046 bool lp_load(const char *pszFname,
4050 bool initialize_globals)
4052 return lp_load_ex(pszFname,
4057 true, /* allow_include_registry */
4058 false); /* load_all_shares*/
4061 bool lp_load_initial_only(const char *pszFname)
4063 return lp_load_ex(pszFname,
4064 true, /* global only */
4065 false, /* save_defaults */
4066 false, /* add_ipc */
4067 true, /* initialize_globals */
4068 false, /* allow_include_registry */
4069 false); /* load_all_shares*/
4073 * most common lp_load wrapper, loading only the globals
4075 bool lp_load_global(const char *file_name)
4077 return lp_load_ex(file_name,
4078 true, /* global_only */
4079 false, /* save_defaults */
4080 false, /* add_ipc */
4081 true, /* initialize_globals */
4082 true, /* allow_include_registry */
4083 false); /* load_all_shares*/
4087 * lp_load wrapper, especially for clients
4089 bool lp_load_client(const char *file_name)
4091 lp_set_in_client(true);
4093 return lp_load_global(file_name);
4097 * lp_load wrapper, loading only globals, but intended
4098 * for subsequent calls, not reinitializing the globals
4101 bool lp_load_global_no_reinit(const char *file_name)
4103 return lp_load_ex(file_name,
4104 true, /* global_only */
4105 false, /* save_defaults */
4106 false, /* add_ipc */
4107 false, /* initialize_globals */
4108 true, /* allow_include_registry */
4109 false); /* load_all_shares*/
4113 * lp_load wrapper, especially for clients, no reinitialization
4115 bool lp_load_client_no_reinit(const char *file_name)
4117 lp_set_in_client(true);
4119 return lp_load_global_no_reinit(file_name);
4122 bool lp_load_with_registry_shares(const char *pszFname,
4126 bool initialize_globals)
4128 return lp_load_ex(pszFname,
4133 true, /* allow_include_registry */
4134 true); /* load_all_shares*/
4137 /***************************************************************************
4138 Return the max number of services.
4139 ***************************************************************************/
4141 int lp_numservices(void)
4143 return (iNumServices);
4146 /***************************************************************************
4147 Display the contents of the services array in human-readable form.
4148 ***************************************************************************/
4150 void lp_dump(FILE *f, bool show_defaults, int maxtoprint)
4155 defaults_saved = false;
4157 dump_globals(f, defaults_saved);
4159 lpcfg_dump_a_service(&sDefault, &sDefault, f, flags_list, show_defaults);
4161 for (iService = 0; iService < maxtoprint; iService++) {
4163 lp_dump_one(f, show_defaults, iService);
4167 /***************************************************************************
4168 Display the contents of one service in human-readable form.
4169 ***************************************************************************/
4171 void lp_dump_one(FILE * f, bool show_defaults, int snum)
4174 if (ServicePtrs[snum]->szService[0] == '\0')
4176 lpcfg_dump_a_service(ServicePtrs[snum], &sDefault, f,
4177 flags_list, show_defaults);
4181 /***************************************************************************
4182 Return the number of the service with the given name, or -1 if it doesn't
4183 exist. Note that this is a DIFFERENT ANIMAL from the internal function
4184 getservicebyname()! This works ONLY if all services have been loaded, and
4185 does not copy the found service.
4186 ***************************************************************************/
4188 int lp_servicenumber(const char *pszServiceName)
4191 fstring serviceName;
4193 if (!pszServiceName) {
4194 return GLOBAL_SECTION_SNUM;
4197 for (iService = iNumServices - 1; iService >= 0; iService--) {
4198 if (VALID(iService) && ServicePtrs[iService]->szService) {
4200 * The substitution here is used to support %U is
4203 fstrcpy(serviceName, ServicePtrs[iService]->szService);
4204 standard_sub_basic(get_current_username(),
4205 current_user_info.domain,
4206 serviceName,sizeof(serviceName));
4207 if (strequal(serviceName, pszServiceName)) {
4213 if (iService >= 0 && ServicePtrs[iService]->usershare == USERSHARE_VALID) {
4214 struct timespec last_mod;
4216 if (!usershare_exists(iService, &last_mod)) {
4217 /* Remove the share security tdb entry for it. */
4218 delete_share_security(lp_servicename(talloc_tos(), iService));
4219 /* Remove it from the array. */
4220 free_service_byindex(iService);
4221 /* Doesn't exist anymore. */
4222 return GLOBAL_SECTION_SNUM;
4225 /* Has it been modified ? If so delete and reload. */
4226 if (timespec_compare(&ServicePtrs[iService]->usershare_last_mod,
4228 /* Remove it from the array. */
4229 free_service_byindex(iService);
4230 /* and now reload it. */
4231 iService = load_usershare_service(pszServiceName);
4236 DEBUG(7,("lp_servicenumber: couldn't find %s\n", pszServiceName));
4237 return GLOBAL_SECTION_SNUM;
4243 /*******************************************************************
4244 A useful volume label function.
4245 ********************************************************************/
4247 const char *volume_label(TALLOC_CTX *ctx, int snum)
4250 const char *label = lp_volume(ctx, snum);
4252 label = lp_servicename(ctx, snum);
4255 /* This returns a 33 byte guarenteed null terminated string. */
4256 ret = talloc_strndup(ctx, label, 32);
4263 /*******************************************************************
4264 Get the default server type we will announce as via nmbd.
4265 ********************************************************************/
4267 int lp_default_server_announce(void)
4269 int default_server_announce = 0;
4270 default_server_announce |= SV_TYPE_WORKSTATION;
4271 default_server_announce |= SV_TYPE_SERVER;
4272 default_server_announce |= SV_TYPE_SERVER_UNIX;
4274 /* note that the flag should be set only if we have a
4275 printer service but nmbd doesn't actually load the
4276 services so we can't tell --jerry */
4278 default_server_announce |= SV_TYPE_PRINTQ_SERVER;
4280 default_server_announce |= SV_TYPE_SERVER_NT;
4281 default_server_announce |= SV_TYPE_NT;
4283 switch (lp_server_role()) {
4284 case ROLE_DOMAIN_MEMBER:
4285 default_server_announce |= SV_TYPE_DOMAIN_MEMBER;
4287 case ROLE_DOMAIN_PDC:
4288 default_server_announce |= SV_TYPE_DOMAIN_CTRL;
4290 case ROLE_DOMAIN_BDC:
4291 default_server_announce |= SV_TYPE_DOMAIN_BAKCTRL;
4293 case ROLE_STANDALONE:
4297 if (lp_time_server())
4298 default_server_announce |= SV_TYPE_TIME_SOURCE;
4300 if (lp_host_msdfs())
4301 default_server_announce |= SV_TYPE_DFS_SERVER;
4303 return default_server_announce;
4306 /***********************************************************
4307 If we are PDC then prefer us as DMB
4308 ************************************************************/
4310 bool lp_domain_master(void)
4312 if (Globals._domain_master == Auto)
4313 return (lp_server_role() == ROLE_DOMAIN_PDC);
4315 return (bool)Globals._domain_master;
4318 /***********************************************************
4319 If we are PDC then prefer us as DMB
4320 ************************************************************/
4322 static bool lp_domain_master_true_or_auto(void)
4324 if (Globals._domain_master) /* auto or yes */
4330 /***********************************************************
4331 If we are DMB then prefer us as LMB
4332 ************************************************************/
4334 bool lp_preferred_master(void)
4336 if (Globals.iPreferredMaster == Auto)
4337 return (lp_local_master() && lp_domain_master());
4339 return (bool)Globals.iPreferredMaster;
4342 /*******************************************************************
4344 ********************************************************************/
4346 void lp_remove_service(int snum)
4348 ServicePtrs[snum]->valid = false;
4351 const char *lp_printername(TALLOC_CTX *ctx, int snum)
4353 const char *ret = lp__printername(ctx, snum);
4354 if (ret == NULL || *ret == '\0') {
4355 ret = lp_const_servicename(snum);
4362 /***********************************************************
4363 Allow daemons such as winbindd to fix their logfile name.
4364 ************************************************************/
4366 void lp_set_logfile(const char *name)
4368 string_set(Globals.ctx, &Globals.logfile, name);
4369 debug_set_logfile(name);
4372 /*******************************************************************
4373 Return the max print jobs per queue.
4374 ********************************************************************/
4376 int lp_maxprintjobs(int snum)
4378 int maxjobs = LP_SNUM_OK(snum) ? ServicePtrs[snum]->iMaxPrintJobs : sDefault.iMaxPrintJobs;
4379 if (maxjobs <= 0 || maxjobs >= PRINT_MAX_JOBID)
4380 maxjobs = PRINT_MAX_JOBID - 1;
4385 const char *lp_printcapname(void)
4387 if ((Globals.szPrintcapname != NULL) &&
4388 (Globals.szPrintcapname[0] != '\0'))
4389 return Globals.szPrintcapname;
4391 if (sDefault.printing == PRINT_CUPS) {
4395 if (sDefault.printing == PRINT_BSD)
4396 return "/etc/printcap";
4398 return PRINTCAP_NAME;
4401 static uint32 spoolss_state;
4403 bool lp_disable_spoolss( void )
4405 if ( spoolss_state == SVCCTL_STATE_UNKNOWN )
4406 spoolss_state = lp__disable_spoolss() ? SVCCTL_STOPPED : SVCCTL_RUNNING;
4408 return spoolss_state == SVCCTL_STOPPED ? true : false;
4411 void lp_set_spoolss_state( uint32 state )
4413 SMB_ASSERT( (state == SVCCTL_STOPPED) || (state == SVCCTL_RUNNING) );
4415 spoolss_state = state;
4418 uint32 lp_get_spoolss_state( void )
4420 return lp_disable_spoolss() ? SVCCTL_STOPPED : SVCCTL_RUNNING;
4423 /*******************************************************************
4424 Ensure we don't use sendfile if server smb signing is active.
4425 ********************************************************************/
4427 bool lp_use_sendfile(int snum, struct smb_signing_state *signing_state)
4429 bool sign_active = false;
4431 /* Using sendfile blows the brains out of any DOS or Win9x TCP stack... JRA. */
4432 if (get_Protocol() < PROTOCOL_NT1) {
4435 if (signing_state) {
4436 sign_active = smb_signing_is_active(signing_state);
4438 return (lp__use_sendfile(snum) &&
4439 (get_remote_arch() != RA_WIN95) &&
4443 /*******************************************************************
4444 Turn off sendfile if we find the underlying OS doesn't support it.
4445 ********************************************************************/
4447 void set_use_sendfile(int snum, bool val)
4449 if (LP_SNUM_OK(snum))
4450 ServicePtrs[snum]->_use_sendfile = val;
4452 sDefault._use_sendfile = val;
4455 /*******************************************************************
4456 Turn off storing DOS attributes if this share doesn't support it.
4457 ********************************************************************/
4459 void set_store_dos_attributes(int snum, bool val)
4461 if (!LP_SNUM_OK(snum))
4463 ServicePtrs[(snum)]->store_dos_attributes = val;
4466 void lp_set_mangling_method(const char *new_method)
4468 string_set(Globals.ctx, &Globals.mangling_method, new_method);
4471 /*******************************************************************
4472 Global state for POSIX pathname processing.
4473 ********************************************************************/
4475 static bool posix_pathnames;
4477 bool lp_posix_pathnames(void)
4479 return posix_pathnames;
4482 /*******************************************************************
4483 Change everything needed to ensure POSIX pathname processing (currently
4485 ********************************************************************/
4487 void lp_set_posix_pathnames(void)
4489 posix_pathnames = true;
4492 /*******************************************************************
4493 Global state for POSIX lock processing - CIFS unix extensions.
4494 ********************************************************************/
4496 bool posix_default_lock_was_set;
4497 static enum brl_flavour posix_cifsx_locktype; /* By default 0 == WINDOWS_LOCK */
4499 enum brl_flavour lp_posix_cifsu_locktype(files_struct *fsp)
4501 if (posix_default_lock_was_set) {
4502 return posix_cifsx_locktype;
4504 return fsp->posix_open ? POSIX_LOCK : WINDOWS_LOCK;
4508 /*******************************************************************
4509 ********************************************************************/
4511 void lp_set_posix_default_cifsx_readwrite_locktype(enum brl_flavour val)
4513 posix_default_lock_was_set = true;
4514 posix_cifsx_locktype = val;
4517 int lp_min_receive_file_size(void)
4519 if (Globals.iminreceivefile < 0) {
4522 return Globals.iminreceivefile;
4525 /*******************************************************************
4526 Safe wide links checks.
4527 This helper function always verify the validity of wide links,
4528 even after a configuration file reload.
4529 ********************************************************************/
4531 static bool lp_widelinks_internal(int snum)
4533 return (bool)(LP_SNUM_OK(snum)? ServicePtrs[(snum)]->bWidelinks :
4534 sDefault.bWidelinks);
4537 void widelinks_warning(int snum)
4539 if (lp_allow_insecure_wide_links()) {
4543 if (lp_unix_extensions() && lp_widelinks_internal(snum)) {
4544 DEBUG(0,("Share '%s' has wide links and unix extensions enabled. "
4545 "These parameters are incompatible. "
4546 "Wide links will be disabled for this share.\n",
4547 lp_servicename(talloc_tos(), snum) ));
4551 bool lp_widelinks(int snum)
4553 /* wide links is always incompatible with unix extensions */
4554 if (lp_unix_extensions()) {
4556 * Unless we have "allow insecure widelinks"
4559 if (!lp_allow_insecure_wide_links()) {
4564 return lp_widelinks_internal(snum);
4567 int lp_server_role(void)
4569 return lp_find_server_role(lp__server_role(),
4571 lp__domain_logons(),
4572 lp_domain_master_true_or_auto());
4575 int lp_security(void)
4577 return lp_find_security(lp__server_role(),
4581 struct loadparm_global * get_globals(void)
4586 unsigned int * get_flags(void)
4588 if (flags_list == NULL) {
4589 flags_list = talloc_zero_array(NULL, unsigned int, num_parameters());