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) James Myers 2003 <myersjj@samba.org>
14 This program is free software; you can redistribute it and/or modify
15 it under the terms of the GNU General Public License as published by
16 the Free Software Foundation; either version 2 of the License, or
17 (at your option) any later version.
19 This program is distributed in the hope that it will be useful,
20 but WITHOUT ANY WARRANTY; without even the implied warranty of
21 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22 GNU General Public License for more details.
24 You should have received a copy of the GNU General Public License
25 along with this program; if not, write to the Free Software
26 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
32 * This module provides suitable callback functions for the params
33 * module. It builds the internal table of service details which is
34 * then used by the rest of the server.
38 * 1) add it to the global or service structure definition
39 * 2) add it to the parm_table
40 * 3) add it to the list of available functions (eg: using FN_GLOBAL_STRING())
41 * 4) If it's a global then initialise it in init_globals. If a local
42 * (ie. service) parameter then initialise it in the sDefault structure
46 * The configuration file is processed sequentially for speed. It is NOT
47 * accessed randomly as happens in 'real' Windows. For this reason, there
48 * is a fair bit of sequence-dependent code here - ie., code which assumes
49 * that certain things happen before others. In particular, the code which
50 * happens at the boundary between sections is delicately poised, so be
57 #include "dynconfig.h"
58 #include "system/time.h"
59 #include "system/iconv.h"
60 #include "system/network.h"
61 #include "system/printing.h"
62 #include "librpc/gen_ndr/ndr_svcctl.h"
63 #include "librpc/gen_ndr/ndr_samr.h"
64 #include "librpc/gen_ndr/ndr_nbt.h"
65 #include "dlinklist.h"
66 #include "param/loadparm.h"
68 static BOOL bLoaded = False;
71 #define GLOBAL_NAME "global"
75 #define PRINTERS_NAME "printers"
79 #define HOMES_NAME "homes"
82 /* some helpful bits */
83 #define LP_SNUM_OK(i) (((i) >= 0) && ((i) < iNumServices) && ServicePtrs[(i)]->valid)
84 #define VALID(i) ServicePtrs[i]->valid
86 static BOOL do_parameter(const char *, const char *);
87 static BOOL do_parameter_var(const char *pszParmName, const char *fmt, ...);
89 static BOOL defaults_saved = False;
93 struct param_opt *prev, *next;
100 * This structure describes global (ie., server-wide) parameters.
108 char *display_charset;
109 char *szPrintcapname;
114 char *szDefaultService;
116 char *szServerString;
117 char *szAutoServices;
118 char *szPasswdProgram;
122 char *szSMBPasswdFile;
128 char **szPreloadModules;
129 char **szPasswordServers;
130 char *szSocketOptions;
137 char **szWINSservers;
139 char *szRemoteAnnounce;
140 char *szRemoteBrowseSync;
141 char *szSocketAddress;
142 char *szAnnounceVersion; /* This is initialised in init_globals */
145 char **szNetbiosAliases;
146 char *szNetbiosScope;
147 char *szDomainOtherSIDs;
148 char **szNameResolveOrder;
150 char *szAddUserScript;
151 char *szAddMachineScript;
153 char *szWINSPartners;
154 char **dcerpc_ep_servers;
155 char **server_services;
156 char *ntptr_providor;
159 char *szNonUnixAccountRange;
160 char *szTemplateHomedir;
161 char *szTemplateShell;
162 char *szWinbindSeparator;
163 BOOL bWinbindEnumUsers;
164 BOOL bWinbindEnumGroups;
165 BOOL bWinbindUseDefaultDomain;
166 char *szIDMapBackend;
167 char *szGuestaccount;
168 char *swat_directory;
182 BOOL paranoid_server_security;
184 BOOL bDisableSpoolss;
186 int enhanced_browsing;
193 int announce_as; /* This is initialised in init_globals */
194 int machine_password_timeout;
195 int winbind_cache_time;
203 char *socket_options;
208 BOOL bPreferredMaster;
211 BOOL bEncryptPasswords;
213 BOOL bObeyPamRestrictions;
215 BOOL bLargeReadwrite;
219 BOOL bBindInterfacesOnly;
220 BOOL bPamPasswordChange;
222 BOOL bNTStatusSupport;
223 BOOL bAllowTrustedDomains;
230 BOOL bClientPlaintextAuth;
231 BOOL bClientLanManAuth;
232 BOOL bClientNTLMv2Auth;
234 BOOL bHideLocalUsers;
237 BOOL bHostnameLookups;
238 BOOL bUnixExtensions;
239 BOOL bDisableNetbios;
241 int restrict_anonymous;
242 int name_cache_timeout;
243 struct param_opt *param_opt;
247 static global Globals;
250 * This structure describes a single service.
259 char **szInvalidUsers;
264 char *szPrintcommand;
267 char *szLppausecommand;
268 char *szLpresumecommand;
269 char *szQueuepausecommand;
270 char *szQueueresumecommand;
278 char **ntvfs_handler;
304 struct param_opt *param_opt;
306 char dummy[3]; /* for alignment */
311 /* This is a default service used to prime a services structure */
312 static service sDefault = {
314 False, /* not autoloaded */
315 NULL, /* szService */
317 NULL, /* szUsername */
318 NULL, /* szInvalidUsers */
319 NULL, /* szValidUsers */
320 NULL, /* szAdminUsers */
322 NULL, /* szInclude */
323 NULL, /* szPrintcommand */
324 NULL, /* szLpqcommand */
325 NULL, /* szLprmcommand */
326 NULL, /* szLppausecommand */
327 NULL, /* szLpresumecommand */
328 NULL, /* szQueuepausecommand */
329 NULL, /* szQueueresumecommand */
330 NULL, /* szPrintername */
331 NULL, /* szHostsallow */
332 NULL, /* szHostsdeny */
336 NULL, /* szMSDfsProxy */
337 NULL, /* ntvfs_handler */
338 0, /* iMinPrintSpace */
339 1000, /* iMaxPrintJobs */
340 0, /* iMaxConnections */
341 DEFAULT_PRINTING, /* iPrinting */
343 True, /* bAvailable */
344 True, /* bBrowseable */
345 True, /* bRead_only */
346 False, /* bPrint_ok */
347 False, /* bMap_system */
348 False, /* bMap_hidden */
349 True, /* bMap_archive */
351 True, /* bStrictLocking */
352 True, /* bPosixLocking */
354 True, /* bLevel2OpLocks */
355 False, /* bOnlyUser */
356 False, /* bGuest_only */
357 False, /* bGuest_ok */
359 False, /* bMSDfsRoot */
360 True, /* bShareModes */
361 False, /* bStrictSync */
362 False, /* bCIFileSystem */
363 NULL, /* Parametric options */
368 /* local variables */
369 static service **ServicePtrs = NULL;
370 static int iNumServices = 0;
371 static int iServiceIndex = 0;
372 static BOOL bInGlobalSection = True;
373 static int server_role;
374 static int default_server_announce;
376 #define NUMPARAMETERS (sizeof(parm_table) / sizeof(struct parm_struct))
378 /* prototypes for the special type handlers */
379 static BOOL handle_include(const char *pszParmValue, char **ptr);
380 static BOOL handle_copy(const char *pszParmValue, char **ptr);
381 static BOOL handle_winbind_uid(const char *pszParmValue, char **ptr);
382 static BOOL handle_winbind_gid(const char *pszParmValue, char **ptr);
383 static BOOL handle_non_unix_account_range(const char *pszParmValue, char **ptr);
385 static void set_server_role(void);
386 static void set_default_server_announce_type(void);
388 static const struct enum_list enum_protocol[] = {
389 {PROTOCOL_NT1, "NT1"},
390 {PROTOCOL_LANMAN2, "LANMAN2"},
391 {PROTOCOL_LANMAN1, "LANMAN1"},
392 {PROTOCOL_CORE, "CORE"},
393 {PROTOCOL_COREPLUS, "COREPLUS"},
394 {PROTOCOL_COREPLUS, "CORE+"},
398 static const struct enum_list enum_security[] = {
399 {SEC_SHARE, "SHARE"},
401 {SEC_SERVER, "SERVER"},
402 {SEC_DOMAIN, "DOMAIN"},
409 static const struct enum_list enum_printing[] = {
410 {PRINT_SYSV, "sysv"},
412 {PRINT_HPUX, "hpux"},
416 {PRINT_LPRNG, "lprng"},
417 {PRINT_SOFTQ, "softq"},
418 {PRINT_CUPS, "cups"},
420 {PRINT_LPROS2, "os2"},
422 {PRINT_TEST, "test"},
424 #endif /* DEVELOPER */
428 /* Types of machine we can announce as. */
429 #define ANNOUNCE_AS_NT_SERVER 1
430 #define ANNOUNCE_AS_WIN95 2
431 #define ANNOUNCE_AS_WFW 3
432 #define ANNOUNCE_AS_NT_WORKSTATION 4
434 static const struct enum_list enum_announce_as[] = {
435 {ANNOUNCE_AS_NT_SERVER, "NT"},
436 {ANNOUNCE_AS_NT_SERVER, "NT Server"},
437 {ANNOUNCE_AS_NT_WORKSTATION, "NT Workstation"},
438 {ANNOUNCE_AS_WIN95, "win95"},
439 {ANNOUNCE_AS_WFW, "WfW"},
443 static const struct enum_list enum_bool_auto[] = {
454 /* Client-side offline caching policy types */
455 #define CSC_POLICY_MANUAL 0
456 #define CSC_POLICY_DOCUMENTS 1
457 #define CSC_POLICY_PROGRAMS 2
458 #define CSC_POLICY_DISABLE 3
460 static const struct enum_list enum_csc_policy[] = {
461 {CSC_POLICY_MANUAL, "manual"},
462 {CSC_POLICY_DOCUMENTS, "documents"},
463 {CSC_POLICY_PROGRAMS, "programs"},
464 {CSC_POLICY_DISABLE, "disable"},
468 /* SMB signing types. */
469 static const struct enum_list enum_smb_signing_vals[] = {
470 {SMB_SIGNING_OFF, "No"},
471 {SMB_SIGNING_OFF, "False"},
472 {SMB_SIGNING_OFF, "0"},
473 {SMB_SIGNING_OFF, "Off"},
474 {SMB_SIGNING_OFF, "disabled"},
475 {SMB_SIGNING_SUPPORTED, "Yes"},
476 {SMB_SIGNING_SUPPORTED, "True"},
477 {SMB_SIGNING_SUPPORTED, "1"},
478 {SMB_SIGNING_SUPPORTED, "On"},
479 {SMB_SIGNING_SUPPORTED, "enabled"},
480 {SMB_SIGNING_REQUIRED, "required"},
481 {SMB_SIGNING_REQUIRED, "mandatory"},
482 {SMB_SIGNING_REQUIRED, "force"},
483 {SMB_SIGNING_REQUIRED, "forced"},
484 {SMB_SIGNING_REQUIRED, "enforced"},
485 {SMB_SIGNING_AUTO, "auto"},
490 /* Note: We do not initialise the defaults union - it is not allowed in ANSI C
492 * Note: We have a flag called FLAG_DEVELOPER but is not used at this time, it
493 * is implied in current control logic. This may change at some later time. A
494 * flag value of 0 means - show as development option only.
496 * The FLAG_HIDE is explicit. Paramters set this way do NOT appear in any edit
497 * screen in SWAT. This is used to exclude parameters as well as to squash all
498 * parameters that have been duplicated by pseudonyms.
500 static struct parm_struct parm_table[] = {
501 {"Base Options", P_SEP, P_SEPARATOR},
503 {"dos charset", P_STRING, P_GLOBAL, &Globals.dos_charset, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
504 {"unix charset", P_STRING, P_GLOBAL, &Globals.unix_charset, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
505 {"ncalrpc dir", P_STRING, P_GLOBAL, &Globals.ncalrpc_dir, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
506 {"display charset", P_STRING, P_GLOBAL, &Globals.display_charset, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
507 {"comment", P_STRING, P_LOCAL, &sDefault.comment, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_SHARE | FLAG_PRINT | FLAG_DEVELOPER},
508 {"path", P_STRING, P_LOCAL, &sDefault.szPath, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_SHARE | FLAG_PRINT | FLAG_DEVELOPER},
509 {"directory", P_STRING, P_LOCAL, &sDefault.szPath, NULL, NULL, FLAG_HIDE},
510 {"workgroup", P_USTRING, P_GLOBAL, &Globals.szWorkgroup, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
511 {"realm", P_STRING, P_GLOBAL, &Globals.szRealm, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
512 {"ADS server", P_STRING, P_GLOBAL, &Globals.szADSserver, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
513 {"netbios name", P_USTRING, P_GLOBAL, &Globals.szNetbiosName, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
514 {"netbios aliases", P_LIST, P_GLOBAL, &Globals.szNetbiosAliases, NULL, NULL, FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
515 {"netbios scope", P_USTRING, P_GLOBAL, &Globals.szNetbiosScope, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
516 {"server string", P_STRING, P_GLOBAL, &Globals.szServerString, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_DEVELOPER},
517 {"interfaces", P_LIST, P_GLOBAL, &Globals.szInterfaces, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
518 {"bind interfaces only", P_BOOL, P_GLOBAL, &Globals.bBindInterfacesOnly, NULL, NULL, FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
519 {"ntvfs handler", P_LIST, P_LOCAL, &sDefault.ntvfs_handler, NULL, NULL, FLAG_ADVANCED},
520 {"ntptr providor", P_STRING, P_GLOBAL, &Globals.ntptr_providor, NULL, NULL, FLAG_ADVANCED},
521 {"dcerpc endpoint servers", P_LIST, P_GLOBAL, &Globals.dcerpc_ep_servers, NULL, NULL, FLAG_ADVANCED},
522 {"server services", P_LIST, P_GLOBAL, &Globals.server_services, NULL, NULL, FLAG_ADVANCED},
524 {"Security Options", P_SEP, P_SEPARATOR},
526 {"security", P_ENUM, P_GLOBAL, &Globals.security, NULL, enum_security, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
527 {"auth methods", P_LIST, P_GLOBAL, &Globals.AuthMethods, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
528 {"encrypt passwords", P_BOOL, P_GLOBAL, &Globals.bEncryptPasswords, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
529 {"allow trusted domains", P_BOOL, P_GLOBAL, &Globals.bAllowTrustedDomains, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
530 {"hosts equiv", P_STRING, P_GLOBAL, &Globals.szHostsEquiv, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
531 {"idmap backend", P_STRING, P_GLOBAL, &Globals.szIDMapBackend, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
532 {"null passwords", P_BOOL, P_GLOBAL, &Globals.bNullPasswords, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
533 {"obey pam restrictions", P_BOOL, P_GLOBAL, &Globals.bObeyPamRestrictions, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
534 {"password server", P_LIST, P_GLOBAL, &Globals.szPasswordServers, NULL, NULL, FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
535 {"smb passwd file", P_STRING, P_GLOBAL, &Globals.szSMBPasswdFile, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
536 {"sam database", P_STRING, P_GLOBAL, &Globals.szSAM_URL, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
537 {"spoolss database", P_STRING, P_GLOBAL, &Globals.szSPOOLSS_URL, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
538 {"wins database", P_STRING, P_GLOBAL, &Globals.szWINS_URL, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
539 {"private dir", P_STRING, P_GLOBAL, &Globals.szPrivateDir, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
540 {"non unix account range", P_STRING, P_GLOBAL, &Globals.szNonUnixAccountRange, handle_non_unix_account_range, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
541 {"root directory", P_STRING, P_GLOBAL, &Globals.szRootdir, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
542 {"root dir", P_STRING, P_GLOBAL, &Globals.szRootdir, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
543 {"root", P_STRING, P_GLOBAL, &Globals.szRootdir, NULL, NULL, FLAG_HIDE | FLAG_DEVELOPER},
544 {"guest account", P_STRING, P_GLOBAL, &Globals.szGuestaccount, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_DEVELOPER},
546 {"pam password change", P_BOOL, P_GLOBAL, &Globals.bPamPasswordChange, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
547 {"passwd program", P_STRING, P_GLOBAL, &Globals.szPasswdProgram, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
548 {"passwd chat", P_STRING, P_GLOBAL, &Globals.szPasswdChat, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
549 {"password level", P_INTEGER, P_GLOBAL, &Globals.pwordlevel, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
550 {"username level", P_INTEGER, P_GLOBAL, &Globals.unamelevel, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
551 {"restrict anonymous", P_INTEGER, P_GLOBAL, &Globals.restrict_anonymous, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
552 {"plaintext auth", P_BOOL, P_GLOBAL, &Globals.bPlaintextAuth, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
553 {"lanman auth", P_BOOL, P_GLOBAL, &Globals.bLanmanAuth, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
554 {"ntlm auth", P_BOOL, P_GLOBAL, &Globals.bNTLMAuth, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
555 {"client NTLMv2 auth", P_BOOL, P_GLOBAL, &Globals.bClientNTLMv2Auth, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
556 {"client lanman auth", P_BOOL, P_GLOBAL, &Globals.bClientLanManAuth, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
557 {"client plaintext auth", P_BOOL, P_GLOBAL, &Globals.bClientPlaintextAuth, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
559 {"username", P_STRING, P_LOCAL, &sDefault.szUsername, NULL, NULL, FLAG_GLOBAL | FLAG_SHARE},
560 {"user", P_STRING, P_LOCAL, &sDefault.szUsername, NULL, NULL, FLAG_HIDE},
561 {"users", P_STRING, P_LOCAL, &sDefault.szUsername, NULL, NULL, FLAG_HIDE},
563 {"invalid users", P_LIST, P_LOCAL, &sDefault.szInvalidUsers, NULL, NULL, FLAG_GLOBAL | FLAG_SHARE},
564 {"valid users", P_LIST, P_LOCAL, &sDefault.szValidUsers, NULL, NULL, FLAG_GLOBAL | FLAG_SHARE},
565 {"admin users", P_LIST, P_LOCAL, &sDefault.szAdminUsers, NULL, NULL, FLAG_GLOBAL | FLAG_SHARE},
567 {"read only", P_BOOL, P_LOCAL, &sDefault.bRead_only, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_SHARE},
569 {"guest only", P_BOOL, P_LOCAL, &sDefault.bGuest_only, NULL, NULL, FLAG_SHARE},
571 {"guest ok", P_BOOL, P_LOCAL, &sDefault.bGuest_ok, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_SHARE | FLAG_PRINT | FLAG_DEVELOPER},
573 {"only user", P_BOOL, P_LOCAL, &sDefault.bOnlyUser, NULL, NULL, FLAG_SHARE},
574 {"hosts allow", P_LIST, P_LOCAL, &sDefault.szHostsallow, NULL, NULL, FLAG_GLOBAL | FLAG_BASIC | FLAG_ADVANCED | FLAG_SHARE | FLAG_PRINT | FLAG_DEVELOPER},
575 {"hosts deny", P_LIST, P_LOCAL, &sDefault.szHostsdeny, NULL, NULL, FLAG_GLOBAL | FLAG_BASIC | FLAG_ADVANCED | FLAG_SHARE | FLAG_PRINT | FLAG_DEVELOPER},
576 {"preload modules", P_LIST, P_GLOBAL, &Globals.szPreloadModules, NULL, NULL, FLAG_BASIC | FLAG_GLOBAL},
578 {"Logging Options", P_SEP, P_SEPARATOR},
580 {"log level", P_INTEGER, P_GLOBAL, &DEBUGLEVEL, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
581 {"debuglevel", P_INTEGER, P_GLOBAL, &DEBUGLEVEL, NULL, NULL, FLAG_HIDE},
582 {"log file", P_STRING, P_GLOBAL, &Globals.szLogFile, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
584 {"Protocol Options", P_SEP, P_SEPARATOR},
586 {"smb ports", P_LIST, P_GLOBAL, &Globals.smb_ports, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
587 {"nbt port", P_INTEGER, P_GLOBAL, &Globals.nbt_port, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
588 {"dgram port", P_INTEGER, P_GLOBAL, &Globals.dgram_port, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
589 {"cldap port", P_INTEGER, P_GLOBAL, &Globals.cldap_port, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
590 {"krb5 port", P_INTEGER, P_GLOBAL, &Globals.krb5_port, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
591 {"web port", P_INTEGER, P_GLOBAL, &Globals.web_port, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
592 {"tls enabled", P_BOOL, P_GLOBAL, &Globals.tls_enabled, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
593 {"tls keyfile", P_STRING, P_GLOBAL, &Globals.tls_keyfile, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
594 {"tls certfile", P_STRING, P_GLOBAL, &Globals.tls_certfile, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
595 {"tls cafile", P_STRING, P_GLOBAL, &Globals.tls_cafile, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
596 {"tls crlfile", P_STRING, P_GLOBAL, &Globals.tls_crlfile, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
597 {"swat directory", P_STRING, P_GLOBAL, &Globals.swat_directory, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
598 {"large readwrite", P_BOOL, P_GLOBAL, &Globals.bLargeReadwrite, NULL, NULL, FLAG_DEVELOPER},
599 {"max protocol", P_ENUM, P_GLOBAL, &Globals.maxprotocol, NULL, enum_protocol, FLAG_DEVELOPER},
600 {"min protocol", P_ENUM, P_GLOBAL, &Globals.minprotocol, NULL, enum_protocol, FLAG_DEVELOPER},
601 {"unicode", P_BOOL, P_GLOBAL, &Globals.bUnicode, NULL, NULL, FLAG_DEVELOPER},
602 {"read raw", P_BOOL, P_GLOBAL, &Globals.bReadRaw, NULL, NULL, FLAG_DEVELOPER},
603 {"write raw", P_BOOL, P_GLOBAL, &Globals.bWriteRaw, NULL, NULL, FLAG_DEVELOPER},
604 {"disable netbios", P_BOOL, P_GLOBAL, &Globals.bDisableNetbios, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
606 {"nt status support", P_BOOL, P_GLOBAL, &Globals.bNTStatusSupport, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
608 {"announce version", P_STRING, P_GLOBAL, &Globals.szAnnounceVersion, NULL, NULL, FLAG_DEVELOPER},
609 {"announce as", P_ENUM, P_GLOBAL, &Globals.announce_as, NULL, enum_announce_as, FLAG_DEVELOPER},
610 {"max mux", P_INTEGER, P_GLOBAL, &Globals.max_mux, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
611 {"max xmit", P_INTEGER, P_GLOBAL, &Globals.max_xmit, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
613 {"name resolve order", P_LIST, P_GLOBAL, &Globals.szNameResolveOrder, NULL, NULL, FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
614 {"max ttl", P_INTEGER, P_GLOBAL, &Globals.max_ttl, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
615 {"max wins ttl", P_INTEGER, P_GLOBAL, &Globals.max_wins_ttl, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
616 {"min wins ttl", P_INTEGER, P_GLOBAL, &Globals.min_wins_ttl, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
617 {"time server", P_BOOL, P_GLOBAL, &Globals.bTimeServer, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
618 {"unix extensions", P_BOOL, P_GLOBAL, &Globals.bUnixExtensions, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
619 {"use spnego", P_BOOL, P_GLOBAL, &Globals.bUseSpnego, NULL, NULL, FLAG_DEVELOPER},
620 {"server signing", P_ENUM, P_GLOBAL, &Globals.server_signing, NULL, enum_smb_signing_vals, FLAG_ADVANCED},
621 {"client signing", P_ENUM, P_GLOBAL, &Globals.client_signing, NULL, enum_smb_signing_vals, FLAG_ADVANCED},
622 {"rpc big endian", P_BOOL, P_GLOBAL, &Globals.bRpcBigEndian, NULL, NULL, FLAG_DEVELOPER},
624 {"Tuning Options", P_SEP, P_SEPARATOR},
626 {"lpq cache time", P_INTEGER, P_GLOBAL, &Globals.lpqcachetime, NULL, NULL, FLAG_DEVELOPER},
627 {"max connections", P_INTEGER, P_LOCAL, &sDefault.iMaxConnections, NULL, NULL, FLAG_SHARE},
628 {"paranoid server security", P_BOOL, P_GLOBAL, &Globals.paranoid_server_security, NULL, NULL, FLAG_DEVELOPER},
629 {"min print space", P_INTEGER, P_LOCAL, &sDefault.iMinPrintSpace, NULL, NULL, FLAG_PRINT},
631 {"socket options", P_STRING, P_GLOBAL, &Globals.socket_options, NULL, NULL, FLAG_DEVELOPER},
632 {"use mmap", P_BOOL, P_GLOBAL, &Globals.bUseMmap, NULL, NULL, FLAG_DEVELOPER},
633 {"hostname lookups", P_BOOL, P_GLOBAL, &Globals.bHostnameLookups, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
635 {"name cache timeout", P_INTEGER, P_GLOBAL, &Globals.name_cache_timeout, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
636 {"strict sync", P_BOOL, P_LOCAL, &sDefault.bStrictSync, NULL, NULL, FLAG_ADVANCED | FLAG_SHARE},
637 {"case insensitive filesystem", P_BOOL, P_LOCAL, &sDefault.bCIFileSystem, NULL, NULL, FLAG_ADVANCED | FLAG_SHARE},
639 {"Printing Options", P_SEP, P_SEPARATOR},
641 {"max print jobs", P_INTEGER, P_LOCAL, &sDefault.iMaxPrintJobs, NULL, NULL, FLAG_PRINT},
642 {"load printers", P_BOOL, P_GLOBAL, &Globals.bLoadPrinters, NULL, NULL, FLAG_PRINT},
643 {"printcap name", P_STRING, P_GLOBAL, &Globals.szPrintcapname, NULL, NULL, FLAG_PRINT | FLAG_DEVELOPER},
644 {"printcap", P_STRING, P_GLOBAL, &Globals.szPrintcapname, NULL, NULL, FLAG_HIDE},
645 {"printable", P_BOOL, P_LOCAL, &sDefault.bPrint_ok, NULL, NULL, FLAG_PRINT},
646 {"print ok", P_BOOL, P_LOCAL, &sDefault.bPrint_ok, NULL, NULL, FLAG_HIDE},
647 {"printing", P_ENUM, P_LOCAL, &sDefault.iPrinting, NULL, enum_printing, FLAG_PRINT | FLAG_GLOBAL},
648 {"print command", P_STRING, P_LOCAL, &sDefault.szPrintcommand, NULL, NULL, FLAG_PRINT | FLAG_GLOBAL},
649 {"disable spoolss", P_BOOL, P_GLOBAL, &Globals.bDisableSpoolss, NULL, NULL, FLAG_PRINT | FLAG_GLOBAL},
650 {"lpq command", P_STRING, P_LOCAL, &sDefault.szLpqcommand, NULL, NULL, FLAG_PRINT | FLAG_GLOBAL},
651 {"lprm command", P_STRING, P_LOCAL, &sDefault.szLprmcommand, NULL, NULL, FLAG_PRINT | FLAG_GLOBAL},
652 {"lppause command", P_STRING, P_LOCAL, &sDefault.szLppausecommand, NULL, NULL, FLAG_PRINT | FLAG_GLOBAL},
653 {"lpresume command", P_STRING, P_LOCAL, &sDefault.szLpresumecommand, NULL, NULL, FLAG_PRINT | FLAG_GLOBAL},
654 {"queuepause command", P_STRING, P_LOCAL, &sDefault.szQueuepausecommand, NULL, NULL, FLAG_PRINT | FLAG_GLOBAL},
655 {"queueresume command", P_STRING, P_LOCAL, &sDefault.szQueueresumecommand, NULL, NULL, FLAG_PRINT | FLAG_GLOBAL},
657 {"printer name", P_STRING, P_LOCAL, &sDefault.szPrintername, NULL, NULL, FLAG_PRINT},
658 {"printer", P_STRING, P_LOCAL, &sDefault.szPrintername, NULL, NULL, FLAG_HIDE},
660 {"Filename Handling", P_SEP, P_SEPARATOR},
662 {"map system", P_BOOL, P_LOCAL, &sDefault.bMap_system, NULL, NULL, FLAG_SHARE | FLAG_GLOBAL},
663 {"map hidden", P_BOOL, P_LOCAL, &sDefault.bMap_hidden, NULL, NULL, FLAG_SHARE | FLAG_GLOBAL},
664 {"map archive", P_BOOL, P_LOCAL, &sDefault.bMap_archive, NULL, NULL, FLAG_SHARE | FLAG_GLOBAL},
666 {"Domain Options", P_SEP, P_SEPARATOR},
668 {"machine password timeout", P_INTEGER, P_GLOBAL, &Globals.machine_password_timeout, NULL, NULL, FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
670 {"Logon Options", P_SEP, P_SEPARATOR},
672 {"add user script", P_STRING, P_GLOBAL, &Globals.szAddUserScript, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
673 {"add machine script", P_STRING, P_GLOBAL, &Globals.szAddMachineScript, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
675 {"logon script", P_STRING, P_GLOBAL, &Globals.szLogonScript, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
676 {"logon path", P_STRING, P_GLOBAL, &Globals.szLogonPath, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
677 {"logon drive", P_STRING, P_GLOBAL, &Globals.szLogonDrive, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
678 {"logon home", P_STRING, P_GLOBAL, &Globals.szLogonHome, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
679 {"domain logons", P_BOOL, P_GLOBAL, &Globals.bDomainLogons, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
681 {"Browse Options", P_SEP, P_SEPARATOR},
683 {"os level", P_INTEGER, P_GLOBAL, &Globals.os_level, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_DEVELOPER},
684 {"lm announce", P_ENUM, P_GLOBAL, &Globals.lm_announce, NULL, enum_bool_auto, FLAG_ADVANCED | FLAG_DEVELOPER},
685 {"lm interval", P_INTEGER, P_GLOBAL, &Globals.lm_interval, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
686 {"preferred master", P_ENUM, P_GLOBAL, &Globals.bPreferredMaster, NULL, enum_bool_auto, FLAG_BASIC | FLAG_ADVANCED | FLAG_DEVELOPER},
687 {"prefered master", P_ENUM, P_GLOBAL, &Globals.bPreferredMaster, NULL, enum_bool_auto, FLAG_HIDE},
688 {"local master", P_BOOL, P_GLOBAL, &Globals.bLocalMaster, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_DEVELOPER},
689 {"domain master", P_ENUM, P_GLOBAL, &Globals.bDomainMaster, NULL, enum_bool_auto, FLAG_BASIC | FLAG_ADVANCED | FLAG_DEVELOPER},
690 {"browseable", P_BOOL, P_LOCAL, &sDefault.bBrowseable, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_SHARE | FLAG_PRINT | FLAG_DEVELOPER},
691 {"browsable", P_BOOL, P_LOCAL, &sDefault.bBrowseable, NULL, NULL, FLAG_HIDE},
692 {"enhanced browsing", P_BOOL, P_GLOBAL, &Globals.enhanced_browsing, NULL, NULL, FLAG_DEVELOPER | FLAG_ADVANCED},
694 {"WINS Options", P_SEP, P_SEPARATOR},
695 {"dns proxy", P_BOOL, P_GLOBAL, &Globals.bDNSproxy, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
696 {"wins proxy", P_BOOL, P_GLOBAL, &Globals.bWINSproxy, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
698 {"wins server", P_LIST, P_GLOBAL, &Globals.szWINSservers, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
699 {"wins support", P_BOOL, P_GLOBAL, &Globals.bWINSsupport, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
700 {"wins hook", P_STRING, P_GLOBAL, &Globals.szWINSHook, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
701 {"wins partners", P_STRING, P_GLOBAL, &Globals.szWINSPartners, NULL, NULL, FLAG_ADVANCED | FLAG_WIZARD | FLAG_DEVELOPER},
703 {"Locking Options", P_SEP, P_SEPARATOR},
705 {"csc policy", P_ENUM, P_LOCAL, &sDefault.iCSCPolicy, NULL, enum_csc_policy, FLAG_SHARE | FLAG_GLOBAL},
706 {"locking", P_BOOL, P_LOCAL, &sDefault.bLocking, NULL, NULL, FLAG_SHARE | FLAG_GLOBAL},
707 {"lock spin count", P_INTEGER, P_GLOBAL, &Globals.iLockSpinCount, NULL, NULL, FLAG_GLOBAL},
708 {"lock spin time", P_INTEGER, P_GLOBAL, &Globals.iLockSpinTime, NULL, NULL, FLAG_GLOBAL},
710 {"oplocks", P_BOOL, P_LOCAL, &sDefault.bOpLocks, NULL, NULL, FLAG_SHARE | FLAG_GLOBAL},
711 {"level2 oplocks", P_BOOL, P_LOCAL, &sDefault.bLevel2OpLocks, NULL, NULL, FLAG_SHARE | FLAG_GLOBAL},
712 {"posix locking", P_BOOL, P_LOCAL, &sDefault.bPosixLocking, NULL, NULL, FLAG_SHARE | FLAG_GLOBAL},
713 {"strict locking", P_BOOL, P_LOCAL, &sDefault.bStrictLocking, NULL, NULL, FLAG_SHARE | FLAG_GLOBAL},
714 {"share modes", P_BOOL, P_LOCAL, &sDefault.bShareModes, NULL, NULL, FLAG_SHARE|FLAG_GLOBAL},
716 {"Miscellaneous Options", P_SEP, P_SEPARATOR},
718 {"config file", P_STRING, P_GLOBAL, &Globals.szConfigFile, NULL, NULL, FLAG_HIDE},
719 {"preload", P_STRING, P_GLOBAL, &Globals.szAutoServices, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
720 {"auto services", P_STRING, P_GLOBAL, &Globals.szAutoServices, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
721 {"lock dir", P_STRING, P_GLOBAL, &Globals.szLockDir, NULL, NULL, FLAG_HIDE},
722 {"lock directory", P_STRING, P_GLOBAL, &Globals.szLockDir, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
723 {"pid directory", P_STRING, P_GLOBAL, &Globals.szPidDir, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
724 {"js include", P_LIST, P_GLOBAL, &Globals.jsInclude, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
725 {"setup directory", P_STRING, P_GLOBAL, &Globals.szSetupDir, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
727 {"default service", P_STRING, P_GLOBAL, &Globals.szDefaultService, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
728 {"default", P_STRING, P_GLOBAL, &Globals.szDefaultService, NULL, NULL, FLAG_DEVELOPER},
729 {"remote announce", P_STRING, P_GLOBAL, &Globals.szRemoteAnnounce, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
730 {"remote browse sync", P_STRING, P_GLOBAL, &Globals.szRemoteBrowseSync, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
731 {"socket address", P_STRING, P_GLOBAL, &Globals.szSocketAddress, NULL, NULL, FLAG_DEVELOPER},
732 {"time offset", P_INTEGER, P_GLOBAL, &Globals.time_offset, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
733 {"-valid", P_BOOL, P_LOCAL, &sDefault.valid, NULL, NULL, FLAG_HIDE},
735 {"copy", P_STRING, P_LOCAL, &sDefault.szCopy, handle_copy, NULL, FLAG_HIDE},
736 {"include", P_STRING, P_LOCAL, &sDefault.szInclude, handle_include, NULL, FLAG_HIDE},
738 {"available", P_BOOL, P_LOCAL, &sDefault.bAvailable, NULL, NULL, FLAG_BASIC | FLAG_ADVANCED | FLAG_SHARE | FLAG_PRINT},
739 {"volume", P_STRING, P_LOCAL, &sDefault.volume, NULL, NULL, FLAG_SHARE },
740 {"fstype", P_STRING, P_LOCAL, &sDefault.fstype, NULL, NULL, FLAG_SHARE},
742 {"panic action", P_STRING, P_GLOBAL, &Globals.szPanicAction, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
743 {"hide local users", P_BOOL, P_GLOBAL, &Globals.bHideLocalUsers, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
745 {"msdfs root", P_BOOL, P_LOCAL, &sDefault.bMSDfsRoot, NULL, NULL, FLAG_SHARE},
746 {"msdfs proxy", P_STRING, P_LOCAL, &sDefault.szMSDfsProxy, NULL, NULL, FLAG_SHARE},
747 {"host msdfs", P_BOOL, P_GLOBAL, &Globals.bHostMSDfs, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
749 {"Winbind options", P_SEP, P_SEPARATOR},
751 {"winbind uid", P_STRING, P_GLOBAL, &Globals.szWinbindUID, handle_winbind_uid, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
752 {"winbind gid", P_STRING, P_GLOBAL, &Globals.szWinbindGID, handle_winbind_gid, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
753 {"template homedir", P_STRING, P_GLOBAL, &Globals.szTemplateHomedir, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
754 {"template shell", P_STRING, P_GLOBAL, &Globals.szTemplateShell, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
755 {"winbind separator", P_STRING, P_GLOBAL, &Globals.szWinbindSeparator, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
756 {"winbind cache time", P_INTEGER, P_GLOBAL, &Globals.winbind_cache_time, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
757 {"winbind enum users", P_BOOL, P_GLOBAL, &Globals.bWinbindEnumUsers, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
758 {"winbind enum groups", P_BOOL, P_GLOBAL, &Globals.bWinbindEnumGroups, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
759 {"winbind use default domain", P_BOOL, P_GLOBAL, &Globals.bWinbindUseDefaultDomain, NULL, NULL, FLAG_ADVANCED | FLAG_DEVELOPER},
761 {NULL, P_BOOL, P_NONE, NULL, NULL, NULL, 0}
766 return the parameter table
768 struct parm_struct *lp_parm_table(void)
774 /***************************************************************************
775 Initialise the sDefault parameter structure for the printer values.
776 ***************************************************************************/
778 static void init_printer_values(void)
780 /* choose defaults depending on the type of printing */
781 switch (sDefault.iPrinting) {
786 do_parameter("Lpqcommand", "lpq -P'%p'");
787 do_parameter("Lprmcommand", "lprm -P'%p' %j");
788 do_parameter("Printcommand",
794 do_parameter("Lpqcommand", "lpq -P'%p'");
795 do_parameter("Lprmcommand", "lprm -P'%p' %j");
796 do_parameter("Printcommand",
798 do_parameter("Queuepausecommand",
800 do_parameter("Queueresumecommand",
802 do_parameter("Lppausecommand",
804 do_parameter("Lpresumecommand",
805 "lpc release '%p' %j");
810 do_parameter("Lpqcommand", "");
811 do_parameter("Lprmcommand", "");
812 do_parameter("Printcommand", "");
813 do_parameter("Lppausecommand", "");
814 do_parameter("Lpresumecommand", "");
815 do_parameter("Queuepausecommand", "");
816 do_parameter("Queueresumecommand", "");
818 do_parameter("Printcapname", "cups");
820 do_parameter("Lpqcommand",
821 "/usr/bin/lpstat -o '%p'");
822 do_parameter("Lprmcommand",
823 "/usr/bin/cancel '%p-%j'");
824 do_parameter("Printcommand",
825 "/usr/bin/lp -d '%p' %s; rm %s");
826 do_parameter("Lppausecommand",
827 "lp -i '%p-%j' -H hold");
828 do_parameter("Lpresumecommand",
829 "lp -i '%p-%j' -H resume");
830 do_parameter("Queuepausecommand",
831 "/usr/bin/disable '%p'");
832 do_parameter("Queueresumecommand",
833 "/usr/bin/enable '%p'");
834 do_parameter("Printcapname", "lpstat");
835 #endif /* HAVE_CUPS */
840 do_parameter("Lpqcommand", "lpstat -o%p");
841 do_parameter("Lprmcommand", "cancel %p-%j");
842 do_parameter("Printcommand",
843 "lp -c -d%p %s; rm %s");
844 do_parameter("Queuepausecommand",
846 do_parameter("Queueresumecommand",
849 do_parameter("Lppausecommand",
850 "lp -i %p-%j -H hold");
851 do_parameter("Lpresumecommand",
852 "lp -i %p-%j -H resume");
857 do_parameter("Lpqcommand", "lpq -P%p");
858 do_parameter("Lprmcommand", "lprm -P%p %j");
859 do_parameter("Printcommand", "lp -r -P%p %s");
863 do_parameter("Lpqcommand", "qstat -l -d%p");
864 do_parameter("Lprmcommand",
866 do_parameter("Printcommand",
867 "lp -d%p -s %s; rm %s");
868 do_parameter("Lppausecommand",
870 do_parameter("Lpresumecommand",
876 do_parameter("Printcommand", "vlp print %p %s");
877 do_parameter("Lpqcommand", "vlp lpq %p");
878 do_parameter("Lprmcommand", "vlp lprm %p %j");
879 do_parameter("Lppausecommand", "vlp lppause %p %j");
880 do_parameter("Lpresumecommand", "vlp lpresum %p %j");
881 do_parameter("Queuepausecommand", "vlp queuepause %p");
882 do_parameter("Queueresumecommand", "vlp queueresume %p");
884 #endif /* DEVELOPER */
890 /***************************************************************************
891 Initialise the global parameter structure.
892 ***************************************************************************/
893 static void init_globals(void)
898 DEBUG(3, ("Initialising global parameters\n"));
900 for (i = 0; parm_table[i].label; i++) {
901 if ((parm_table[i].type == P_STRING ||
902 parm_table[i].type == P_USTRING) &&
904 !(parm_table[i].flags & FLAG_CMDLINE)) {
905 string_set(parm_table[i].ptr, "");
909 do_parameter("config file", dyn_CONFIGFILE);
911 /* options that can be set on the command line must be initialised via
912 the slower do_parameter() to ensure that FLAG_CMDLINE is obeyed */
914 do_parameter("socket options", "TCP_NODELAY");
916 do_parameter("workgroup", DEFAULT_WORKGROUP);
917 myname = get_myname();
918 do_parameter("netbios name", myname);
920 do_parameter("max protocol", "NT1");
921 do_parameter("name resolve order", "lmhosts wins host bcast");
923 init_printer_values();
925 do_parameter("fstype", FSTYPE_STRING);
926 do_parameter("ntvfs handler", "unixuid default");
927 do_parameter("max connections", "-1");
929 do_parameter("dcerpc endpoint servers", "epmapper srvsvc wkssvc rpcecho samr netlogon lsarpc spoolss drsuapi winreg dssetup");
930 do_parameter("server services", "smb rpc nbt ldap cldap web kdc");
931 do_parameter("ntptr providor", "simple_ldb");
932 do_parameter("auth methods", "anonymous sam_ignoredomain");
933 do_parameter("smb passwd file", dyn_SMB_PASSWD_FILE);
934 do_parameter("private dir", dyn_PRIVATE_DIR);
935 do_parameter("sam database", "sam.ldb");
936 do_parameter("spoolss database", "spoolss.ldb");
937 do_parameter("wins database", "wins.ldb");
938 do_parameter("registry:HKEY_LOCAL_MACHINE", "hklm.ldb");
940 /* This hive should be dynamically generated by Samba using
941 data from the sam, but for the moment leave it in a tdb to
942 keep regedt32 from popping up an annoying dialog. */
943 do_parameter("registry:HKEY_USERS", "hku.ldb");
945 do_parameter("guest account", GUEST_ACCOUNT);
947 /* using UTF8 by default allows us to support all chars */
948 do_parameter("unix charset", "UTF8");
950 /* Use codepage 850 as a default for the dos character set */
951 do_parameter("dos charset", "CP850");
954 * Allow the default PASSWD_CHAT to be overridden in local.h.
956 do_parameter("passwd chat", DEFAULT_PASSWD_CHAT);
958 do_parameter("passwd program", "");
959 do_parameter("printcap name", PRINTCAP_NAME);
961 do_parameter("pid directory", dyn_PIDDIR);
962 do_parameter("lock dir", dyn_LOCKDIR);
963 do_parameter("ncalrpc dir", dyn_NCALRPCDIR);
965 do_parameter("socket address", "0.0.0.0");
966 do_parameter_var("server string", "Samba %s", SAMBA_VERSION_STRING);
968 do_parameter_var("announce version", "%d.%d",
969 DEFAULT_MAJOR_VERSION,
970 DEFAULT_MINOR_VERSION);
972 do_parameter("logon drive", "");
974 do_parameter("logon home", "\\\\%N\\%U");
975 do_parameter("logon path", "\\\\%N\\%U\\profile");
976 do_parameter("password server", "*");
978 do_parameter("load printers", "True");
980 do_parameter("max mux", "50");
981 do_parameter("max xmit", "12288");
982 do_parameter("lpqcachetime", "10");
983 do_parameter("DisableSpoolss", "False");
984 do_parameter("password level", "0");
985 do_parameter("username level", "0");
986 do_parameter("LargeReadwrite", "True");
987 do_parameter("minprotocol", "CORE");
988 do_parameter("security", "USER");
989 do_parameter("paranoid server security", "True");
990 do_parameter("EncryptPasswords", "True");
991 do_parameter("ReadRaw", "True");
992 do_parameter("WriteRaw", "True");
993 do_parameter("NullPasswords", "False");
994 do_parameter("ObeyPamRestrictions", "False");
995 do_parameter("lm announce", "Auto");
996 do_parameter("lm interval", "60");
997 do_parameter("announce as", "NT SERVER");
999 do_parameter("TimeServer", "False");
1000 do_parameter("BindInterfacesOnly", "False");
1001 do_parameter("PamPasswordChange", "False");
1002 do_parameter("Unicode", "True");
1003 do_parameter("restrict anonymous", "0");
1004 do_parameter("ClientLanManAuth", "True");
1005 do_parameter("LanmanAuth", "True");
1006 do_parameter("NTLMAuth", "True");
1008 do_parameter("enhanced browsing", "True");
1009 do_parameter("LockSpinCount", "3");
1010 do_parameter("LockSpinTime", "10");
1011 #ifdef MMAP_BLACKLIST
1012 do_parameter("UseMmap", "False");
1014 do_parameter("UseMmap", "True");
1016 do_parameter("UnixExtensions", "False");
1018 /* hostname lookups can be very expensive and are broken on
1019 a large number of sites (tridge) */
1020 do_parameter("HostnameLookups", "False");
1022 do_parameter("PreferredMaster", "Auto");
1023 do_parameter("os level", "20");
1024 do_parameter("LocalMaster", "True");
1025 do_parameter("DomainMaster", "Auto"); /* depending on bDomainLogons */
1026 do_parameter("DomainLogons", "False");
1027 do_parameter("WINSsupport", "False");
1028 do_parameter("WINSproxy", "False");
1030 do_parameter("DNSproxy", "True");
1032 do_parameter("AllowTrustedDomains", "True");
1034 do_parameter("TemplateShell", "/bin/false");
1035 do_parameter("TemplateHomedir", "/home/%D/%U");
1036 do_parameter("WinbindSeparator", "\\");
1038 do_parameter("winbind cache time", "15");
1039 do_parameter("WinbindEnumUsers", "True");
1040 do_parameter("WinbindEnumGroups", "True");
1041 do_parameter("WinbindUseDefaultDomain", "False");
1043 do_parameter("IDMapBackend", "tdb");
1045 do_parameter("name cache timeout", "660"); /* In seconds */
1047 do_parameter("client signing", "Yes");
1048 do_parameter("server signing", "auto");
1050 do_parameter("use spnego", "True");
1052 do_parameter("smb ports", SMB_PORTS);
1053 do_parameter("nbt port", "137");
1054 do_parameter("dgram port", "138");
1055 do_parameter("cldap port", "389");
1056 do_parameter("krb5 port", "88");
1057 do_parameter("web port", "901");
1058 do_parameter("swat directory", dyn_SWATDIR);
1060 do_parameter("nt status support", "True");
1062 do_parameter("max wins ttl", "432000");
1063 do_parameter("min wins ttl", "10");
1065 do_parameter("tls enabled", "True");
1066 do_parameter("tls keyfile", "tls/key.pem");
1067 do_parameter("tls certfile", "tls/cert.pem");
1068 do_parameter("tls cafile", "tls/ca.pem");
1069 do_parameter_var("js include", "%s/js", dyn_LIBDIR);
1070 do_parameter_var("setup directory", "%s/setup", dyn_LIBDIR);
1073 static TALLOC_CTX *lp_talloc;
1075 /******************************************************************* a
1076 Free up temporary memory - called from the main loop.
1077 ********************************************************************/
1079 void lp_talloc_free(void)
1083 talloc_free(lp_talloc);
1087 /*******************************************************************
1088 Convenience routine to grab string parameters into temporary memory
1089 and run standard_sub_basic on them. The buffers can be written to by
1090 callers without affecting the source string.
1091 ********************************************************************/
1093 static const char *lp_string(const char *s)
1095 #if 0 /* until REWRITE done to make thread-safe */
1096 size_t len = s ? strlen(s) : 0;
1100 /* The follow debug is useful for tracking down memory problems
1101 especially if you have an inner loop that is calling a lp_*()
1102 function that returns a string. Perhaps this debug should be
1103 present all the time? */
1106 DEBUG(10, ("lp_string(%s)\n", s));
1109 #if 0 /* until REWRITE done to make thread-safe */
1111 lp_talloc = talloc_init("lp_talloc");
1113 ret = talloc_array(lp_talloc, char, len + 100); /* leave room for substitution */
1121 StrnCpy(ret, s, len);
1123 if (trim_string(ret, "\"", "\"")) {
1124 if (strchr(ret,'"') != NULL)
1125 StrnCpy(ret, s, len);
1128 standard_sub_basic(ret,len+100);
1135 In this section all the functions that are used to access the
1136 parameters from the rest of the program are defined
1139 #define FN_GLOBAL_STRING(fn_name,ptr) \
1140 const char *fn_name(void) {return(lp_string(*(char **)(ptr) ? *(char **)(ptr) : ""));}
1141 #define FN_GLOBAL_CONST_STRING(fn_name,ptr) \
1142 const char *fn_name(void) {return(*(const char **)(ptr) ? *(const char **)(ptr) : "");}
1143 #define FN_GLOBAL_LIST(fn_name,ptr) \
1144 const char **fn_name(void) {return(*(const char ***)(ptr));}
1145 #define FN_GLOBAL_BOOL(fn_name,ptr) \
1146 BOOL fn_name(void) {return(*(BOOL *)(ptr));}
1147 #define FN_GLOBAL_CHAR(fn_name,ptr) \
1148 char fn_name(void) {return(*(char *)(ptr));}
1149 #define FN_GLOBAL_INTEGER(fn_name,ptr) \
1150 int fn_name(void) {return(*(int *)(ptr));}
1152 #define FN_LOCAL_STRING(fn_name,val) \
1153 const char *fn_name(int i) {return(lp_string((LP_SNUM_OK(i) && ServicePtrs[(i)]->val) ? ServicePtrs[(i)]->val : sDefault.val));}
1154 #define FN_LOCAL_CONST_STRING(fn_name,val) \
1155 const char *fn_name(int i) {return (const char *)((LP_SNUM_OK(i) && ServicePtrs[(i)]->val) ? ServicePtrs[(i)]->val : sDefault.val);}
1156 #define FN_LOCAL_LIST(fn_name,val) \
1157 const char **fn_name(int i) {return(const char **)(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1158 #define FN_LOCAL_BOOL(fn_name,val) \
1159 BOOL fn_name(int i) {return(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1160 #define FN_LOCAL_CHAR(fn_name,val) \
1161 char fn_name(int i) {return(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1162 #define FN_LOCAL_INTEGER(fn_name,val) \
1163 int fn_name(int i) {return(LP_SNUM_OK(i)? ServicePtrs[(i)]->val : sDefault.val);}
1165 FN_GLOBAL_LIST(lp_smb_ports, &Globals.smb_ports)
1166 FN_GLOBAL_INTEGER(lp_nbt_port, &Globals.nbt_port)
1167 FN_GLOBAL_INTEGER(lp_dgram_port, &Globals.dgram_port)
1168 FN_GLOBAL_INTEGER(lp_cldap_port, &Globals.cldap_port)
1169 FN_GLOBAL_INTEGER(lp_krb5_port, &Globals.krb5_port)
1170 FN_GLOBAL_INTEGER(lp_web_port, &Globals.web_port)
1171 FN_GLOBAL_STRING(lp_dos_charset, &Globals.dos_charset)
1172 FN_GLOBAL_STRING(lp_swat_directory, &Globals.swat_directory)
1173 FN_GLOBAL_BOOL(lp_tls_enabled, &Globals.tls_enabled)
1174 FN_GLOBAL_STRING(lp_tls_keyfile, &Globals.tls_keyfile)
1175 FN_GLOBAL_STRING(lp_tls_certfile, &Globals.tls_certfile)
1176 FN_GLOBAL_STRING(lp_tls_cafile, &Globals.tls_cafile)
1177 FN_GLOBAL_STRING(lp_tls_crlfile, &Globals.tls_crlfile)
1178 FN_GLOBAL_STRING(lp_unix_charset, &Globals.unix_charset)
1179 FN_GLOBAL_STRING(lp_display_charset, &Globals.display_charset)
1180 FN_GLOBAL_STRING(lp_logfile, &Globals.szLogFile)
1181 FN_GLOBAL_STRING(lp_configfile, &Globals.szConfigFile)
1182 FN_GLOBAL_STRING(lp_smb_passwd_file, &Globals.szSMBPasswdFile)
1183 FN_GLOBAL_STRING(lp_sam_url, &Globals.szSAM_URL)
1184 FN_GLOBAL_STRING(lp_spoolss_url, &Globals.szSPOOLSS_URL)
1185 FN_GLOBAL_STRING(lp_wins_url, &Globals.szWINS_URL)
1186 FN_GLOBAL_STRING(lp_private_dir, &Globals.szPrivateDir)
1187 FN_GLOBAL_STRING(lp_serverstring, &Globals.szServerString)
1188 FN_GLOBAL_STRING(lp_printcapname, &Globals.szPrintcapname)
1189 FN_GLOBAL_STRING(lp_lockdir, &Globals.szLockDir)
1190 FN_GLOBAL_STRING(lp_setupdir, &Globals.szSetupDir)
1191 FN_GLOBAL_STRING(lp_ncalrpc_dir, &Globals.ncalrpc_dir)
1192 FN_GLOBAL_STRING(lp_piddir, &Globals.szPidDir)
1193 FN_GLOBAL_LIST(lp_dcerpc_endpoint_servers, &Globals.dcerpc_ep_servers)
1194 FN_GLOBAL_LIST(lp_server_services, &Globals.server_services)
1195 FN_GLOBAL_STRING(lp_ntptr_providor, &Globals.ntptr_providor)
1196 FN_GLOBAL_STRING(lp_rootdir, &Globals.szRootdir)
1197 FN_GLOBAL_STRING(lp_defaultservice, &Globals.szDefaultService)
1198 FN_GLOBAL_STRING(lp_hosts_equiv, &Globals.szHostsEquiv)
1199 FN_GLOBAL_STRING(lp_auto_services, &Globals.szAutoServices)
1200 FN_GLOBAL_STRING(lp_passwd_program, &Globals.szPasswdProgram)
1201 FN_GLOBAL_STRING(lp_passwd_chat, &Globals.szPasswdChat)
1202 FN_GLOBAL_LIST(lp_passwordserver, &Globals.szPasswordServers)
1203 FN_GLOBAL_LIST(lp_name_resolve_order, &Globals.szNameResolveOrder)
1204 FN_GLOBAL_STRING(lp_realm, &Globals.szRealm)
1205 FN_GLOBAL_STRING(lp_ads_server, &Globals.szADSserver)
1206 FN_GLOBAL_STRING(lp_socket_options, &Globals.socket_options)
1207 FN_GLOBAL_STRING(lp_workgroup, &Globals.szWorkgroup)
1208 FN_GLOBAL_STRING(lp_netbios_name, &Globals.szNetbiosName)
1209 FN_GLOBAL_STRING(lp_netbios_scope, &Globals.szNetbiosScope)
1210 FN_GLOBAL_CONST_STRING(lp_logon_script, &Globals.szLogonScript)
1211 FN_GLOBAL_CONST_STRING(lp_logon_path, &Globals.szLogonPath)
1212 FN_GLOBAL_CONST_STRING(lp_logon_drive, &Globals.szLogonDrive)
1213 FN_GLOBAL_CONST_STRING(lp_logon_home, &Globals.szLogonHome)
1214 FN_GLOBAL_STRING(lp_remote_announce, &Globals.szRemoteAnnounce)
1215 FN_GLOBAL_STRING(lp_remote_browse_sync, &Globals.szRemoteBrowseSync)
1216 FN_GLOBAL_LIST(lp_wins_server_list, &Globals.szWINSservers)
1217 FN_GLOBAL_LIST(lp_interfaces, &Globals.szInterfaces)
1218 FN_GLOBAL_STRING(lp_socket_address, &Globals.szSocketAddress)
1219 FN_GLOBAL_LIST(lp_netbios_aliases, &Globals.szNetbiosAliases)
1220 FN_GLOBAL_LIST(lp_preload_modules, &Globals.szPreloadModules)
1221 FN_GLOBAL_STRING(lp_panic_action, &Globals.szPanicAction)
1222 FN_GLOBAL_STRING(lp_adduser_script, &Globals.szAddUserScript)
1224 FN_GLOBAL_CONST_STRING(lp_guestaccount, &Globals.szGuestaccount)
1226 FN_GLOBAL_STRING(lp_addmachine_script, &Globals.szAddMachineScript)
1228 FN_GLOBAL_STRING(lp_wins_hook, &Globals.szWINSHook)
1229 FN_GLOBAL_STRING(lp_wins_partners, &Globals.szWINSPartners)
1230 FN_GLOBAL_STRING(lp_template_homedir, &Globals.szTemplateHomedir)
1231 FN_GLOBAL_STRING(lp_template_shell, &Globals.szTemplateShell)
1232 FN_GLOBAL_CONST_STRING(lp_winbind_separator, &Globals.szWinbindSeparator)
1233 FN_GLOBAL_BOOL(lp_winbind_enum_users, &Globals.bWinbindEnumUsers)
1234 FN_GLOBAL_BOOL(lp_winbind_enum_groups, &Globals.bWinbindEnumGroups)
1235 FN_GLOBAL_BOOL(lp_winbind_use_default_domain, &Globals.bWinbindUseDefaultDomain)
1236 FN_GLOBAL_STRING(lp_idmap_backend, &Globals.szIDMapBackend)
1238 FN_GLOBAL_BOOL(lp_disable_netbios, &Globals.bDisableNetbios)
1239 FN_GLOBAL_BOOL(lp_dns_proxy, &Globals.bDNSproxy)
1240 FN_GLOBAL_BOOL(lp_wins_support, &Globals.bWINSsupport)
1241 FN_GLOBAL_BOOL(lp_we_are_a_wins_server, &Globals.bWINSsupport)
1242 FN_GLOBAL_BOOL(lp_wins_proxy, &Globals.bWINSproxy)
1243 FN_GLOBAL_BOOL(lp_local_master, &Globals.bLocalMaster)
1244 FN_GLOBAL_BOOL(lp_domain_logons, &Globals.bDomainLogons)
1245 FN_GLOBAL_BOOL(lp_load_printers, &Globals.bLoadPrinters)
1246 FN_GLOBAL_BOOL(lp_readraw, &Globals.bReadRaw)
1247 FN_GLOBAL_BOOL(lp_large_readwrite, &Globals.bLargeReadwrite)
1248 FN_GLOBAL_BOOL(lp_writeraw, &Globals.bWriteRaw)
1249 FN_GLOBAL_BOOL(lp_null_passwords, &Globals.bNullPasswords)
1250 FN_GLOBAL_BOOL(lp_obey_pam_restrictions, &Globals.bObeyPamRestrictions)
1251 FN_GLOBAL_BOOL(lp_encrypted_passwords, &Globals.bEncryptPasswords)
1252 static FN_GLOBAL_BOOL(lp_time_server, &Globals.bTimeServer)
1253 FN_GLOBAL_BOOL(lp_bind_interfaces_only, &Globals.bBindInterfacesOnly)
1254 FN_GLOBAL_BOOL(lp_pam_password_change, &Globals.bPamPasswordChange)
1255 FN_GLOBAL_BOOL(lp_unicode, &Globals.bUnicode)
1256 FN_GLOBAL_BOOL(lp_nt_status_support, &Globals.bNTStatusSupport)
1257 FN_GLOBAL_BOOL(lp_allow_trusted_domains, &Globals.bAllowTrustedDomains)
1258 FN_GLOBAL_INTEGER(lp_restrict_anonymous, &Globals.restrict_anonymous)
1259 FN_GLOBAL_BOOL(lp_plaintext_auth, &Globals.bPlaintextAuth)
1260 FN_GLOBAL_BOOL(lp_lanman_auth, &Globals.bLanmanAuth)
1261 FN_GLOBAL_BOOL(lp_ntlm_auth, &Globals.bNTLMAuth)
1262 FN_GLOBAL_BOOL(lp_client_plaintext_auth, &Globals.bClientPlaintextAuth)
1263 FN_GLOBAL_BOOL(lp_client_lanman_auth, &Globals.bClientLanManAuth)
1264 FN_GLOBAL_BOOL(lp_client_ntlmv2_auth, &Globals.bClientNTLMv2Auth)
1265 FN_GLOBAL_BOOL(lp_host_msdfs, &Globals.bHostMSDfs)
1266 FN_GLOBAL_BOOL(lp_enhanced_browsing, &Globals.enhanced_browsing)
1267 FN_GLOBAL_BOOL(lp_use_mmap, &Globals.bUseMmap)
1268 FN_GLOBAL_BOOL(lp_unix_extensions, &Globals.bUnixExtensions)
1269 FN_GLOBAL_BOOL(lp_use_spnego, &Globals.bUseSpnego)
1270 FN_GLOBAL_BOOL(lp_hostname_lookups, &Globals.bHostnameLookups)
1271 FN_GLOBAL_BOOL(lp_rpc_big_endian, &Globals.bRpcBigEndian)
1272 FN_GLOBAL_INTEGER(lp_os_level, &Globals.os_level)
1273 FN_GLOBAL_INTEGER(lp_max_ttl, &Globals.max_ttl)
1274 FN_GLOBAL_INTEGER(lp_max_wins_ttl, &Globals.max_wins_ttl)
1275 FN_GLOBAL_INTEGER(lp_min_wins_ttl, &Globals.min_wins_ttl)
1276 FN_GLOBAL_INTEGER(lp_time_offset, &Globals.time_offset)
1277 FN_GLOBAL_INTEGER(lp_maxmux, &Globals.max_mux)
1278 FN_GLOBAL_INTEGER(lp_max_xmit, &Globals.max_xmit)
1279 FN_GLOBAL_INTEGER(lp_passwordlevel, &Globals.pwordlevel)
1280 FN_GLOBAL_INTEGER(lp_usernamelevel, &Globals.unamelevel)
1281 FN_GLOBAL_INTEGER(lp_maxprotocol, &Globals.maxprotocol)
1282 FN_GLOBAL_INTEGER(lp_minprotocol, &Globals.minprotocol)
1283 FN_GLOBAL_INTEGER(lp_security, &Globals.security)
1284 FN_GLOBAL_LIST(lp_auth_methods, &Globals.AuthMethods)
1285 FN_GLOBAL_BOOL(lp_paranoid_server_security, &Globals.paranoid_server_security)
1286 FN_GLOBAL_INTEGER(lp_lpqcachetime, &Globals.lpqcachetime)
1287 FN_GLOBAL_INTEGER(lp_disable_spoolss, &Globals.bDisableSpoolss)
1288 static FN_GLOBAL_INTEGER(lp_announce_as, &Globals.announce_as)
1289 FN_GLOBAL_INTEGER(lp_lm_announce, &Globals.lm_announce)
1290 FN_GLOBAL_INTEGER(lp_lm_interval, &Globals.lm_interval)
1291 FN_GLOBAL_INTEGER(lp_machine_password_timeout, &Globals.machine_password_timeout)
1292 FN_GLOBAL_INTEGER(lp_lock_spin_count, &Globals.iLockSpinCount)
1293 FN_GLOBAL_INTEGER(lp_lock_sleep_time, &Globals.iLockSpinTime)
1294 FN_GLOBAL_LIST(lp_js_include, &Globals.jsInclude)
1297 FN_LOCAL_STRING(lp_servicename, szService)
1298 FN_LOCAL_CONST_STRING(lp_const_servicename, szService)
1299 FN_LOCAL_STRING(lp_pathname, szPath)
1300 FN_LOCAL_STRING(lp_username, szUsername)
1301 FN_LOCAL_LIST(lp_invalid_users, szInvalidUsers)
1302 FN_LOCAL_LIST(lp_valid_users, szValidUsers)
1303 FN_LOCAL_LIST(lp_admin_users, szAdminUsers)
1304 FN_LOCAL_STRING(lp_printcommand, szPrintcommand)
1305 FN_LOCAL_STRING(lp_lpqcommand, szLpqcommand)
1306 FN_LOCAL_STRING(lp_lprmcommand, szLprmcommand)
1307 FN_LOCAL_STRING(lp_lppausecommand, szLppausecommand)
1308 FN_LOCAL_STRING(lp_lpresumecommand, szLpresumecommand)
1309 FN_LOCAL_STRING(lp_queuepausecommand, szQueuepausecommand)
1310 FN_LOCAL_STRING(lp_queueresumecommand, szQueueresumecommand)
1311 static FN_LOCAL_STRING(_lp_printername, szPrintername)
1312 FN_LOCAL_LIST(lp_hostsallow, szHostsallow)
1313 FN_LOCAL_LIST(lp_hostsdeny, szHostsdeny)
1314 FN_LOCAL_STRING(lp_comment, comment)
1315 FN_LOCAL_STRING(lp_fstype, fstype)
1316 FN_LOCAL_STRING(lp_msdfs_proxy, szMSDfsProxy)
1317 static FN_LOCAL_STRING(lp_volume, volume)
1318 FN_LOCAL_LIST(lp_ntvfs_handler, ntvfs_handler)
1319 FN_LOCAL_BOOL(lp_msdfs_root, bMSDfsRoot)
1320 FN_LOCAL_BOOL(lp_autoloaded, autoloaded)
1321 FN_LOCAL_BOOL(lp_browseable, bBrowseable)
1322 FN_LOCAL_BOOL(lp_readonly, bRead_only)
1323 FN_LOCAL_BOOL(lp_guest_ok, bGuest_ok)
1324 FN_LOCAL_BOOL(lp_guest_only, bGuest_only)
1325 FN_LOCAL_BOOL(lp_print_ok, bPrint_ok)
1326 FN_LOCAL_BOOL(lp_map_hidden, bMap_hidden)
1327 FN_LOCAL_BOOL(lp_map_archive, bMap_archive)
1328 FN_LOCAL_BOOL(lp_locking, bLocking)
1329 FN_LOCAL_BOOL(lp_strict_locking, bStrictLocking)
1330 FN_LOCAL_BOOL(lp_posix_locking, bPosixLocking)
1331 FN_LOCAL_BOOL(lp_strict_sync, bStrictSync)
1332 FN_LOCAL_BOOL(lp_ci_filesystem, bCIFileSystem)
1333 FN_LOCAL_BOOL(lp_share_modes, bShareModes)
1334 FN_LOCAL_BOOL(lp_oplocks, bOpLocks)
1335 FN_LOCAL_BOOL(lp_level2_oplocks, bLevel2OpLocks)
1336 FN_LOCAL_BOOL(lp_onlyuser, bOnlyUser)
1337 FN_LOCAL_BOOL(lp_map_system, bMap_system)
1338 FN_LOCAL_INTEGER(lp_max_connections, iMaxConnections)
1339 FN_LOCAL_INTEGER(lp_minprintspace, iMinPrintSpace)
1340 FN_LOCAL_INTEGER(lp_printing, iPrinting)
1341 FN_LOCAL_INTEGER(lp_csc_policy, iCSCPolicy)
1342 FN_GLOBAL_INTEGER(lp_winbind_cache_time, &Globals.winbind_cache_time)
1343 FN_GLOBAL_BOOL(lp_hide_local_users, &Globals.bHideLocalUsers)
1344 FN_GLOBAL_INTEGER(lp_name_cache_timeout, &Globals.name_cache_timeout)
1345 FN_GLOBAL_INTEGER(lp_server_signing, &Globals.server_signing)
1346 FN_GLOBAL_INTEGER(lp_client_signing, &Globals.client_signing)
1348 /* local prototypes */
1350 static int map_parameter(const char *pszParmName);
1351 static BOOL set_boolean(BOOL *pb, const char *pszParmValue);
1352 static int getservicebyname(const char *pszServiceName,
1353 service * pserviceDest);
1354 static void copy_service(service * pserviceDest,
1355 service * pserviceSource, BOOL *pcopymapDest);
1356 static BOOL service_ok(int iService);
1357 static BOOL do_section(const char *pszSectionName);
1358 static void init_copymap(service * pservice);
1360 /* This is a helper function for parametrical options support. */
1361 /* It returns a pointer to parametrical option value if it exists or NULL otherwise */
1362 /* Actual parametrical functions are quite simple */
1363 const char *lp_get_parametric(int lookup_service, const char *type, const char *option)
1366 struct param_opt *data;
1368 if (lookup_service >= iNumServices) return NULL;
1370 data = (lookup_service < 0) ?
1371 Globals.param_opt : ServicePtrs[lookup_service]->param_opt;
1373 asprintf(&vfskey, "%s:%s", type, option);
1377 if (strcmp(data->key, vfskey) == 0) {
1384 if (lookup_service >= 0) {
1385 /* Try to fetch the same option but from globals */
1386 /* but only if we are not already working with Globals */
1387 data = Globals.param_opt;
1389 if (strcmp(data->key, vfskey) == 0) {
1403 /*******************************************************************
1404 convenience routine to return int parameters.
1405 ********************************************************************/
1406 static int lp_int(const char *s)
1410 DEBUG(0,("lp_int(%s): is called with NULL!\n",s));
1414 return strtol(s, NULL, 0);
1417 /*******************************************************************
1418 convenience routine to return unsigned long parameters.
1419 ********************************************************************/
1420 static int lp_ulong(const char *s)
1424 DEBUG(0,("lp_int(%s): is called with NULL!\n",s));
1428 return strtoul(s, NULL, 0);
1431 /*******************************************************************
1432 convenience routine to return boolean parameters.
1433 ********************************************************************/
1434 static BOOL lp_bool(const char *s)
1439 DEBUG(0,("lp_bool(%s): is called with NULL!\n",s));
1443 if (!set_boolean(&ret,s)) {
1444 DEBUG(0,("lp_bool(%s): value is not boolean!\n",s));
1452 /* Return parametric option from a given service. Type is a part of option before ':' */
1453 /* Parametric option has following syntax: 'Type: option = value' */
1454 /* Returned value is allocated in 'lp_talloc' context */
1456 const char *lp_parm_string(int lookup_service, const char *type, const char *option)
1458 const char *value = lp_get_parametric(lookup_service, type, option);
1461 return lp_string(value);
1466 /* Return parametric option from a given service. Type is a part of option before ':' */
1467 /* Parametric option has following syntax: 'Type: option = value' */
1468 /* Returned value is allocated in 'lp_talloc' context */
1470 const char **lp_parm_string_list(int lookup_service, const char *type, const char *option,
1471 const char *separator)
1473 const char *value = lp_get_parametric(lookup_service, type, option);
1476 return str_list_make(talloc_autofree_context(), value, separator);
1481 /* Return parametric option from a given service. Type is a part of option before ':' */
1482 /* Parametric option has following syntax: 'Type: option = value' */
1484 int lp_parm_int(int lookup_service, const char *type, const char *option, int default_v)
1486 const char *value = lp_get_parametric(lookup_service, type, option);
1489 return lp_int(value);
1494 /* Return parametric option from a given service. Type is a part of option before ':' */
1495 /* Parametric option has following syntax: 'Type: option = value' */
1497 unsigned long lp_parm_ulong(int lookup_service, const char *type, const char *option, unsigned long default_v)
1499 const char *value = lp_get_parametric(lookup_service, type, option);
1502 return lp_ulong(value);
1507 /* Return parametric option from a given service. Type is a part of option before ':' */
1508 /* Parametric option has following syntax: 'Type: option = value' */
1510 BOOL lp_parm_bool(int lookup_service, const char *type, const char *option, BOOL default_v)
1512 const char *value = lp_get_parametric(lookup_service, type, option);
1515 return lp_bool(value);
1521 /***************************************************************************
1522 Initialise a service to the defaults.
1523 ***************************************************************************/
1525 static void init_service(service * pservice)
1527 memset((char *)pservice, '\0', sizeof(service));
1528 copy_service(pservice, &sDefault, NULL);
1531 /***************************************************************************
1532 Free the dynamically allocated parts of a service struct.
1533 ***************************************************************************/
1535 static void free_service(service *pservice)
1538 struct param_opt *data, *pdata;
1542 if (pservice->szService)
1543 DEBUG(5, ("free_service: Freeing service %s\n",
1544 pservice->szService));
1546 string_free(&pservice->szService);
1547 SAFE_FREE(pservice->copymap);
1549 for (i = 0; parm_table[i].label; i++) {
1550 if ((parm_table[i].type == P_STRING ||
1551 parm_table[i].type == P_USTRING) &&
1552 parm_table[i].class == P_LOCAL) {
1553 string_free((char **)
1554 (((char *)pservice) +
1555 PTR_DIFF(parm_table[i].ptr, &sDefault)));
1556 } else if (parm_table[i].type == P_LIST &&
1557 parm_table[i].class == P_LOCAL) {
1558 char ***listp = (char ***)(((char *)pservice) +
1559 PTR_DIFF(parm_table[i].ptr, &sDefault));
1560 talloc_free(*listp);
1565 DEBUG(5,("Freeing parametrics:\n"));
1566 data = pservice->param_opt;
1568 DEBUG(5,("[%s = %s]\n", data->key, data->value));
1569 string_free(&data->key);
1570 string_free(&data->value);
1576 ZERO_STRUCTP(pservice);
1579 /***************************************************************************
1580 Add a new service to the services array initialising it with the given
1582 ***************************************************************************/
1584 static int add_a_service(const service *pservice, const char *name)
1588 int num_to_alloc = iNumServices + 1;
1589 struct param_opt *data, *pdata;
1591 tservice = *pservice;
1593 /* it might already exist */
1595 i = getservicebyname(name, NULL);
1597 /* Clean all parametric options for service */
1598 /* They will be added during parsing again */
1599 data = ServicePtrs[i]->param_opt;
1601 string_free(&data->key);
1602 string_free(&data->value);
1607 ServicePtrs[i]->param_opt = NULL;
1612 /* find an invalid one */
1613 for (i = 0; i < iNumServices; i++)
1614 if (!ServicePtrs[i]->valid)
1617 /* if not, then create one */
1618 if (i == iNumServices) {
1621 tsp = realloc_p(ServicePtrs, service *, num_to_alloc);
1624 DEBUG(0,("add_a_service: failed to enlarge ServicePtrs!\n"));
1629 ServicePtrs[iNumServices] = malloc_p(service);
1631 if (!ServicePtrs[iNumServices]) {
1632 DEBUG(0,("add_a_service: out of memory!\n"));
1638 free_service(ServicePtrs[i]);
1640 ServicePtrs[i]->valid = True;
1642 init_service(ServicePtrs[i]);
1643 copy_service(ServicePtrs[i], &tservice, NULL);
1645 string_set(&ServicePtrs[i]->szService, name);
1649 /***************************************************************************
1650 Add a new home service, with the specified home directory, defaults coming
1652 ***************************************************************************/
1654 BOOL lp_add_home(const char *pszHomename, int iDefaultService,
1655 const char *user, const char *pszHomedir)
1660 i = add_a_service(ServicePtrs[iDefaultService], pszHomename);
1665 if (!(*(ServicePtrs[iDefaultService]->szPath))
1666 || strequal(ServicePtrs[iDefaultService]->szPath, lp_pathname(-1))) {
1667 pstrcpy(newHomedir, pszHomedir);
1669 pstrcpy(newHomedir, lp_pathname(iDefaultService));
1670 string_sub(newHomedir,"%H", pszHomedir, sizeof(newHomedir));
1673 string_set(&ServicePtrs[i]->szPath, newHomedir);
1675 if (!(*(ServicePtrs[i]->comment))) {
1677 slprintf(comment, sizeof(comment) - 1,
1678 "Home directory of %s", user);
1679 string_set(&ServicePtrs[i]->comment, comment);
1681 ServicePtrs[i]->bAvailable = sDefault.bAvailable;
1682 ServicePtrs[i]->bBrowseable = sDefault.bBrowseable;
1684 DEBUG(3, ("adding home's share [%s] for user '%s' at '%s'\n", pszHomename,
1690 /***************************************************************************
1691 Add a new service, based on an old one.
1692 ***************************************************************************/
1694 int lp_add_service(const char *pszService, int iDefaultService)
1696 return (add_a_service(ServicePtrs[iDefaultService], pszService));
1699 /***************************************************************************
1700 Add the IPC service.
1701 ***************************************************************************/
1703 static BOOL lp_add_hidden(const char *name, const char *fstype, BOOL guest_ok)
1706 int i = add_a_service(&sDefault, name);
1711 slprintf(comment, sizeof(comment) - 1,
1712 "%s Service (%s)", fstype, Globals.szServerString);
1714 string_set(&ServicePtrs[i]->szPath, tmpdir());
1715 string_set(&ServicePtrs[i]->szUsername, "");
1716 string_set(&ServicePtrs[i]->comment, comment);
1717 string_set(&ServicePtrs[i]->fstype, fstype);
1718 ServicePtrs[i]->iMaxConnections = -1;
1719 ServicePtrs[i]->bAvailable = True;
1720 ServicePtrs[i]->bRead_only = True;
1721 ServicePtrs[i]->bGuest_only = False;
1722 ServicePtrs[i]->bGuest_ok = guest_ok;
1723 ServicePtrs[i]->bPrint_ok = False;
1724 ServicePtrs[i]->bBrowseable = False;
1726 if (strcasecmp(fstype, "IPC") == 0) {
1727 lp_do_parameter(i, "ntvfs handler", "default");
1730 DEBUG(3, ("adding hidden service %s\n", name));
1735 /***************************************************************************
1736 Add a new printer service, with defaults coming from service iFrom.
1737 ***************************************************************************/
1739 BOOL lp_add_printer(const char *pszPrintername, int iDefaultService)
1741 const char *comment = "From Printcap";
1742 int i = add_a_service(ServicePtrs[iDefaultService], pszPrintername);
1747 /* note that we do NOT default the availability flag to True - */
1748 /* we take it from the default service passed. This allows all */
1749 /* dynamic printers to be disabled by disabling the [printers] */
1750 /* entry (if/when the 'available' keyword is implemented!). */
1752 /* the printer name is set to the service name. */
1753 string_set(&ServicePtrs[i]->szPrintername, pszPrintername);
1754 string_set(&ServicePtrs[i]->comment, comment);
1755 ServicePtrs[i]->bBrowseable = sDefault.bBrowseable;
1756 /* Printers cannot be read_only. */
1757 ServicePtrs[i]->bRead_only = False;
1758 /* No share modes on printer services. */
1759 ServicePtrs[i]->bShareModes = False;
1760 /* No oplocks on printer services. */
1761 ServicePtrs[i]->bOpLocks = False;
1762 /* Printer services must be printable. */
1763 ServicePtrs[i]->bPrint_ok = True;
1765 DEBUG(3, ("adding printer service %s\n", pszPrintername));
1767 update_server_announce_as_printserver();
1772 /***************************************************************************
1773 Map a parameter's string representation to something we can use.
1774 Returns False if the parameter string is not recognised, else TRUE.
1775 ***************************************************************************/
1777 static int map_parameter(const char *pszParmName)
1781 if (*pszParmName == '-')
1784 for (iIndex = 0; parm_table[iIndex].label; iIndex++)
1785 if (strwicmp(parm_table[iIndex].label, pszParmName) == 0)
1788 /* Warn only if it isn't parametric option */
1789 if (strchr(pszParmName, ':') == NULL)
1790 DEBUG(0, ("Unknown parameter encountered: \"%s\"\n", pszParmName));
1791 /* We do return 'fail' for parametric options as well because they are
1792 stored in different storage
1799 return the parameter structure for a parameter
1801 struct parm_struct *lp_parm_struct(const char *name)
1803 int parmnum = map_parameter(name);
1804 if (parmnum == -1) return NULL;
1805 return &parm_table[parmnum];
1809 return the parameter pointer for a parameter
1811 void *lp_parm_ptr(int snum, struct parm_struct *parm)
1816 return ((char *)ServicePtrs[snum]) + PTR_DIFF(parm->ptr, &sDefault);
1819 /***************************************************************************
1820 Set a boolean variable from the text value stored in the passed string.
1821 Returns True in success, False if the passed string does not correctly
1822 represent a boolean.
1823 ***************************************************************************/
1825 static BOOL set_boolean(BOOL *pb, const char *pszParmValue)
1830 if (strwicmp(pszParmValue, "yes") == 0 ||
1831 strwicmp(pszParmValue, "true") == 0 ||
1832 strwicmp(pszParmValue, "1") == 0)
1834 else if (strwicmp(pszParmValue, "no") == 0 ||
1835 strwicmp(pszParmValue, "False") == 0 ||
1836 strwicmp(pszParmValue, "0") == 0)
1840 ("ERROR: Badly formed boolean in configuration file: \"%s\".\n",
1847 /***************************************************************************
1848 Find a service by name. Otherwise works like get_service.
1849 ***************************************************************************/
1851 static int getservicebyname(const char *pszServiceName, service * pserviceDest)
1855 for (iService = iNumServices - 1; iService >= 0; iService--)
1856 if (VALID(iService) &&
1857 strwicmp(ServicePtrs[iService]->szService, pszServiceName) == 0) {
1858 if (pserviceDest != NULL)
1859 copy_service(pserviceDest, ServicePtrs[iService], NULL);
1866 /***************************************************************************
1867 Copy a service structure to another.
1868 If pcopymapDest is NULL then copy all fields
1869 ***************************************************************************/
1871 static void copy_service(service * pserviceDest, service * pserviceSource, BOOL *pcopymapDest)
1874 BOOL bcopyall = (pcopymapDest == NULL);
1875 struct param_opt *data, *pdata, *paramo;
1878 for (i = 0; parm_table[i].label; i++)
1879 if (parm_table[i].ptr && parm_table[i].class == P_LOCAL &&
1880 (bcopyall || pcopymapDest[i])) {
1881 void *def_ptr = parm_table[i].ptr;
1883 ((char *)pserviceSource) + PTR_DIFF(def_ptr,
1886 ((char *)pserviceDest) + PTR_DIFF(def_ptr,
1889 switch (parm_table[i].type) {
1891 *(BOOL *)dest_ptr = *(BOOL *)src_ptr;
1896 *(int *)dest_ptr = *(int *)src_ptr;
1900 string_set(dest_ptr,
1905 string_set(dest_ptr,
1907 strupper(*(char **)dest_ptr);
1910 *(const char ***)dest_ptr = str_list_copy(talloc_autofree_context(),
1911 *(const char ***)src_ptr);
1919 init_copymap(pserviceDest);
1920 if (pserviceSource->copymap)
1921 memcpy((void *)pserviceDest->copymap,
1922 (void *)pserviceSource->copymap,
1923 sizeof(BOOL) * NUMPARAMETERS);
1926 data = pserviceSource->param_opt;
1929 pdata = pserviceDest->param_opt;
1930 /* Traverse destination */
1932 /* If we already have same option, override it */
1933 if (strcmp(pdata->key, data->key) == 0) {
1934 string_free(&pdata->value);
1935 pdata->value = strdup(data->value);
1939 pdata = pdata->next;
1942 paramo = smb_xmalloc_p(struct param_opt);
1943 paramo->key = strdup(data->key);
1944 paramo->value = strdup(data->value);
1945 DLIST_ADD(pserviceDest->param_opt, paramo);
1951 /***************************************************************************
1952 Check a service for consistency. Return False if the service is in any way
1953 incomplete or faulty, else True.
1954 ***************************************************************************/
1956 static BOOL service_ok(int iService)
1961 if (ServicePtrs[iService]->szService[0] == '\0') {
1962 DEBUG(0, ("The following message indicates an internal error:\n"));
1963 DEBUG(0, ("No service name in service entry.\n"));
1967 /* The [printers] entry MUST be printable. I'm all for flexibility, but */
1968 /* I can't see why you'd want a non-printable printer service... */
1969 if (strwicmp(ServicePtrs[iService]->szService, PRINTERS_NAME) == 0) {
1970 if (!ServicePtrs[iService]->bPrint_ok) {
1971 DEBUG(0, ("WARNING: [%s] service MUST be printable!\n",
1972 ServicePtrs[iService]->szService));
1973 ServicePtrs[iService]->bPrint_ok = True;
1974 update_server_announce_as_printserver();
1976 /* [printers] service must also be non-browsable. */
1977 if (ServicePtrs[iService]->bBrowseable)
1978 ServicePtrs[iService]->bBrowseable = False;
1981 /* If a service is flagged unavailable, log the fact at level 0. */
1982 if (!ServicePtrs[iService]->bAvailable)
1983 DEBUG(1, ("NOTE: Service %s is flagged unavailable.\n",
1984 ServicePtrs[iService]->szService));
1989 static struct file_lists {
1990 struct file_lists *next;
1994 } *file_lists = NULL;
1996 /*******************************************************************
1997 Keep a linked list of all config files so we know when one has changed
1998 it's date and needs to be reloaded.
1999 ********************************************************************/
2001 static void add_to_file_list(const char *fname, const char *subfname)
2003 struct file_lists *f = file_lists;
2006 if (f->name && !strcmp(f->name, fname))
2012 f = malloc_p(struct file_lists);
2015 f->next = file_lists;
2016 f->name = strdup(fname);
2021 f->subfname = strdup(subfname);
2027 f->modtime = file_modtime(subfname);
2029 time_t t = file_modtime(subfname);
2035 /*******************************************************************
2036 Check if a config file has changed date.
2037 ********************************************************************/
2039 BOOL lp_file_list_changed(void)
2041 struct file_lists *f = file_lists;
2042 DEBUG(6, ("lp_file_list_changed()\n"));
2048 pstrcpy(n2, f->name);
2049 standard_sub_basic(n2,sizeof(n2));
2051 DEBUGADD(6, ("file %s -> %s last mod_time: %s\n",
2052 f->name, n2, ctime(&f->modtime)));
2054 mod_time = file_modtime(n2);
2056 if (mod_time && ((f->modtime != mod_time) || (f->subfname == NULL) || (strcmp(n2, f->subfname) != 0))) {
2058 ("file %s modified: %s\n", n2,
2060 f->modtime = mod_time;
2061 SAFE_FREE(f->subfname);
2062 f->subfname = strdup(n2);
2070 /***************************************************************************
2071 Handle the include operation.
2072 ***************************************************************************/
2074 static BOOL handle_include(const char *pszParmValue, char **ptr)
2077 pstrcpy(fname, pszParmValue);
2079 standard_sub_basic(fname,sizeof(fname));
2081 add_to_file_list(pszParmValue, fname);
2083 string_set(ptr, fname);
2085 if (file_exist(fname))
2086 return (pm_process(fname, do_section, do_parameter));
2088 DEBUG(2, ("Can't find include file %s\n", fname));
2093 /***************************************************************************
2094 Handle the interpretation of the copy parameter.
2095 ***************************************************************************/
2097 static BOOL handle_copy(const char *pszParmValue, char **ptr)
2101 service serviceTemp;
2103 string_set(ptr, pszParmValue);
2105 init_service(&serviceTemp);
2109 DEBUG(3, ("Copying service from service %s\n", pszParmValue));
2111 if ((iTemp = getservicebyname(pszParmValue, &serviceTemp)) >= 0) {
2112 if (iTemp == iServiceIndex) {
2113 DEBUG(0, ("Can't copy service %s - unable to copy self!\n", pszParmValue));
2115 copy_service(ServicePtrs[iServiceIndex],
2117 ServicePtrs[iServiceIndex]->copymap);
2121 DEBUG(0, ("Unable to copy service - source not found: %s\n", pszParmValue));
2125 free_service(&serviceTemp);
2129 /***************************************************************************
2130 Handle winbind/non unix account uid and gid allocation parameters. The format of these
2135 winbind uid = 1000-1999
2136 winbind gid = 700-899
2138 We only do simple parsing checks here. The strings are parsed into useful
2139 structures in the winbind daemon code.
2141 ***************************************************************************/
2143 /* Some lp_ routines to return winbind [ug]id information */
2145 static uid_t winbind_uid_low, winbind_uid_high;
2146 static gid_t winbind_gid_low, winbind_gid_high;
2147 static uint32_t non_unix_account_low, non_unix_account_high;
2149 BOOL lp_winbind_uid(uid_t *low, uid_t *high)
2151 if (winbind_uid_low == 0 || winbind_uid_high == 0)
2155 *low = winbind_uid_low;
2158 *high = winbind_uid_high;
2163 BOOL lp_winbind_gid(gid_t *low, gid_t *high)
2165 if (winbind_gid_low == 0 || winbind_gid_high == 0)
2169 *low = winbind_gid_low;
2172 *high = winbind_gid_high;
2177 BOOL lp_non_unix_account_range(uint32_t *low, uint32_t *high)
2179 if (non_unix_account_low == 0 || non_unix_account_high == 0)
2183 *low = non_unix_account_low;
2186 *high = non_unix_account_high;
2191 /* Do some simple checks on "winbind [ug]id" parameter values */
2193 static BOOL handle_winbind_uid(const char *pszParmValue, char **ptr)
2197 if (sscanf(pszParmValue, "%u-%u", &low, &high) != 2 || high < low)
2202 string_set(ptr, pszParmValue);
2204 winbind_uid_low = low;
2205 winbind_uid_high = high;
2210 static BOOL handle_winbind_gid(const char *pszParmValue, char **ptr)
2214 if (sscanf(pszParmValue, "%u-%u", &low, &high) != 2 || high < low)
2219 string_set(ptr, pszParmValue);
2221 winbind_gid_low = low;
2222 winbind_gid_high = high;
2227 /***************************************************************************
2228 Do some simple checks on "non unix account range" parameter values.
2229 ***************************************************************************/
2231 static BOOL handle_non_unix_account_range(const char *pszParmValue, char **ptr)
2235 if (sscanf(pszParmValue, "%u-%u", &low, &high) != 2 || high < low)
2240 string_set(ptr, pszParmValue);
2242 non_unix_account_low = low;
2243 non_unix_account_high = high;
2249 /***************************************************************************
2250 Initialise a copymap.
2251 ***************************************************************************/
2253 static void init_copymap(service * pservice)
2256 SAFE_FREE(pservice->copymap);
2257 pservice->copymap = malloc_array_p(BOOL, NUMPARAMETERS);
2258 if (!pservice->copymap)
2260 ("Couldn't allocate copymap!! (size %d)\n",
2261 (int)NUMPARAMETERS));
2263 for (i = 0; i < NUMPARAMETERS; i++)
2264 pservice->copymap[i] = True;
2267 /***************************************************************************
2268 Return the local pointer to a parameter given the service number and the
2269 pointer into the default structure.
2270 ***************************************************************************/
2272 void *lp_local_ptr(int snum, void *ptr)
2274 return (void *)(((char *)ServicePtrs[snum]) + PTR_DIFF(ptr, &sDefault));
2278 /***************************************************************************
2279 Process a parametric option
2280 ***************************************************************************/
2281 static BOOL lp_do_parameter_parametric(int snum, const char *pszParmName, const char *pszParmValue, int flags)
2283 struct param_opt *paramo, *data;
2286 while (isspace((unsigned char)*pszParmName)) {
2290 name = strdup(pszParmName);
2291 if (!name) return False;
2296 data = Globals.param_opt;
2298 data = ServicePtrs[snum]->param_opt;
2301 /* Traverse destination */
2302 for (paramo=data; paramo; paramo=paramo->next) {
2303 /* If we already have the option set, override it unless
2304 it was a command line option and the new one isn't */
2305 if (strcmp(paramo->key, name) == 0) {
2306 if ((paramo->flags & FLAG_CMDLINE) &&
2307 !(flags & FLAG_CMDLINE)) {
2311 free(paramo->value);
2312 paramo->value = strdup(pszParmValue);
2313 paramo->flags = flags;
2319 paramo = smb_xmalloc_p(struct param_opt);
2320 paramo->key = strdup(name);
2321 paramo->value = strdup(pszParmValue);
2322 paramo->flags = flags;
2324 DLIST_ADD(Globals.param_opt, paramo);
2326 DLIST_ADD(ServicePtrs[snum]->param_opt, paramo);
2334 /***************************************************************************
2335 Process a parameter for a particular service number. If snum < 0
2336 then assume we are in the globals.
2337 ***************************************************************************/
2338 BOOL lp_do_parameter(int snum, const char *pszParmName, const char *pszParmValue)
2341 void *parm_ptr = NULL; /* where we are going to store the result */
2342 void *def_ptr = NULL;
2344 parmnum = map_parameter(pszParmName);
2347 if (strchr(pszParmName, ':')) {
2348 return lp_do_parameter_parametric(snum, pszParmName, pszParmValue, 0);
2350 DEBUG(0, ("Ignoring unknown parameter \"%s\"\n", pszParmName));
2354 if (parm_table[parmnum].flags & FLAG_DEPRECATED) {
2355 DEBUG(1, ("WARNING: The \"%s\" option is deprecated\n",
2359 /* if the flag has been set on the command line, then don't allow override,
2360 but don't report an error */
2361 if (parm_table[parmnum].flags & FLAG_CMDLINE) {
2365 def_ptr = parm_table[parmnum].ptr;
2367 /* we might point at a service, the default service or a global */
2371 if (parm_table[parmnum].class == P_GLOBAL) {
2373 ("Global parameter %s found in service section!\n",
2378 ((char *)ServicePtrs[snum]) + PTR_DIFF(def_ptr,
2383 if (!ServicePtrs[snum]->copymap)
2384 init_copymap(ServicePtrs[snum]);
2386 /* this handles the aliases - set the copymap for other entries with
2387 the same data pointer */
2388 for (i = 0; parm_table[i].label; i++)
2389 if (parm_table[i].ptr == parm_table[parmnum].ptr)
2390 ServicePtrs[snum]->copymap[i] = False;
2393 /* if it is a special case then go ahead */
2394 if (parm_table[parmnum].special) {
2395 parm_table[parmnum].special(pszParmValue, (char **)parm_ptr);
2399 /* now switch on the type of variable it is */
2400 switch (parm_table[parmnum].type)
2403 set_boolean(parm_ptr, pszParmValue);
2407 *(int *)parm_ptr = atoi(pszParmValue);
2411 *(const char ***)parm_ptr = str_list_make(talloc_autofree_context(),
2412 pszParmValue, NULL);
2416 string_set(parm_ptr, pszParmValue);
2420 string_set(parm_ptr, pszParmValue);
2421 strupper(*(char **)parm_ptr);
2425 for (i = 0; parm_table[parmnum].enum_list[i].name; i++) {
2428 parm_table[parmnum].enum_list[i].name)) {
2430 parm_table[parmnum].
2435 if (!parm_table[parmnum].enum_list[i].name) {
2436 DEBUG(0,("Unknown enumerated value '%s' for '%s'\n",
2437 pszParmValue, pszParmName));
2448 /***************************************************************************
2449 Process a parameter.
2450 ***************************************************************************/
2452 static BOOL do_parameter(const char *pszParmName, const char *pszParmValue)
2454 return (lp_do_parameter(bInGlobalSection ? -2 : iServiceIndex,
2455 pszParmName, pszParmValue));
2459 variable argument do parameter
2461 static BOOL do_parameter_var(const char *pszParmName, const char *fmt, ...) PRINTF_ATTRIBUTE(2, 3);
2463 static BOOL do_parameter_var(const char *pszParmName, const char *fmt, ...)
2470 s = talloc_vasprintf(NULL, fmt, ap);
2472 ret = do_parameter(pszParmName, s);
2479 set a parameter from the commandline - this is called from command line parameter
2480 parsing code. It sets the parameter then marks the parameter as unable to be modified
2481 by smb.conf processing
2483 BOOL lp_set_cmdline(const char *pszParmName, const char *pszParmValue)
2485 int parmnum = map_parameter(pszParmName);
2488 while (isspace((unsigned char)*pszParmValue)) pszParmValue++;
2491 if (parmnum < 0 && strchr(pszParmName, ':')) {
2492 /* set a parametric option */
2493 return lp_do_parameter_parametric(-1, pszParmName, pszParmValue, FLAG_CMDLINE);
2497 DEBUG(0,("Unknown option '%s'\n", pszParmName));
2501 /* reset the CMDLINE flag in case this has been called before */
2502 parm_table[parmnum].flags &= ~FLAG_CMDLINE;
2504 if (!lp_do_parameter(-2, pszParmName, pszParmValue)) {
2508 parm_table[parmnum].flags |= FLAG_CMDLINE;
2510 /* we have to also set FLAG_CMDLINE on aliases */
2511 for (i=parmnum-1;i>=0 && parm_table[i].ptr == parm_table[parmnum].ptr;i--) {
2512 parm_table[i].flags |= FLAG_CMDLINE;
2514 for (i=parmnum+1;i<NUMPARAMETERS && parm_table[i].ptr == parm_table[parmnum].ptr;i++) {
2515 parm_table[i].flags |= FLAG_CMDLINE;
2522 set a option from the commandline in 'a=b' format. Use to support --option
2524 BOOL lp_set_option(const char *option)
2542 ret = lp_set_cmdline(s, p+1);
2548 #define BOOLSTR(b) ((b) ? "Yes" : "No")
2550 /***************************************************************************
2551 Print a parameter of the specified type.
2552 ***************************************************************************/
2554 static void print_parameter(struct parm_struct *p, void *ptr, FILE * f)
2560 for (i = 0; p->enum_list[i].name; i++) {
2561 if (*(int *)ptr == p->enum_list[i].value) {
2563 p->enum_list[i].name);
2570 fprintf(f, "%s", BOOLSTR(*(BOOL *)ptr));
2574 fprintf(f, "%d", *(int *)ptr);
2578 if ((char ***)ptr && *(char ***)ptr) {
2579 char **list = *(char ***)ptr;
2581 for (; *list; list++)
2582 fprintf(f, "%s%s", *list,
2583 ((*(list+1))?", ":""));
2589 if (*(char **)ptr) {
2590 fprintf(f, "%s", *(char **)ptr);
2598 /***************************************************************************
2599 Check if two parameters are equal.
2600 ***************************************************************************/
2602 static BOOL equal_parameter(parm_type type, void *ptr1, void *ptr2)
2606 return (*((BOOL *)ptr1) == *((BOOL *)ptr2));
2610 return (*((int *)ptr1) == *((int *)ptr2));
2613 return str_list_equal((const char **)(*(char ***)ptr1),
2614 (const char **)(*(char ***)ptr2));
2619 char *p1 = *(char **)ptr1, *p2 = *(char **)ptr2;
2624 return (p1 == p2 || strequal(p1, p2));
2632 /***************************************************************************
2633 Process a new section (service). At this stage all sections are services.
2634 Later we'll have special sections that permit server parameters to be set.
2635 Returns True on success, False on failure.
2636 ***************************************************************************/
2638 static BOOL do_section(const char *pszSectionName)
2641 BOOL isglobal = ((strwicmp(pszSectionName, GLOBAL_NAME) == 0) ||
2642 (strwicmp(pszSectionName, GLOBAL_NAME2) == 0));
2645 /* if we've just struck a global section, note the fact. */
2646 bInGlobalSection = isglobal;
2648 /* check for multiple global sections */
2649 if (bInGlobalSection) {
2650 DEBUG(3, ("Processing section \"[%s]\"\n", pszSectionName));
2654 /* if we have a current service, tidy it up before moving on */
2657 if (iServiceIndex >= 0)
2658 bRetval = service_ok(iServiceIndex);
2660 /* if all is still well, move to the next record in the services array */
2662 /* We put this here to avoid an odd message order if messages are */
2663 /* issued by the post-processing of a previous section. */
2664 DEBUG(2, ("Processing section \"[%s]\"\n", pszSectionName));
2666 if ((iServiceIndex = add_a_service(&sDefault, pszSectionName))
2668 DEBUG(0, ("Failed to add a new service\n"));
2677 /***************************************************************************
2678 Determine if a partcular base parameter is currentl set to the default value.
2679 ***************************************************************************/
2681 static BOOL is_default(int i)
2683 if (!defaults_saved)
2685 switch (parm_table[i].type) {
2687 return str_list_equal((const char **)parm_table[i].def.lvalue,
2688 (const char **)(*(char ***)parm_table[i].ptr));
2691 return strequal(parm_table[i].def.svalue,
2692 *(char **)parm_table[i].ptr);
2694 return parm_table[i].def.bvalue ==
2695 *(BOOL *)parm_table[i].ptr;
2698 return parm_table[i].def.ivalue ==
2699 *(int *)parm_table[i].ptr;
2706 /***************************************************************************
2707 Display the contents of the global structure.
2708 ***************************************************************************/
2710 static void dump_globals(FILE *f)
2713 struct param_opt *data;
2715 fprintf(f, "# Global parameters\n[global]\n");
2717 for (i = 0; parm_table[i].label; i++)
2718 if (parm_table[i].class == P_GLOBAL &&
2719 parm_table[i].ptr &&
2720 (i == 0 || (parm_table[i].ptr != parm_table[i - 1].ptr))) {
2721 if (defaults_saved && is_default(i))
2723 fprintf(f, "\t%s = ", parm_table[i].label);
2724 print_parameter(&parm_table[i], parm_table[i].ptr, f);
2727 if (Globals.param_opt != NULL) {
2728 data = Globals.param_opt;
2730 fprintf(f, "\t%s = %s\n", data->key, data->value);
2737 /***************************************************************************
2738 Display the contents of a single services record.
2739 ***************************************************************************/
2741 static void dump_a_service(service * pService, FILE * f)
2744 struct param_opt *data;
2746 if (pService != &sDefault)
2747 fprintf(f, "\n[%s]\n", pService->szService);
2749 for (i = 0; parm_table[i].label; i++)
2750 if (parm_table[i].class == P_LOCAL &&
2751 parm_table[i].ptr &&
2752 (*parm_table[i].label != '-') &&
2753 (i == 0 || (parm_table[i].ptr != parm_table[i - 1].ptr))) {
2754 int pdiff = PTR_DIFF(parm_table[i].ptr, &sDefault);
2756 if (pService == &sDefault) {
2757 if (defaults_saved && is_default(i))
2760 if (equal_parameter(parm_table[i].type,
2761 ((char *)pService) +
2763 ((char *)&sDefault) +
2768 fprintf(f, "\t%s = ", parm_table[i].label);
2769 print_parameter(&parm_table[i],
2770 ((char *)pService) + pdiff, f);
2773 if (pService->param_opt != NULL) {
2774 data = pService->param_opt;
2776 fprintf(f, "\t%s = %s\n", data->key, data->value);
2783 /***************************************************************************
2784 Return info about the next service in a service. snum==-1 gives the globals.
2785 Return NULL when out of parameters.
2786 ***************************************************************************/
2788 struct parm_struct *lp_next_parameter(int snum, int *i, int allparameters)
2791 /* do the globals */
2792 for (; parm_table[*i].label; (*i)++) {
2793 if (parm_table[*i].class == P_SEPARATOR)
2794 return &parm_table[(*i)++];
2796 if (!parm_table[*i].ptr
2797 || (*parm_table[*i].label == '-'))
2801 && (parm_table[*i].ptr ==
2802 parm_table[(*i) - 1].ptr))
2805 return &parm_table[(*i)++];
2808 service *pService = ServicePtrs[snum];
2810 for (; parm_table[*i].label; (*i)++) {
2811 if (parm_table[*i].class == P_SEPARATOR)
2812 return &parm_table[(*i)++];
2814 if (parm_table[*i].class == P_LOCAL &&
2815 parm_table[*i].ptr &&
2816 (*parm_table[*i].label != '-') &&
2818 (parm_table[*i].ptr !=
2819 parm_table[(*i) - 1].ptr)))
2822 PTR_DIFF(parm_table[*i].ptr,
2825 if (allparameters ||
2826 !equal_parameter(parm_table[*i].type,
2827 ((char *)pService) +
2829 ((char *)&sDefault) +
2832 return &parm_table[(*i)++];
2842 /***************************************************************************
2843 Return TRUE if the passed service number is within range.
2844 ***************************************************************************/
2846 BOOL lp_snum_ok(int iService)
2848 return (LP_SNUM_OK(iService) && ServicePtrs[iService]->bAvailable);
2851 /***************************************************************************
2852 Auto-load some home services.
2853 ***************************************************************************/
2855 static void lp_add_auto_services(const char *str)
2860 /***************************************************************************
2861 Auto-load one printer.
2862 ***************************************************************************/
2864 void lp_add_one_printer(char *name, char *comment)
2866 int printers = lp_servicenumber(PRINTERS_NAME);
2869 if (lp_servicenumber(name) < 0) {
2870 lp_add_printer(name, printers);
2871 if ((i = lp_servicenumber(name)) >= 0) {
2872 string_set(&ServicePtrs[i]->comment, comment);
2873 ServicePtrs[i]->autoloaded = True;
2878 /***************************************************************************
2879 Announce ourselves as a print server.
2880 ***************************************************************************/
2882 void update_server_announce_as_printserver(void)
2884 default_server_announce |= SV_TYPE_PRINTQ_SERVER;
2887 /***************************************************************************
2888 Have we loaded a services file yet?
2889 ***************************************************************************/
2891 BOOL lp_loaded(void)
2896 /***************************************************************************
2897 Unload unused services.
2898 ***************************************************************************/
2900 void lp_killunused(struct smbsrv_connection *smb, BOOL (*snumused) (struct smbsrv_connection *, int))
2903 for (i = 0; i < iNumServices; i++) {
2907 if (!snumused || !snumused(smb, i)) {
2908 ServicePtrs[i]->valid = False;
2909 free_service(ServicePtrs[i]);
2914 /***************************************************************************
2916 ***************************************************************************/
2918 void lp_killservice(int iServiceIn)
2920 if (VALID(iServiceIn)) {
2921 ServicePtrs[iServiceIn]->valid = False;
2922 free_service(ServicePtrs[iServiceIn]);
2926 /*******************************************************************
2927 Set the server type we will announce as via nmbd.
2928 ********************************************************************/
2930 static void set_server_role(void)
2932 server_role = ROLE_STANDALONE;
2934 switch (lp_security()) {
2936 if (lp_domain_logons())
2937 DEBUG(0, ("Server's Role (logon server) conflicts with share-level security\n"));
2942 if (lp_domain_logons()) {
2943 if (Globals.bDomainMaster) /* auto or yes */
2944 server_role = ROLE_DOMAIN_PDC;
2946 server_role = ROLE_DOMAIN_BDC;
2949 server_role = ROLE_DOMAIN_MEMBER;
2952 if (lp_domain_logons()) {
2954 if (Globals.bDomainMaster) /* auto or yes */
2955 server_role = ROLE_DOMAIN_PDC;
2957 server_role = ROLE_DOMAIN_BDC;
2961 DEBUG(0, ("Server's Role undefined due to unknown security mode\n"));
2965 DEBUG(10, ("set_server_role: role = "));
2967 switch(server_role) {
2968 case ROLE_STANDALONE:
2969 DEBUGADD(10, ("ROLE_STANDALONE\n"));
2971 case ROLE_DOMAIN_MEMBER:
2972 DEBUGADD(10, ("ROLE_DOMAIN_MEMBER\n"));
2974 case ROLE_DOMAIN_BDC:
2975 DEBUGADD(10, ("ROLE_DOMAIN_BDC\n"));
2977 case ROLE_DOMAIN_PDC:
2978 DEBUGADD(10, ("ROLE_DOMAIN_PDC\n"));
2983 /***************************************************************************
2984 Load the services array from the services file. Return True on success,
2986 ***************************************************************************/
2992 struct param_opt *data;
2996 bInGlobalSection = True;
2998 if (Globals.param_opt != NULL) {
2999 struct param_opt *next;
3000 for (data=Globals.param_opt; data; data=next) {
3002 if (data->flags & FLAG_CMDLINE) continue;
3005 DLIST_REMOVE(Globals.param_opt, data);
3012 pstrcpy(n2, lp_configfile());
3013 standard_sub_basic(n2,sizeof(n2));
3014 DEBUG(2, ("lp_load: refreshing parameters from %s\n", n2));
3016 add_to_file_list(lp_configfile(), n2);
3018 /* We get sections first, so have to start 'behind' to make up */
3020 bRetval = pm_process(n2, do_section, do_parameter);
3022 /* finish up the last section */
3023 DEBUG(4, ("pm_process() returned %s\n", BOOLSTR(bRetval)));
3025 if (iServiceIndex >= 0)
3026 bRetval = service_ok(iServiceIndex);
3028 lp_add_auto_services(lp_auto_services());
3030 /* When 'restrict anonymous = 2' guest connections to ipc$
3032 lp_add_hidden("IPC$", "IPC", (lp_restrict_anonymous() < 2));
3033 lp_add_hidden("ADMIN$", "DISK", False);
3036 set_default_server_announce_type();
3040 if (Globals.bWINSsupport) {
3041 lp_do_parameter(-1, "wins server", "127.0.0.1");
3049 /***************************************************************************
3050 Reset the max number of services.
3051 ***************************************************************************/
3053 void lp_resetnumservices(void)
3058 /***************************************************************************
3059 Return the max number of services.
3060 ***************************************************************************/
3062 int lp_numservices(void)
3064 return (iNumServices);
3067 /***************************************************************************
3068 Display the contents of the services array in human-readable form.
3069 ***************************************************************************/
3071 void lp_dump(FILE *f, BOOL show_defaults, int maxtoprint)
3076 defaults_saved = False;
3080 dump_a_service(&sDefault, f);
3082 for (iService = 0; iService < maxtoprint; iService++)
3083 lp_dump_one(f, show_defaults, iService);
3086 /***************************************************************************
3087 Display the contents of one service in human-readable form.
3088 ***************************************************************************/
3090 void lp_dump_one(FILE * f, BOOL show_defaults, int snum)
3093 if (ServicePtrs[snum]->szService[0] == '\0')
3095 dump_a_service(ServicePtrs[snum], f);
3099 /***************************************************************************
3100 Return the number of the service with the given name, or -1 if it doesn't
3101 exist. Note that this is a DIFFERENT ANIMAL from the internal function
3102 getservicebyname()! This works ONLY if all services have been loaded, and
3103 does not copy the found service.
3104 ***************************************************************************/
3106 int lp_servicenumber(const char *pszServiceName)
3109 fstring serviceName;
3112 for (iService = iNumServices - 1; iService >= 0; iService--) {
3113 if (VALID(iService) && ServicePtrs[iService]->szService) {
3115 * The substitution here is used to support %U is
3118 fstrcpy(serviceName, ServicePtrs[iService]->szService);
3119 standard_sub_basic(serviceName,sizeof(serviceName));
3120 if (strequal(serviceName, pszServiceName))
3126 DEBUG(7,("lp_servicenumber: couldn't find %s\n", pszServiceName));
3131 /*******************************************************************
3132 A useful volume label function.
3133 ********************************************************************/
3134 const char *volume_label(int snum)
3136 const char *ret = lp_volume(snum);
3138 return lp_servicename(snum);
3143 /*******************************************************************
3144 Set the server type we will announce as via nmbd.
3145 ********************************************************************/
3147 static void set_default_server_announce_type(void)
3149 default_server_announce = 0;
3150 default_server_announce |= SV_TYPE_WORKSTATION;
3151 default_server_announce |= SV_TYPE_SERVER;
3152 default_server_announce |= SV_TYPE_SERVER_UNIX;
3154 switch (lp_announce_as()) {
3155 case ANNOUNCE_AS_NT_SERVER:
3156 default_server_announce |= SV_TYPE_SERVER_NT;
3157 /* fall through... */
3158 case ANNOUNCE_AS_NT_WORKSTATION:
3159 default_server_announce |= SV_TYPE_NT;
3161 case ANNOUNCE_AS_WIN95:
3162 default_server_announce |= SV_TYPE_WIN95_PLUS;
3164 case ANNOUNCE_AS_WFW:
3165 default_server_announce |= SV_TYPE_WFW;
3171 switch (lp_server_role()) {
3172 case ROLE_DOMAIN_MEMBER:
3173 default_server_announce |= SV_TYPE_DOMAIN_MEMBER;
3175 case ROLE_DOMAIN_PDC:
3176 default_server_announce |= SV_TYPE_DOMAIN_CTRL;
3178 case ROLE_DOMAIN_BDC:
3179 default_server_announce |= SV_TYPE_DOMAIN_BAKCTRL;
3181 case ROLE_STANDALONE:
3185 if (lp_time_server())
3186 default_server_announce |= SV_TYPE_TIME_SOURCE;
3188 if (lp_host_msdfs())
3189 default_server_announce |= SV_TYPE_DFS_SERVER;
3191 /* TODO: only announce us as print server when we are a print server */
3192 default_server_announce |= SV_TYPE_PRINTQ_SERVER;
3195 /***********************************************************
3196 returns role of Samba server
3197 ************************************************************/
3199 int lp_server_role(void)
3204 /***********************************************************
3205 If we are PDC then prefer us as DMB
3206 ************************************************************/
3208 BOOL lp_domain_master(void)
3210 if (Globals.bDomainMaster == Auto)
3211 return (lp_server_role() == ROLE_DOMAIN_PDC);
3213 return Globals.bDomainMaster;
3216 /***********************************************************
3217 If we are DMB then prefer us as LMB
3218 ************************************************************/
3220 BOOL lp_preferred_master(void)
3222 if (Globals.bPreferredMaster == Auto)
3223 return (lp_local_master() && lp_domain_master());
3225 return Globals.bPreferredMaster;
3228 /*******************************************************************
3230 ********************************************************************/
3232 void lp_remove_service(int snum)
3234 ServicePtrs[snum]->valid = False;
3237 /*******************************************************************
3239 ********************************************************************/
3241 void lp_copy_service(int snum, const char *new_name)
3243 const char *oldname = lp_servicename(snum);
3244 do_section(new_name);
3246 snum = lp_servicenumber(new_name);
3248 lp_do_parameter(snum, "copy", oldname);
3253 /*******************************************************************
3254 Get the default server type we will announce as via nmbd.
3255 ********************************************************************/
3256 int lp_default_server_announce(void)
3258 return default_server_announce;
3261 const char *lp_printername(int snum)
3263 const char *ret = _lp_printername(snum);
3264 if (ret == NULL || (ret != NULL && *ret == '\0'))
3265 ret = lp_const_servicename(snum);
3271 /*******************************************************************
3272 Return the max print jobs per queue.
3273 ********************************************************************/
3275 int lp_maxprintjobs(int snum)
3277 int maxjobs = LP_SNUM_OK(snum) ? ServicePtrs[snum]->iMaxPrintJobs : sDefault.iMaxPrintJobs;
3278 if (maxjobs <= 0 || maxjobs >= PRINT_MAX_JOBID)
3279 maxjobs = PRINT_MAX_JOBID - 1;