2 Unix SMB/Netbios implementation.
4 Parameter loading functions
5 Copyright (C) Karl Auer 1993-1998
7 Largely re-written by Andrew Tridgell, September 1994
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program; if not, write to the Free Software
21 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
27 * This module provides suitable callback functions for the params
28 * module. It builds the internal table of service details which is
29 * then used by the rest of the server.
33 * 1) add it to the global or service structure definition
34 * 2) add it to the parm_table
35 * 3) add it to the list of available functions (eg: using FN_GLOBAL_STRING())
36 * 4) If it's a global then initialise it in init_globals. If a local
37 * (ie. service) parameter then initialise it in the sDefault structure
41 * The configuration file is processed sequentially for speed. It is NOT
42 * accessed randomly as happens in 'real' Windows. For this reason, there
43 * is a fair bit of sequence-dependent code here - ie., code which assumes
44 * that certain things happen before others. In particular, the code which
45 * happens at the boundary between sections is delicately poised, so be
52 /* Set default coding system for KANJI if none specified in Makefile. */
54 * We treat KANJI specially due to historical precedent (it was the
55 * first non-english codepage added to Samba). With the new dynamic
56 * codepage support this is not needed anymore.
58 * The define 'KANJI' is being overloaded to mean 'use kanji codepage
59 * by default' and also 'this is the filename-to-disk conversion
60 * method to use'. This really should be removed and all control
61 * over this left in the smb.conf parameters 'client codepage'
62 * and 'coding system'.
70 extern int DEBUGLEVEL;
71 extern pstring user_socket_options;
72 extern pstring global_myname;
75 #define GLOBAL_NAME "global"
79 #define PRINTERS_NAME "printers"
83 #define HOMES_NAME "homes"
86 /* some helpful bits */
87 #define pSERVICE(i) ServicePtrs[i]
88 #define iSERVICE(i) (*pSERVICE(i))
89 #define LP_SNUM_OK(iService) (((iService) >= 0) && ((iService) < iNumServices) && iSERVICE(iService).valid)
90 #define VALID(i) iSERVICE(i).valid
92 int keepalive=DEFAULT_KEEPALIVE;
93 extern BOOL use_getwd_cache;
95 extern int extra_time_offset;
97 static BOOL defaults_saved=False;
100 * This structure describes global (ie., server-wide) parameters.
104 char *szPrintcapname;
107 char *szDefaultService;
111 char *szServerString;
112 char *szAutoServices;
113 char *szPasswdProgram;
117 char *szSMBPasswdFile;
118 char *szPasswordServer;
119 char *szSocketOptions;
122 char *szDomainAdminGroup;
123 char *szDomainGuestGroup;
124 char *szDomainAdminUsers;
125 char *szDomainGuestUsers;
126 char *szDomainHostsallow;
127 char *szDomainHostsdeny;
129 char *szGroupnameMap;
130 char *szCharacterSet;
137 char *szCodingSystem;
139 char *szRemoteAnnounce;
140 char *szRemoteBrowseSync;
141 char *szSocketAddress;
142 char *szNISHomeMapName;
143 char *szAnnounceVersion; /* This is initialised in init_globals */
144 char *szNetbiosAliases;
146 char *szDomainOtherSIDs;
147 char *szDomainGroups;
149 char *szNameResolveOrder;
154 char *szLdapRootPassword;
176 int client_code_page;
177 int announce_as; /* This is initialised in init_globals */
178 int machine_password_timeout;
181 #endif /* WITH_LDAP */
184 char *sslHostsRequire;
185 char *sslHostsResign;
191 char *sslClientPrivKey;
194 BOOL sslReqClientCert;
195 BOOL sslReqServerCert;
196 BOOL sslCompatibility;
197 #endif /* WITH_SSL */
202 BOOL bPreferredMaster;
203 BOOL bDomainController;
206 BOOL bEncryptPasswords;
214 BOOL bReadPrediction;
221 BOOL bBindInterfacesOnly;
222 BOOL bNetWkstaUserLogon;
223 BOOL bUnixPasswdSync;
224 BOOL bPasswdChatDebug;
225 BOOL bOleLockingCompat;
228 static global Globals;
233 * This structure describes a single service.
241 char *szGuestaccount;
242 char *szInvalidUsers;
250 char *szRootPostExec;
251 char *szPrintcommand;
254 char *szLppausecommand;
255 char *szLpresumecommand;
256 char *szQueuepausecommand;
257 char *szQueueresumecommand;
259 char *szPrinterDriver;
260 char *szPrinterDriverLocation;
269 char *szVetoOplockFiles;
278 int iCreate_force_mode;
288 BOOL bShortCasePreserve;
315 BOOL bDeleteReadonly;
317 BOOL bDeleteVetoFiles;
319 BOOL bDosFiletimeResolution;
320 BOOL bFakeDirCreateTimes;
321 char dummy[3]; /* for alignment */
325 /* This is a default service used to prime a services structure */
326 static service sDefault =
329 NULL, /* szService */
331 NULL, /* szUsername */
332 NULL, /* szGuestAccount - this is set in init_globals() */
333 NULL, /* szInvalidUsers */
334 NULL, /* szValidUsers */
335 NULL, /* szAdminUsers */
337 NULL, /* szInclude */
338 NULL, /* szPreExec */
339 NULL, /* szPostExec */
340 NULL, /* szRootPreExec */
341 NULL, /* szRootPostExec */
342 NULL, /* szPrintcommand */
343 NULL, /* szLpqcommand */
344 NULL, /* szLprmcommand */
345 NULL, /* szLppausecommand */
346 NULL, /* szLpresumecommand */
347 NULL, /* szQueuepausecommand */
348 NULL, /* szQueueresumecommand */
349 NULL, /* szPrintername */
350 NULL, /* szPrinterDriver - this is set in init_globals() */
351 NULL, /* szPrinterDriverLocation */
352 NULL, /* szDontdescend */
353 NULL, /* szHostsallow */
354 NULL, /* szHostsdeny */
355 NULL, /* szMagicScript */
356 NULL, /* szMagicOutput */
357 NULL, /* szMangledMap */
358 NULL, /* szVetoFiles */
359 NULL, /* szHideFiles */
360 NULL, /* szVetoOplockFiles */
362 NULL, /* force user */
363 NULL, /* force group */
365 NULL, /* writelist */
367 0, /* iMinPrintSpace */
368 0744, /* iCreate_mask */
369 0000, /* iCreate_force_mode */
370 0755, /* iDir_mask */
371 0000, /* iDir_force_mode */
372 0, /* iMaxConnections */
373 CASE_LOWER, /* iDefaultCase */
374 DEFAULT_PRINTING, /* iPrinting */
375 False, /* bAlternatePerm */
376 False, /* revalidate */
377 False, /* case sensitive */
378 True, /* case preserve */
379 True, /* short case preserve */
380 False, /* case mangle */
382 True, /* bHideDotFiles */
383 True, /* bBrowseable */
384 True, /* bAvailable */
385 True, /* bRead_only */
386 True, /* bNo_set_dir */
387 False, /* bGuest_only */
388 False, /* bGuest_ok */
389 False, /* bPrint_ok */
390 False, /* bPostscript */
391 False, /* bMap_system */
392 False, /* bMap_hidden */
393 True, /* bMap_archive */
395 False, /* bStrictLocking */
396 True, /* bShareModes */
398 False, /* bOnlyUser */
399 True, /* bMangledNames */
400 True, /* bWidelinks */
401 True, /* bSymlinks */
402 False, /* bSyncAlways */
403 False, /* bStrictSync */
404 '~', /* magic char */
406 False, /* bDeleteReadonly */
407 False, /* bFakeOplocks */
408 False, /* bDeleteVetoFiles */
409 False, /* bDosFiletimes */
410 False, /* bDosFiletimeResolution */
411 False, /* bFakeDirCreateTimes */
417 /* local variables */
418 static service **ServicePtrs = NULL;
419 static int iNumServices = 0;
420 static int iServiceIndex = 0;
421 static BOOL bInGlobalSection = True;
422 static BOOL bGlobalOnly = False;
423 static int default_server_announce;
425 #define NUMPARAMETERS (sizeof(parm_table) / sizeof(struct parm_struct))
427 /* prototypes for the special type handlers */
428 static BOOL handle_valid_chars(char *pszParmValue, char **ptr);
429 static BOOL handle_include(char *pszParmValue, char **ptr);
430 static BOOL handle_copy(char *pszParmValue, char **ptr);
431 static BOOL handle_character_set(char *pszParmValue,char **ptr);
432 static BOOL handle_coding_system(char *pszParmValue,char **ptr);
434 static void set_default_server_announce_type(void);
436 static struct enum_list enum_protocol[] = {{PROTOCOL_NT1, "NT1"}, {PROTOCOL_LANMAN2, "LANMAN2"},
437 {PROTOCOL_LANMAN1, "LANMAN1"}, {PROTOCOL_CORE,"CORE"},
438 {PROTOCOL_COREPLUS, "COREPLUS"},
439 {PROTOCOL_COREPLUS, "CORE+"}, {-1, NULL}};
441 static struct enum_list enum_security[] = {{SEC_SHARE, "SHARE"}, {SEC_USER, "USER"},
442 {SEC_SERVER, "SERVER"}, {SEC_DOMAIN, "DOMAIN"},
445 static struct enum_list enum_printing[] = {{PRINT_SYSV, "sysv"}, {PRINT_AIX, "aix"},
446 {PRINT_HPUX, "hpux"}, {PRINT_BSD, "bsd"},
447 {PRINT_QNX, "qnx"}, {PRINT_PLP, "plp"},
448 {PRINT_LPRNG, "lprng"}, {PRINT_SOFTQ, "softq"},
451 static struct enum_list enum_announce_as[] = {{ANNOUNCE_AS_NT, "NT"}, {ANNOUNCE_AS_WIN95, "win95"},
452 {ANNOUNCE_AS_WFW, "WfW"}, {-1, NULL}};
454 static struct enum_list enum_case[] = {{CASE_LOWER, "lower"}, {CASE_UPPER, "upper"}, {-1, NULL}};
456 static struct enum_list enum_lm_announce[] = {{0, "False"}, {1, "True"}, {2, "Auto"}, {-1, NULL}};
459 static struct enum_list enum_ssl_version[] = {{SMB_SSL_V2, "ssl2"}, {SMB_SSL_V3, "ssl3"},
460 {SMB_SSL_V23, "ssl2or3"}, {SMB_SSL_TLS1, "tls1"}, {-1, NULL}};
463 /* note that we do not initialise the defaults union - it is not allowed in ANSI C */
464 static struct parm_struct parm_table[] =
466 {"Base Options", P_SEP, P_SEPARATOR},
467 {"comment", P_STRING, P_LOCAL, &sDefault.comment, NULL, NULL, FLAG_BASIC|FLAG_PRINT},
468 {"path", P_STRING, P_LOCAL, &sDefault.szPath, NULL, NULL, FLAG_BASIC|FLAG_PRINT},
469 {"directory", P_STRING, P_LOCAL, &sDefault.szPath, NULL, NULL, 0},
470 {"workgroup", P_USTRING, P_GLOBAL, &Globals.szWorkGroup, NULL, NULL, FLAG_BASIC},
471 {"netbios name", P_UGSTRING,P_GLOBAL, global_myname, NULL, NULL, FLAG_BASIC},
472 {"netbios aliases", P_STRING, P_GLOBAL, &Globals.szNetbiosAliases, NULL, NULL, 0},
473 {"server string", P_STRING, P_GLOBAL, &Globals.szServerString, NULL, NULL, FLAG_BASIC},
474 {"interfaces", P_STRING, P_GLOBAL, &Globals.szInterfaces, NULL, NULL, FLAG_BASIC},
475 {"bind interfaces only", P_BOOL,P_GLOBAL, &Globals.bBindInterfacesOnly,NULL, NULL, 0},
477 {"Security Options", P_SEP, P_SEPARATOR},
478 {"security", P_ENUM, P_GLOBAL, &Globals.security, NULL, enum_security, FLAG_BASIC},
479 {"encrypt passwords",P_BOOL, P_GLOBAL, &Globals.bEncryptPasswords, NULL, NULL, FLAG_BASIC},
480 {"update encrypted", P_BOOL, P_GLOBAL, &Globals.bUpdateEncrypt, NULL, NULL, FLAG_BASIC},
481 {"use rhosts", P_BOOL, P_GLOBAL, &Globals.bUseRhosts, NULL, NULL, 0},
482 {"null passwords", P_BOOL, P_GLOBAL, &Globals.bNullPasswords, NULL, NULL, 0},
483 {"password server", P_STRING, P_GLOBAL, &Globals.szPasswordServer, NULL, NULL, 0},
484 {"smb passwd file", P_STRING, P_GLOBAL, &Globals.szSMBPasswdFile, NULL, NULL, 0},
485 {"hosts equiv", P_STRING, P_GLOBAL, &Globals.szHostsEquiv, NULL, NULL, 0},
486 {"root directory", P_STRING, P_GLOBAL, &Globals.szRootdir, NULL, NULL, 0},
487 {"root dir", P_STRING, P_GLOBAL, &Globals.szRootdir, NULL, NULL, 0},
488 {"root", P_STRING, P_GLOBAL, &Globals.szRootdir, NULL, NULL, 0},
489 {"passwd program", P_STRING, P_GLOBAL, &Globals.szPasswdProgram, NULL, NULL, 0},
490 {"passwd chat", P_STRING, P_GLOBAL, &Globals.szPasswdChat, NULL, NULL, 0},
491 {"passwd chat debug",P_BOOL, P_GLOBAL, &Globals.bPasswdChatDebug, NULL, NULL, 0},
492 {"username map", P_STRING, P_GLOBAL, &Globals.szUsernameMap, NULL, NULL, 0},
493 {"password level", P_INTEGER, P_GLOBAL, &Globals.pwordlevel, NULL, NULL, 0},
494 {"username level", P_INTEGER, P_GLOBAL, &Globals.unamelevel, NULL, NULL, 0},
495 {"unix password sync", P_BOOL, P_GLOBAL, &Globals.bUnixPasswdSync, NULL, NULL, 0},
496 {"alternate permissions",P_BOOL,P_LOCAL, &sDefault.bAlternatePerm, NULL, NULL, FLAG_GLOBAL},
497 {"revalidate", P_BOOL, P_LOCAL, &sDefault.bRevalidate, NULL, NULL, FLAG_GLOBAL},
498 {"username", P_STRING, P_LOCAL, &sDefault.szUsername, NULL, NULL, FLAG_GLOBAL},
499 {"user", P_STRING, P_LOCAL, &sDefault.szUsername, NULL, NULL, 0},
500 {"users", P_STRING, P_LOCAL, &sDefault.szUsername, NULL, NULL, 0},
501 {"guest account", P_STRING, P_LOCAL, &sDefault.szGuestaccount, NULL, NULL, FLAG_BASIC|FLAG_PRINT|FLAG_GLOBAL},
502 {"invalid users", P_STRING, P_LOCAL, &sDefault.szInvalidUsers, NULL, NULL, FLAG_GLOBAL},
503 {"valid users", P_STRING, P_LOCAL, &sDefault.szValidUsers, NULL, NULL, FLAG_GLOBAL},
504 {"admin users", P_STRING, P_LOCAL, &sDefault.szAdminUsers, NULL, NULL, FLAG_GLOBAL},
505 {"read list", P_STRING, P_LOCAL, &sDefault.readlist, NULL, NULL, FLAG_GLOBAL},
506 {"write list", P_STRING, P_LOCAL, &sDefault.writelist, NULL, NULL, FLAG_GLOBAL},
507 {"force user", P_STRING, P_LOCAL, &sDefault.force_user, NULL, NULL, 0},
508 {"force group", P_STRING, P_LOCAL, &sDefault.force_group, NULL, NULL, 0},
509 {"group", P_STRING, P_LOCAL, &sDefault.force_group, NULL, NULL, 0},
510 {"read only", P_BOOL, P_LOCAL, &sDefault.bRead_only, NULL, NULL, FLAG_BASIC},
511 {"write ok", P_BOOLREV, P_LOCAL, &sDefault.bRead_only, NULL, NULL, 0},
512 {"writeable", P_BOOLREV, P_LOCAL, &sDefault.bRead_only, NULL, NULL, 0},
513 {"writable", P_BOOLREV, P_LOCAL, &sDefault.bRead_only, NULL, NULL, 0},
514 {"create mask", P_OCTAL, P_LOCAL, &sDefault.iCreate_mask, NULL, NULL, FLAG_GLOBAL},
515 {"create mode", P_OCTAL, P_LOCAL, &sDefault.iCreate_mask, NULL, NULL, FLAG_GLOBAL},
516 {"force create mode",P_OCTAL, P_LOCAL, &sDefault.iCreate_force_mode, NULL, NULL, FLAG_GLOBAL},
517 {"directory mask", P_OCTAL, P_LOCAL, &sDefault.iDir_mask, NULL, NULL, FLAG_GLOBAL},
518 {"directory mode", P_OCTAL, P_LOCAL, &sDefault.iDir_mask, NULL, NULL, FLAG_GLOBAL},
519 {"force directory mode", P_OCTAL, P_LOCAL, &sDefault.iDir_force_mode, NULL, NULL, FLAG_GLOBAL},
520 {"guest only", P_BOOL, P_LOCAL, &sDefault.bGuest_only, NULL, NULL, 0},
521 {"only guest", P_BOOL, P_LOCAL, &sDefault.bGuest_only, NULL, NULL, 0},
522 {"guest ok", P_BOOL, P_LOCAL, &sDefault.bGuest_ok, NULL, NULL, FLAG_BASIC|FLAG_PRINT},
523 {"public", P_BOOL, P_LOCAL, &sDefault.bGuest_ok, NULL, NULL, 0},
524 {"only user", P_BOOL, P_LOCAL, &sDefault.bOnlyUser, NULL, NULL, 0},
525 {"hosts allow", P_STRING, P_LOCAL, &sDefault.szHostsallow, NULL, NULL, FLAG_GLOBAL|FLAG_BASIC|FLAG_PRINT},
526 {"allow hosts", P_STRING, P_LOCAL, &sDefault.szHostsallow, NULL, NULL, 0},
527 {"hosts deny", P_STRING, P_LOCAL, &sDefault.szHostsdeny, NULL, NULL, FLAG_GLOBAL|FLAG_BASIC|FLAG_PRINT},
528 {"deny hosts", P_STRING, P_LOCAL, &sDefault.szHostsdeny, NULL, NULL, 0},
531 {"Secure Socket Layer Options", P_SEP, P_SEPARATOR},
532 {"ssl", P_BOOL, P_GLOBAL, &Globals.sslEnabled, NULL, NULL, 0 },
533 {"ssl hosts", P_STRING, P_GLOBAL, &Globals.sslHostsRequire, NULL, NULL, 0 },
534 {"ssl hosts resign", P_STRING, P_GLOBAL, &Globals.sslHostsResign, NULL, NULL, 0} ,
535 {"ssl CA certDir", P_STRING, P_GLOBAL, &Globals.sslCaCertDir, NULL, NULL, 0 },
536 {"ssl CA certFile", P_STRING, P_GLOBAL, &Globals.sslCaCertFile, NULL, NULL, 0 },
537 {"ssl server cert", P_STRING, P_GLOBAL, &Globals.sslCert, NULL, NULL, 0 },
538 {"ssl server key", P_STRING, P_GLOBAL, &Globals.sslPrivKey, NULL, NULL, 0 },
539 {"ssl client cert", P_STRING, P_GLOBAL, &Globals.sslClientCert, NULL, NULL, 0 },
540 {"ssl client key", P_STRING, P_GLOBAL, &Globals.sslClientPrivKey, NULL, NULL, 0 },
541 {"ssl require clientcert", P_BOOL, P_GLOBAL, &Globals.sslReqClientCert, NULL, NULL , 0},
542 {"ssl require servercert", P_BOOL, P_GLOBAL, &Globals.sslReqServerCert, NULL, NULL , 0},
543 {"ssl ciphers", P_STRING, P_GLOBAL, &Globals.sslCiphers, NULL, NULL, 0 },
544 {"ssl version", P_ENUM, P_GLOBAL, &Globals.sslVersion, NULL, enum_ssl_version, 0},
545 {"ssl compatibility", P_BOOL, P_GLOBAL, &Globals.sslCompatibility, NULL, NULL, 0 },
546 #endif /* WITH_SSL */
548 {"Logging Options", P_SEP, P_SEPARATOR},
549 {"log level", P_INTEGER, P_GLOBAL, &DEBUGLEVEL, NULL, NULL, FLAG_BASIC},
550 {"debuglevel", P_INTEGER, P_GLOBAL, &DEBUGLEVEL, NULL, NULL, 0},
551 {"syslog", P_INTEGER, P_GLOBAL, &Globals.syslog, NULL, NULL, 0},
552 {"syslog only", P_BOOL, P_GLOBAL, &Globals.bSyslogOnly, NULL, NULL, 0},
553 {"log file", P_STRING, P_GLOBAL, &Globals.szLogFile, NULL, NULL, 0},
554 {"max log size", P_INTEGER, P_GLOBAL, &Globals.max_log_size, NULL, NULL, 0},
555 {"status", P_BOOL, P_LOCAL, &sDefault.status, NULL, NULL, FLAG_GLOBAL},
557 {"Protocol Options", P_SEP, P_SEPARATOR},
558 {"protocol", P_ENUM, P_GLOBAL, &Globals.maxprotocol, NULL, enum_protocol, 0},
559 {"read bmpx", P_BOOL, P_GLOBAL, &Globals.bReadbmpx, NULL, NULL, 0},
560 {"read raw", P_BOOL, P_GLOBAL, &Globals.bReadRaw, NULL, NULL, 0},
561 {"write raw", P_BOOL, P_GLOBAL, &Globals.bWriteRaw, NULL, NULL, 0},
562 {"networkstation user login", P_BOOL,P_GLOBAL, &Globals.bNetWkstaUserLogon,NULL, NULL, 0},
563 {"announce version", P_STRING, P_GLOBAL, &Globals.szAnnounceVersion, NULL, NULL, 0},
564 {"announce as", P_ENUM, P_GLOBAL, &Globals.announce_as, NULL, enum_announce_as, 0},
565 {"max mux", P_INTEGER, P_GLOBAL, &Globals.max_mux, NULL, NULL, 0},
566 {"max xmit", P_INTEGER, P_GLOBAL, &Globals.max_xmit, NULL, NULL, 0},
567 {"name resolve order", P_STRING, P_GLOBAL, &Globals.szNameResolveOrder, NULL, NULL, 0},
568 {"max packet", P_INTEGER, P_GLOBAL, &Globals.max_packet, NULL, NULL, 0},
569 {"packet size", P_INTEGER, P_GLOBAL, &Globals.max_packet, NULL, NULL, 0},
570 {"max ttl", P_INTEGER, P_GLOBAL, &Globals.max_ttl, NULL, NULL, 0},
571 {"max wins ttl", P_INTEGER, P_GLOBAL, &Globals.max_wins_ttl, NULL, NULL, 0},
572 {"min wins ttl", P_INTEGER, P_GLOBAL, &Globals.min_wins_ttl, NULL, NULL, 0},
573 {"time server", P_BOOL, P_GLOBAL, &Globals.bTimeServer, NULL, NULL, 0},
575 {"Tuning Options", P_SEP, P_SEPARATOR},
576 {"max disk size", P_INTEGER, P_GLOBAL, &Globals.maxdisksize, NULL, NULL, 0},
577 {"lpq cache time", P_INTEGER, P_GLOBAL, &Globals.lpqcachetime, NULL, NULL, 0},
578 {"getwd cache", P_BOOL, P_GLOBAL, &use_getwd_cache, NULL, NULL, 0},
579 {"read prediction", P_BOOL, P_GLOBAL, &Globals.bReadPrediction, NULL, NULL, 0},
580 {"socket options", P_GSTRING, P_GLOBAL, user_socket_options, NULL, NULL, 0},
581 {"keepalive", P_INTEGER, P_GLOBAL, &keepalive, NULL, NULL, 0},
582 {"deadtime", P_INTEGER, P_GLOBAL, &Globals.deadtime, NULL, NULL, 0},
583 {"read size", P_INTEGER, P_GLOBAL, &Globals.ReadSize, NULL, NULL, 0},
584 {"shared mem size", P_INTEGER, P_GLOBAL, &Globals.shmem_size, NULL, NULL, 0},
585 {"max connections", P_INTEGER, P_LOCAL, &sDefault.iMaxConnections, NULL, NULL, 0},
586 {"min print space", P_INTEGER, P_LOCAL, &sDefault.iMinPrintSpace, NULL, NULL, 0},
587 {"sync always", P_BOOL, P_LOCAL, &sDefault.bSyncAlways, NULL, NULL, 0},
588 {"strict sync", P_BOOL, P_LOCAL, &sDefault.bStrictSync, NULL, NULL, 0},
590 {"Printing Options", P_SEP, P_SEPARATOR},
591 {"load printers", P_BOOL, P_GLOBAL, &Globals.bLoadPrinters, NULL, NULL, 0},
592 {"printcap name", P_STRING, P_GLOBAL, &Globals.szPrintcapname, NULL, NULL, 0},
593 {"printcap", P_STRING, P_GLOBAL, &Globals.szPrintcapname, NULL, NULL, 0},
594 {"printer driver file", P_STRING, P_GLOBAL, &Globals.szDriverFile, NULL, NULL, 0},
595 {"print ok", P_BOOL, P_LOCAL, &sDefault.bPrint_ok, NULL, NULL, 0},
596 {"printable", P_BOOL, P_LOCAL, &sDefault.bPrint_ok, NULL, NULL, 0},
597 {"postscript", P_BOOL, P_LOCAL, &sDefault.bPostscript, NULL, NULL, FLAG_PRINT},
598 {"printing", P_ENUM, P_LOCAL, &sDefault.iPrinting, NULL, enum_printing, FLAG_PRINT|FLAG_GLOBAL},
599 {"print command", P_STRING, P_LOCAL, &sDefault.szPrintcommand, NULL, NULL, FLAG_PRINT|FLAG_GLOBAL},
600 {"lpq command", P_STRING, P_LOCAL, &sDefault.szLpqcommand, NULL, NULL, FLAG_PRINT|FLAG_GLOBAL},
601 {"lprm command", P_STRING, P_LOCAL, &sDefault.szLprmcommand, NULL, NULL, FLAG_PRINT|FLAG_GLOBAL},
602 {"lppause command", P_STRING, P_LOCAL, &sDefault.szLppausecommand, NULL, NULL, FLAG_GLOBAL},
603 {"lpresume command", P_STRING, P_LOCAL, &sDefault.szLpresumecommand,NULL, NULL, FLAG_GLOBAL},
604 {"queuepause command", P_STRING, P_LOCAL, &sDefault.szQueuepausecommand, NULL, NULL, FLAG_GLOBAL},
605 {"queueresume command", P_STRING, P_LOCAL, &sDefault.szQueueresumecommand, NULL, NULL, FLAG_GLOBAL},
607 {"printer name", P_STRING, P_LOCAL, &sDefault.szPrintername, NULL, NULL, FLAG_PRINT},
608 {"printer", P_STRING, P_LOCAL, &sDefault.szPrintername, NULL, NULL, 0},
609 {"printer driver", P_STRING, P_LOCAL, &sDefault.szPrinterDriver, NULL, NULL, 0},
610 {"printer driver location", P_STRING, P_LOCAL, &sDefault.szPrinterDriverLocation, NULL, NULL, FLAG_GLOBAL},
613 {"Filename Handling", P_SEP, P_SEPARATOR},
614 {"strip dot", P_BOOL, P_GLOBAL, &Globals.bStripDot, NULL, NULL, 0},
615 {"character set", P_STRING, P_GLOBAL, &Globals.szCharacterSet, handle_character_set, NULL, 0},
616 {"mangled stack", P_INTEGER, P_GLOBAL, &Globals.mangled_stack, NULL, NULL, 0},
617 {"coding system", P_STRING, P_GLOBAL, &Globals.szCodingSystem, handle_coding_system, NULL, 0},
618 {"client code page", P_INTEGER, P_GLOBAL, &Globals.client_code_page, NULL, NULL, 0},
619 {"default case", P_ENUM, P_LOCAL, &sDefault.iDefaultCase, NULL, enum_case, 0},
620 {"case sensitive", P_BOOL, P_LOCAL, &sDefault.bCaseSensitive, NULL, NULL, FLAG_GLOBAL},
621 {"casesignames", P_BOOL, P_LOCAL, &sDefault.bCaseSensitive, NULL, NULL, 0},
622 {"preserve case", P_BOOL, P_LOCAL, &sDefault.bCasePreserve, NULL, NULL, FLAG_GLOBAL},
623 {"short preserve case",P_BOOL, P_LOCAL, &sDefault.bShortCasePreserve,NULL, NULL, FLAG_GLOBAL},
624 {"mangle case", P_BOOL, P_LOCAL, &sDefault.bCaseMangle, NULL, NULL, FLAG_GLOBAL},
625 {"mangling char", P_CHAR, P_LOCAL, &sDefault.magic_char, NULL, NULL, FLAG_GLOBAL},
626 {"hide dot files", P_BOOL, P_LOCAL, &sDefault.bHideDotFiles, NULL, NULL, FLAG_GLOBAL},
627 {"delete veto files",P_BOOL, P_LOCAL, &sDefault.bDeleteVetoFiles, NULL, NULL, FLAG_GLOBAL},
628 {"veto files", P_STRING, P_LOCAL, &sDefault.szVetoFiles, NULL, NULL, FLAG_GLOBAL},
629 {"hide files", P_STRING, P_LOCAL, &sDefault.szHideFiles, NULL, NULL, FLAG_GLOBAL},
630 {"veto oplock files",P_STRING, P_LOCAL, &sDefault.szVetoOplockFiles,NULL, NULL, FLAG_GLOBAL},
631 {"map system", P_BOOL, P_LOCAL, &sDefault.bMap_system, NULL, NULL, FLAG_GLOBAL},
632 {"map hidden", P_BOOL, P_LOCAL, &sDefault.bMap_hidden, NULL, NULL, FLAG_GLOBAL},
633 {"map archive", P_BOOL, P_LOCAL, &sDefault.bMap_archive, NULL, NULL, FLAG_GLOBAL},
634 {"mangled names", P_BOOL, P_LOCAL, &sDefault.bMangledNames, NULL, NULL, FLAG_GLOBAL},
635 {"mangled map", P_STRING, P_LOCAL, &sDefault.szMangledMap, NULL, NULL, FLAG_GLOBAL},
637 {"Domain Options", P_SEP, P_SEPARATOR},
638 {"domain sid", P_USTRING, P_GLOBAL, &Globals.szDomainSID, NULL, NULL, 0},
639 {"domain groups", P_STRING, P_GLOBAL, &Globals.szDomainGroups, NULL, NULL, 0},
640 {"domain controller",P_BOOL , P_GLOBAL, &Globals.bDomainController,NULL, NULL, 0},
641 {"domain admin group",P_STRING, P_GLOBAL, &Globals.szDomainAdminGroup, NULL, NULL, 0},
642 {"domain guest group",P_STRING, P_GLOBAL, &Globals.szDomainGuestGroup, NULL, NULL, 0},
643 {"domain admin users",P_STRING, P_GLOBAL, &Globals.szDomainAdminUsers, NULL, NULL, 0},
644 {"domain guest users",P_STRING, P_GLOBAL, &Globals.szDomainGuestUsers, NULL, NULL, 0},
645 {"groupname map", P_STRING, P_GLOBAL, &Globals.szGroupnameMap, NULL, NULL, 0},
646 {"machine password timeout", P_INTEGER, P_GLOBAL, &Globals.machine_password_timeout, NULL, NULL, 0},
648 {"Logon Options", P_SEP, P_SEPARATOR},
649 {"logon script", P_STRING, P_GLOBAL, &Globals.szLogonScript, NULL, NULL, 0},
650 {"logon path", P_STRING, P_GLOBAL, &Globals.szLogonPath, NULL, NULL, 0},
651 {"logon drive", P_STRING, P_GLOBAL, &Globals.szLogonDrive, NULL, NULL, 0},
652 {"logon home", P_STRING, P_GLOBAL, &Globals.szLogonHome, NULL, NULL, 0},
653 {"domain logons", P_BOOL, P_GLOBAL, &Globals.bDomainLogons, NULL, NULL, 0},
655 {"Browse Options", P_SEP, P_SEPARATOR},
656 {"os level", P_INTEGER, P_GLOBAL, &Globals.os_level, NULL, NULL, FLAG_BASIC},
657 {"lm announce", P_ENUM, P_GLOBAL, &Globals.lm_announce, NULL, enum_lm_announce, 0},
658 {"lm interval", P_INTEGER, P_GLOBAL, &Globals.lm_interval, NULL, NULL, 0},
659 {"preferred master", P_BOOL, P_GLOBAL, &Globals.bPreferredMaster, NULL, NULL, FLAG_BASIC},
660 {"prefered master", P_BOOL, P_GLOBAL, &Globals.bPreferredMaster, NULL, NULL, 0},
661 {"local master", P_BOOL, P_GLOBAL, &Globals.bLocalMaster, NULL, NULL, FLAG_BASIC},
662 {"domain master", P_BOOL, P_GLOBAL, &Globals.bDomainMaster, NULL, NULL, FLAG_BASIC},
663 {"browse list", P_BOOL, P_GLOBAL, &Globals.bBrowseList, NULL, NULL, 0},
664 {"browseable", P_BOOL, P_LOCAL, &sDefault.bBrowseable, NULL, NULL, 0},
665 {"browsable", P_BOOL, P_LOCAL, &sDefault.bBrowseable, NULL, NULL, 0},
667 {"WINS Options", P_SEP, P_SEPARATOR},
668 {"dns proxy", P_BOOL, P_GLOBAL, &Globals.bDNSproxy, NULL, NULL, 0},
669 {"wins support", P_BOOL, P_GLOBAL, &Globals.bWINSsupport, NULL, NULL, FLAG_BASIC},
670 {"wins proxy", P_BOOL, P_GLOBAL, &Globals.bWINSproxy, NULL, NULL, 0},
671 {"wins server", P_STRING, P_GLOBAL, &Globals.szWINSserver, NULL, NULL, FLAG_BASIC},
673 {"Locking Options", P_SEP, P_SEPARATOR},
674 {"locking", P_BOOL, P_LOCAL, &sDefault.bLocking, NULL, NULL, FLAG_GLOBAL},
675 {"strict locking", P_BOOL, P_LOCAL, &sDefault.bStrictLocking, NULL, NULL, FLAG_GLOBAL},
676 {"share modes", P_BOOL, P_LOCAL, &sDefault.bShareModes, NULL, NULL, FLAG_GLOBAL},
677 {"oplocks", P_BOOL, P_LOCAL, &sDefault.bOpLocks, NULL, NULL, FLAG_GLOBAL},
678 {"fake oplocks", P_BOOL, P_LOCAL, &sDefault.bFakeOplocks, NULL, NULL, 0},
679 {"ole locking compatibility", P_BOOL, P_GLOBAL, &Globals.bOleLockingCompat, NULL, NULL, FLAG_GLOBAL},
682 {"Ldap Options", P_SEP, P_SEPARATOR},
683 {"ldap server", P_STRING, P_GLOBAL, &Globals.szLdapServer, NULL, NULL, 0},
684 {"ldap port", P_INTEGER, P_GLOBAL, &Globals.ldap_port, NULL, NULL, 0},
685 {"ldap suffix", P_STRING, P_GLOBAL, &Globals.szLdapSuffix, NULL, NULL, 0},
686 {"ldap filter", P_STRING, P_GLOBAL, &Globals.szLdapFilter, NULL, NULL, 0},
687 {"ldap root", P_STRING, P_GLOBAL, &Globals.szLdapRoot, NULL, NULL, 0},
688 {"ldap root passwd", P_STRING, P_GLOBAL, &Globals.szLdapRootPassword,NULL, NULL, 0},
689 #endif /* WITH_LDAP */
692 {"Miscellaneous Options", P_SEP, P_SEPARATOR},
693 {"smbrun", P_STRING, P_GLOBAL, &Globals.szSmbrun, NULL, NULL, 0},
694 {"config file", P_STRING, P_GLOBAL, &Globals.szConfigFile, NULL, NULL, FLAG_HIDE},
695 {"preload", P_STRING, P_GLOBAL, &Globals.szAutoServices, NULL, NULL, 0},
696 {"auto services", P_STRING, P_GLOBAL, &Globals.szAutoServices, NULL, NULL, 0},
697 {"lock dir", P_STRING, P_GLOBAL, &Globals.szLockDir, NULL, NULL, 0},
698 {"lock directory", P_STRING, P_GLOBAL, &Globals.szLockDir, NULL, NULL, 0},
699 {"default service", P_STRING, P_GLOBAL, &Globals.szDefaultService, NULL, NULL, 0},
700 {"default", P_STRING, P_GLOBAL, &Globals.szDefaultService, NULL, NULL, 0},
701 {"message command", P_STRING, P_GLOBAL, &Globals.szMsgCommand, NULL, NULL, 0},
702 {"dfree command", P_STRING, P_GLOBAL, &Globals.szDfree, NULL, NULL, 0},
703 {"valid chars", P_STRING, P_GLOBAL, &Globals.szValidChars, handle_valid_chars, NULL, 0},
704 {"remote announce", P_STRING, P_GLOBAL, &Globals.szRemoteAnnounce, NULL, NULL, 0},
705 {"remote browse sync",P_STRING, P_GLOBAL, &Globals.szRemoteBrowseSync,NULL, NULL, 0},
706 {"socket address", P_STRING, P_GLOBAL, &Globals.szSocketAddress, NULL, NULL, 0},
707 {"homedir map", P_STRING, P_GLOBAL, &Globals.szNISHomeMapName, NULL, NULL, 0},
708 {"time offset", P_INTEGER, P_GLOBAL, &extra_time_offset, NULL, NULL, 0},
709 {"unix realname", P_BOOL, P_GLOBAL, &Globals.bUnixRealname, NULL, NULL, 0},
710 {"NIS homedir", P_BOOL, P_GLOBAL, &Globals.bNISHomeMap, NULL, NULL, 0},
711 {"-valid", P_BOOL, P_LOCAL, &sDefault.valid, NULL, NULL, FLAG_HIDE},
712 {"copy", P_STRING, P_LOCAL, &sDefault.szCopy, handle_copy, NULL, FLAG_HIDE},
713 {"include", P_STRING, P_LOCAL, &sDefault.szInclude, handle_include, NULL, FLAG_HIDE},
714 {"exec", P_STRING, P_LOCAL, &sDefault.szPreExec, NULL, NULL, 0},
715 {"preexec", P_STRING, P_LOCAL, &sDefault.szPreExec, NULL, NULL, 0},
716 {"postexec", P_STRING, P_LOCAL, &sDefault.szPostExec, NULL, NULL, 0},
717 {"root preexec", P_STRING, P_LOCAL, &sDefault.szRootPreExec, NULL, NULL, 0},
718 {"root postexec", P_STRING, P_LOCAL, &sDefault.szRootPostExec, NULL, NULL, 0},
719 {"available", P_BOOL, P_LOCAL, &sDefault.bAvailable, NULL, NULL, 0},
720 {"volume", P_STRING, P_LOCAL, &sDefault.volume, NULL, NULL, 0},
721 {"set directory", P_BOOLREV, P_LOCAL, &sDefault.bNo_set_dir, NULL, NULL, 0},
722 {"wide links", P_BOOL, P_LOCAL, &sDefault.bWidelinks, NULL, NULL, FLAG_GLOBAL},
723 {"follow symlinks", P_BOOL, P_LOCAL, &sDefault.bSymlinks, NULL, NULL, FLAG_GLOBAL},
724 {"dont descend", P_STRING, P_LOCAL, &sDefault.szDontdescend, NULL, NULL, 0},
725 {"magic script", P_STRING, P_LOCAL, &sDefault.szMagicScript, NULL, NULL, 0},
726 {"magic output", P_STRING, P_LOCAL, &sDefault.szMagicOutput, NULL, NULL, 0},
727 {"delete readonly", P_BOOL, P_LOCAL, &sDefault.bDeleteReadonly, NULL, NULL, FLAG_GLOBAL},
728 {"dos filetimes", P_BOOL, P_LOCAL, &sDefault.bDosFiletimes, NULL, NULL, FLAG_GLOBAL},
729 {"dos filetime resolution",P_BOOL,P_LOCAL,&sDefault.bDosFiletimeResolution, NULL, NULL, FLAG_GLOBAL},
731 {"fake directory create times", P_BOOL,P_LOCAL, &sDefault.bFakeDirCreateTimes, NULL, NULL, FLAG_GLOBAL},
732 {NULL, P_BOOL, P_NONE, NULL, NULL, NULL, 0}
737 /***************************************************************************
738 Initialise the global parameter structure.
739 ***************************************************************************/
740 static void init_globals(void)
742 static BOOL done_init = False;
748 bzero((void *)&Globals,sizeof(Globals));
750 for (i = 0; parm_table[i].label; i++)
751 if ((parm_table[i].type == P_STRING ||
752 parm_table[i].type == P_USTRING) &&
754 string_init(parm_table[i].ptr,"");
756 string_set(&sDefault.szGuestaccount, GUEST_ACCOUNT);
757 string_set(&sDefault.szPrinterDriver, "NULL");
763 DEBUG(3,("Initialising global parameters\n"));
765 string_set(&Globals.szSMBPasswdFile, SMB_PASSWD_FILE);
766 string_set(&Globals.szPasswdChat,"*old*password* %o\\n *new*password* %n\\n *new*password* %n\\n *changed*");
767 string_set(&Globals.szWorkGroup, WORKGROUP);
768 string_set(&Globals.szPasswdProgram, SMB_PASSWD);
769 string_set(&Globals.szPrintcapname, PRINTCAP_NAME);
770 string_set(&Globals.szDriverFile, DRIVERFILE);
771 string_set(&Globals.szLockDir, LOCKDIR);
772 string_set(&Globals.szRootdir, "/");
773 string_set(&Globals.szSmbrun, SMBRUN);
774 string_set(&Globals.szSocketAddress, "0.0.0.0");
775 pstrcpy(s, "Samba ");
777 string_set(&Globals.szServerString,s);
778 slprintf(s,sizeof(s)-1, "%d.%d", DEFAULT_MAJOR_VERSION, DEFAULT_MINOR_VERSION);
779 string_set(&Globals.szAnnounceVersion,s);
781 string_set(&Globals.szLogonDrive, "");
782 /* %N is the NIS auto.home server if -DAUTOHOME is used, else same as %L */
783 string_set(&Globals.szLogonHome, "\\\\%N\\%U");
784 string_set(&Globals.szLogonPath, "\\\\%N\\%U\\profile");
786 string_set(&Globals.szNameResolveOrder, "lmhosts host wins bcast");
788 Globals.bLoadPrinters = True;
789 Globals.bUseRhosts = False;
790 Globals.max_packet = 65535;
791 Globals.mangled_stack = 50;
792 Globals.max_xmit = 65535;
793 Globals.max_mux = 50; /* This is *needed* for profile support. */
794 Globals.lpqcachetime = 10;
795 Globals.pwordlevel = 0;
796 Globals.unamelevel = 0;
797 Globals.deadtime = 0;
798 Globals.max_log_size = 5000;
799 Globals.maxprotocol = PROTOCOL_NT1;
800 Globals.security = SEC_USER;
801 Globals.bEncryptPasswords = False;
802 Globals.bUpdateEncrypt = False;
803 Globals.bReadRaw = True;
804 Globals.bWriteRaw = True;
805 Globals.bReadPrediction = False;
806 Globals.bReadbmpx = True;
807 Globals.bNullPasswords = False;
808 Globals.bStripDot = False;
810 Globals.bSyslogOnly = False;
811 Globals.os_level = 0;
812 Globals.max_ttl = 60*60*24*3; /* 3 days default */
813 Globals.max_wins_ttl = 60*60*24*6; /* 6 days default */
814 Globals.min_wins_ttl = 60*60*6; /* 6 hours default */
815 Globals.machine_password_timeout = 60*60*24*7; /* 7 days default */
816 Globals.ReadSize = 16*1024;
817 Globals.lm_announce = 2; /* = Auto: send only if LM clients found */
818 Globals.lm_interval = 60;
819 Globals.shmem_size = SHMEM_SIZE;
820 Globals.announce_as = ANNOUNCE_AS_NT;
821 Globals.bUnixRealname = False;
822 #if (defined(HAVE_NETGROUP) && defined(WITH_AUTOMOUNT))
823 Globals.bNISHomeMap = False;
825 string_set(&Globals.szNISHomeMapName, "auto_home.org_dir");
827 string_set(&Globals.szNISHomeMapName, "auto.home");
830 Globals.client_code_page = DEFAULT_CLIENT_CODE_PAGE;
831 Globals.bTimeServer = False;
832 Globals.bBindInterfacesOnly = False;
833 Globals.bNetWkstaUserLogon = False; /* This is now set to false by default as
834 the code in password.c protects us from this bug. */
835 Globals.bUnixPasswdSync = False;
836 Globals.bPasswdChatDebug = False;
837 Globals.bOleLockingCompat = True;
840 /* default values for ldap */
841 string_set(&Globals.szLdapServer, "localhost");
842 Globals.ldap_port=389;
843 #endif /* WITH_LDAP */
846 Globals.sslVersion = SMB_SSL_V23;
847 Globals.sslHostsRequire = NULL;
848 Globals.sslHostsResign = NULL;
849 Globals.sslCaCertDir = NULL;
850 Globals.sslCaCertFile = NULL;
851 Globals.sslCert = NULL;
852 Globals.sslPrivKey = NULL;
853 Globals.sslClientCert = NULL;
854 Globals.sslClientPrivKey = NULL;
855 Globals.sslCiphers = NULL;
856 Globals.sslEnabled = False;
857 Globals.sslReqClientCert = False;
858 Globals.sslReqServerCert = False;
859 Globals.sslCompatibility = False;
860 #endif /* WITH_SSL */
862 /* these parameters are set to defaults that are more appropriate
863 for the increasing samba install base:
865 as a member of the workgroup, that will possibly become a
866 _local_ master browser (lm = True). this is opposed to a forced
867 local master browser startup (pm = True).
869 doesn't provide WINS server service by default (wsupp = False),
870 and doesn't provide domain master browser services by default, either.
874 Globals.bPreferredMaster = False;
875 Globals.bLocalMaster = True;
876 Globals.bDomainMaster = False;
877 Globals.bDomainLogons = False;
878 Globals.bBrowseList = True;
879 Globals.bWINSsupport = False;
880 Globals.bWINSproxy = False;
882 Globals.bDNSproxy = True;
885 * This must be done last as it checks the value in
889 interpret_coding_system(KANJI);
892 /***************************************************************************
893 check if a string is initialised and if not then initialise it
894 ***************************************************************************/
895 static void string_initial(char **s,char *v)
902 /***************************************************************************
903 Initialise the sDefault parameter structure.
904 ***************************************************************************/
905 static void init_locals(void)
907 /* choose defaults depending on the type of printing */
908 switch (sDefault.iPrinting)
914 string_initial(&sDefault.szLpqcommand,"lpq -P%p");
915 string_initial(&sDefault.szLprmcommand,"lprm -P%p %j");
916 string_initial(&sDefault.szPrintcommand,"lpr -r -P%p %s");
921 string_initial(&sDefault.szLpqcommand,"lpstat -o%p");
922 string_initial(&sDefault.szLprmcommand,"cancel %p-%j");
923 string_initial(&sDefault.szPrintcommand,"lp -c -d%p %s; rm %s");
925 string_initial(&sDefault.szLppausecommand,"lp -i %p-%j -H hold");
926 string_initial(&sDefault.szLpresumecommand,"lp -i %p-%j -H resume");
927 string_initial(&sDefault.szQueuepausecommand, "lpc stop %p");
928 string_initial(&sDefault.szQueueresumecommand, "lpc start %p");
930 string_initial(&sDefault.szQueuepausecommand, "disable %p");
931 string_initial(&sDefault.szQueueresumecommand, "enable %p");
936 string_initial(&sDefault.szLpqcommand,"lpq -P%p");
937 string_initial(&sDefault.szLprmcommand,"lprm -P%p %j");
938 string_initial(&sDefault.szPrintcommand,"lp -r -P%p %s");
942 string_initial(&sDefault.szLpqcommand,"qstat -l -d%p");
943 string_initial(&sDefault.szLprmcommand,"qstat -s -j%j -c");
944 string_initial(&sDefault.szPrintcommand,"lp -d%p -s %s; rm %s");
945 string_initial(&sDefault.szLppausecommand,"qstat -s -j%j -h");
946 string_initial(&sDefault.szLpresumecommand,"qstat -s -j%j -r");
953 /******************************************************************* a
954 convenience routine to grab string parameters into a rotating buffer,
955 and run standard_sub_basic on them. The buffers can be written to by
956 callers without affecting the source string.
957 ********************************************************************/
958 char *lp_string(char *s)
960 static char *bufs[10];
961 static int buflen[10];
962 static int next = -1;
965 int len = s?strlen(s):0;
976 len = MAX(len+100,sizeof(pstring)); /* the +100 is for some
979 if (buflen[next] != len) {
981 if (bufs[next]) free(bufs[next]);
982 bufs[next] = (char *)malloc(len);
984 DEBUG(0,("out of memory in lp_string()"));
989 ret = &bufs[next][0];
997 trim_string(ret, "\"", "\"");
999 standard_sub_basic(ret);
1005 In this section all the functions that are used to access the
1006 parameters from the rest of the program are defined
1009 #define FN_GLOBAL_STRING(fn_name,ptr) \
1010 char *fn_name(void) {return(lp_string(*(char **)(ptr) ? *(char **)(ptr) : ""));}
1011 #define FN_GLOBAL_BOOL(fn_name,ptr) \
1012 BOOL fn_name(void) {return(*(BOOL *)(ptr));}
1013 #define FN_GLOBAL_CHAR(fn_name,ptr) \
1014 char fn_name(void) {return(*(char *)(ptr));}
1015 #define FN_GLOBAL_INTEGER(fn_name,ptr) \
1016 int fn_name(void) {return(*(int *)(ptr));}
1018 #define FN_LOCAL_STRING(fn_name,val) \
1019 char *fn_name(int i) {return(lp_string((LP_SNUM_OK(i)&&pSERVICE(i)->val)?pSERVICE(i)->val : sDefault.val));}
1020 #define FN_LOCAL_BOOL(fn_name,val) \
1021 BOOL fn_name(int i) {return(LP_SNUM_OK(i)? pSERVICE(i)->val : sDefault.val);}
1022 #define FN_LOCAL_CHAR(fn_name,val) \
1023 char fn_name(int i) {return(LP_SNUM_OK(i)? pSERVICE(i)->val : sDefault.val);}
1024 #define FN_LOCAL_INTEGER(fn_name,val) \
1025 int fn_name(int i) {return(LP_SNUM_OK(i)? pSERVICE(i)->val : sDefault.val);}
1027 FN_GLOBAL_STRING(lp_logfile,&Globals.szLogFile)
1028 FN_GLOBAL_STRING(lp_smbrun,&Globals.szSmbrun)
1029 FN_GLOBAL_STRING(lp_configfile,&Globals.szConfigFile)
1030 FN_GLOBAL_STRING(lp_smb_passwd_file,&Globals.szSMBPasswdFile)
1031 FN_GLOBAL_STRING(lp_serverstring,&Globals.szServerString)
1032 FN_GLOBAL_STRING(lp_printcapname,&Globals.szPrintcapname)
1033 FN_GLOBAL_STRING(lp_lockdir,&Globals.szLockDir)
1034 FN_GLOBAL_STRING(lp_rootdir,&Globals.szRootdir)
1035 FN_GLOBAL_STRING(lp_defaultservice,&Globals.szDefaultService)
1036 FN_GLOBAL_STRING(lp_msg_command,&Globals.szMsgCommand)
1037 FN_GLOBAL_STRING(lp_dfree_command,&Globals.szDfree)
1038 FN_GLOBAL_STRING(lp_hosts_equiv,&Globals.szHostsEquiv)
1039 FN_GLOBAL_STRING(lp_auto_services,&Globals.szAutoServices)
1040 FN_GLOBAL_STRING(lp_passwd_program,&Globals.szPasswdProgram)
1041 FN_GLOBAL_STRING(lp_passwd_chat,&Globals.szPasswdChat)
1042 FN_GLOBAL_STRING(lp_passwordserver,&Globals.szPasswordServer)
1043 FN_GLOBAL_STRING(lp_name_resolve_order,&Globals.szNameResolveOrder)
1044 FN_GLOBAL_STRING(lp_workgroup,&Globals.szWorkGroup)
1045 FN_GLOBAL_STRING(lp_username_map,&Globals.szUsernameMap)
1046 FN_GLOBAL_STRING(lp_groupname_map,&Globals.szGroupnameMap)
1047 FN_GLOBAL_STRING(lp_character_set,&Globals.szCharacterSet)
1048 FN_GLOBAL_STRING(lp_logon_script,&Globals.szLogonScript)
1049 FN_GLOBAL_STRING(lp_logon_path,&Globals.szLogonPath)
1050 FN_GLOBAL_STRING(lp_logon_drive,&Globals.szLogonDrive)
1051 FN_GLOBAL_STRING(lp_logon_home,&Globals.szLogonHome)
1052 FN_GLOBAL_STRING(lp_remote_announce,&Globals.szRemoteAnnounce)
1053 FN_GLOBAL_STRING(lp_remote_browse_sync,&Globals.szRemoteBrowseSync)
1054 FN_GLOBAL_STRING(lp_wins_server,&Globals.szWINSserver)
1055 FN_GLOBAL_STRING(lp_interfaces,&Globals.szInterfaces)
1056 FN_GLOBAL_STRING(lp_socket_address,&Globals.szSocketAddress)
1057 FN_GLOBAL_STRING(lp_nis_home_map_name,&Globals.szNISHomeMapName)
1058 FN_GLOBAL_STRING(lp_announce_version,&Globals.szAnnounceVersion)
1059 FN_GLOBAL_STRING(lp_netbios_aliases,&Globals.szNetbiosAliases)
1060 FN_GLOBAL_STRING(lp_driverfile,&Globals.szDriverFile)
1062 FN_GLOBAL_STRING(lp_domain_sid,&Globals.szDomainSID)
1063 FN_GLOBAL_STRING(lp_domain_other_sids,&Globals.szDomainOtherSIDs)
1064 FN_GLOBAL_STRING(lp_domain_groups,&Globals.szDomainGroups)
1065 FN_GLOBAL_STRING(lp_domain_admin_group,&Globals.szDomainAdminGroup)
1066 FN_GLOBAL_STRING(lp_domain_guest_group,&Globals.szDomainGuestGroup)
1067 FN_GLOBAL_STRING(lp_domain_admin_users,&Globals.szDomainAdminUsers)
1068 FN_GLOBAL_STRING(lp_domain_guest_users,&Globals.szDomainGuestUsers)
1069 FN_GLOBAL_STRING(lp_domain_hostsallow,&Globals.szDomainHostsallow)
1070 FN_GLOBAL_STRING(lp_domain_hostsdeny,&Globals.szDomainHostsdeny)
1073 FN_GLOBAL_STRING(lp_ldap_server,&Globals.szLdapServer);
1074 FN_GLOBAL_STRING(lp_ldap_suffix,&Globals.szLdapSuffix);
1075 FN_GLOBAL_STRING(lp_ldap_filter,&Globals.szLdapFilter);
1076 FN_GLOBAL_STRING(lp_ldap_root,&Globals.szLdapRoot);
1077 FN_GLOBAL_STRING(lp_ldap_rootpasswd,&Globals.szLdapRootPassword);
1078 #endif /* WITH_LDAP */
1081 FN_GLOBAL_INTEGER(lp_ssl_version,&Globals.sslVersion);
1082 FN_GLOBAL_STRING(lp_ssl_hosts,&Globals.sslHostsRequire);
1083 FN_GLOBAL_STRING(lp_ssl_hosts_resign,&Globals.sslHostsResign);
1084 FN_GLOBAL_STRING(lp_ssl_cacertdir,&Globals.sslCaCertDir);
1085 FN_GLOBAL_STRING(lp_ssl_cacertfile,&Globals.sslCaCertFile);
1086 FN_GLOBAL_STRING(lp_ssl_cert,&Globals.sslCert);
1087 FN_GLOBAL_STRING(lp_ssl_privkey,&Globals.sslPrivKey);
1088 FN_GLOBAL_STRING(lp_ssl_client_cert,&Globals.sslClientCert);
1089 FN_GLOBAL_STRING(lp_ssl_client_privkey,&Globals.sslClientPrivKey);
1090 FN_GLOBAL_STRING(lp_ssl_ciphers,&Globals.sslCiphers);
1091 FN_GLOBAL_BOOL(lp_ssl_enabled,&Globals.sslEnabled);
1092 FN_GLOBAL_BOOL(lp_ssl_reqClientCert,&Globals.sslReqClientCert);
1093 FN_GLOBAL_BOOL(lp_ssl_reqServerCert,&Globals.sslReqServerCert);
1094 FN_GLOBAL_BOOL(lp_ssl_compatibility,&Globals.sslCompatibility);
1095 #endif /* WITH_SSL */
1097 FN_GLOBAL_BOOL(lp_dns_proxy,&Globals.bDNSproxy)
1098 FN_GLOBAL_BOOL(lp_wins_support,&Globals.bWINSsupport)
1099 FN_GLOBAL_BOOL(lp_we_are_a_wins_server,&Globals.bWINSsupport)
1100 FN_GLOBAL_BOOL(lp_wins_proxy,&Globals.bWINSproxy)
1101 FN_GLOBAL_BOOL(lp_local_master,&Globals.bLocalMaster)
1102 FN_GLOBAL_BOOL(lp_domain_controller,&Globals.bDomainController)
1103 FN_GLOBAL_BOOL(lp_domain_master,&Globals.bDomainMaster)
1104 FN_GLOBAL_BOOL(lp_domain_logons,&Globals.bDomainLogons)
1105 FN_GLOBAL_BOOL(lp_preferred_master,&Globals.bPreferredMaster)
1106 FN_GLOBAL_BOOL(lp_load_printers,&Globals.bLoadPrinters)
1107 FN_GLOBAL_BOOL(lp_use_rhosts,&Globals.bUseRhosts)
1108 FN_GLOBAL_BOOL(lp_getwdcache,&use_getwd_cache)
1109 FN_GLOBAL_BOOL(lp_readprediction,&Globals.bReadPrediction)
1110 FN_GLOBAL_BOOL(lp_readbmpx,&Globals.bReadbmpx)
1111 FN_GLOBAL_BOOL(lp_readraw,&Globals.bReadRaw)
1112 FN_GLOBAL_BOOL(lp_writeraw,&Globals.bWriteRaw)
1113 FN_GLOBAL_BOOL(lp_null_passwords,&Globals.bNullPasswords)
1114 FN_GLOBAL_BOOL(lp_strip_dot,&Globals.bStripDot)
1115 FN_GLOBAL_BOOL(lp_encrypted_passwords,&Globals.bEncryptPasswords)
1116 FN_GLOBAL_BOOL(lp_update_encrypted,&Globals.bUpdateEncrypt)
1117 FN_GLOBAL_BOOL(lp_syslog_only,&Globals.bSyslogOnly)
1118 FN_GLOBAL_BOOL(lp_browse_list,&Globals.bBrowseList)
1119 FN_GLOBAL_BOOL(lp_unix_realname,&Globals.bUnixRealname)
1120 FN_GLOBAL_BOOL(lp_nis_home_map,&Globals.bNISHomeMap)
1121 FN_GLOBAL_BOOL(lp_time_server,&Globals.bTimeServer)
1122 FN_GLOBAL_BOOL(lp_bind_interfaces_only,&Globals.bBindInterfacesOnly)
1123 FN_GLOBAL_BOOL(lp_net_wksta_user_logon,&Globals.bNetWkstaUserLogon)
1124 FN_GLOBAL_BOOL(lp_unix_password_sync,&Globals.bUnixPasswdSync)
1125 FN_GLOBAL_BOOL(lp_passwd_chat_debug,&Globals.bPasswdChatDebug)
1126 FN_GLOBAL_BOOL(lp_ole_locking_compat,&Globals.bOleLockingCompat)
1128 FN_GLOBAL_INTEGER(lp_os_level,&Globals.os_level)
1129 FN_GLOBAL_INTEGER(lp_max_ttl,&Globals.max_ttl)
1130 FN_GLOBAL_INTEGER(lp_max_wins_ttl,&Globals.max_wins_ttl)
1131 FN_GLOBAL_INTEGER(lp_min_wins_ttl,&Globals.max_wins_ttl)
1132 FN_GLOBAL_INTEGER(lp_max_log_size,&Globals.max_log_size)
1133 FN_GLOBAL_INTEGER(lp_mangledstack,&Globals.mangled_stack)
1134 FN_GLOBAL_INTEGER(lp_maxxmit,&Globals.max_xmit)
1135 FN_GLOBAL_INTEGER(lp_maxmux,&Globals.max_mux)
1136 FN_GLOBAL_INTEGER(lp_maxpacket,&Globals.max_packet)
1137 FN_GLOBAL_INTEGER(lp_keepalive,&keepalive)
1138 FN_GLOBAL_INTEGER(lp_passwordlevel,&Globals.pwordlevel)
1139 FN_GLOBAL_INTEGER(lp_usernamelevel,&Globals.unamelevel)
1140 FN_GLOBAL_INTEGER(lp_readsize,&Globals.ReadSize)
1141 FN_GLOBAL_INTEGER(lp_shmem_size,&Globals.shmem_size)
1142 FN_GLOBAL_INTEGER(lp_deadtime,&Globals.deadtime)
1143 FN_GLOBAL_INTEGER(lp_maxprotocol,&Globals.maxprotocol)
1144 FN_GLOBAL_INTEGER(lp_security,&Globals.security)
1145 FN_GLOBAL_INTEGER(lp_maxdisksize,&Globals.maxdisksize)
1146 FN_GLOBAL_INTEGER(lp_lpqcachetime,&Globals.lpqcachetime)
1147 FN_GLOBAL_INTEGER(lp_syslog,&Globals.syslog)
1148 FN_GLOBAL_INTEGER(lp_client_code_page,&Globals.client_code_page)
1149 FN_GLOBAL_INTEGER(lp_announce_as,&Globals.announce_as)
1150 FN_GLOBAL_INTEGER(lp_lm_announce,&Globals.lm_announce)
1151 FN_GLOBAL_INTEGER(lp_lm_interval,&Globals.lm_interval)
1152 FN_GLOBAL_INTEGER(lp_machine_password_timeout,&Globals.machine_password_timeout)
1155 FN_GLOBAL_INTEGER(lp_ldap_port,&Globals.ldap_port)
1156 #endif /* WITH_LDAP */
1158 FN_LOCAL_STRING(lp_preexec,szPreExec)
1159 FN_LOCAL_STRING(lp_postexec,szPostExec)
1160 FN_LOCAL_STRING(lp_rootpreexec,szRootPreExec)
1161 FN_LOCAL_STRING(lp_rootpostexec,szRootPostExec)
1162 FN_LOCAL_STRING(lp_servicename,szService)
1163 FN_LOCAL_STRING(lp_pathname,szPath)
1164 FN_LOCAL_STRING(lp_dontdescend,szDontdescend)
1165 FN_LOCAL_STRING(lp_username,szUsername)
1166 FN_LOCAL_STRING(lp_guestaccount,szGuestaccount)
1167 FN_LOCAL_STRING(lp_invalid_users,szInvalidUsers)
1168 FN_LOCAL_STRING(lp_valid_users,szValidUsers)
1169 FN_LOCAL_STRING(lp_admin_users,szAdminUsers)
1170 FN_LOCAL_STRING(lp_printcommand,szPrintcommand)
1171 FN_LOCAL_STRING(lp_lpqcommand,szLpqcommand)
1172 FN_LOCAL_STRING(lp_lprmcommand,szLprmcommand)
1173 FN_LOCAL_STRING(lp_lppausecommand,szLppausecommand)
1174 FN_LOCAL_STRING(lp_lpresumecommand,szLpresumecommand)
1175 FN_LOCAL_STRING(lp_queuepausecommand,szQueuepausecommand)
1176 FN_LOCAL_STRING(lp_queueresumecommand,szQueueresumecommand)
1177 FN_LOCAL_STRING(lp_printername,szPrintername)
1178 FN_LOCAL_STRING(lp_printerdriver,szPrinterDriver)
1179 FN_LOCAL_STRING(lp_hostsallow,szHostsallow)
1180 FN_LOCAL_STRING(lp_hostsdeny,szHostsdeny)
1181 FN_LOCAL_STRING(lp_magicscript,szMagicScript)
1182 FN_LOCAL_STRING(lp_magicoutput,szMagicOutput)
1183 FN_LOCAL_STRING(lp_comment,comment)
1184 FN_LOCAL_STRING(lp_force_user,force_user)
1185 FN_LOCAL_STRING(lp_force_group,force_group)
1186 FN_LOCAL_STRING(lp_readlist,readlist)
1187 FN_LOCAL_STRING(lp_writelist,writelist)
1188 FN_LOCAL_STRING(lp_volume,volume)
1189 FN_LOCAL_STRING(lp_mangled_map,szMangledMap)
1190 FN_LOCAL_STRING(lp_veto_files,szVetoFiles)
1191 FN_LOCAL_STRING(lp_hide_files,szHideFiles)
1192 FN_LOCAL_STRING(lp_veto_oplocks,szVetoOplockFiles)
1193 FN_LOCAL_STRING(lp_driverlocation,szPrinterDriverLocation)
1195 FN_LOCAL_BOOL(lp_alternate_permissions,bAlternatePerm)
1196 FN_LOCAL_BOOL(lp_revalidate,bRevalidate)
1197 FN_LOCAL_BOOL(lp_casesensitive,bCaseSensitive)
1198 FN_LOCAL_BOOL(lp_preservecase,bCasePreserve)
1199 FN_LOCAL_BOOL(lp_shortpreservecase,bShortCasePreserve)
1200 FN_LOCAL_BOOL(lp_casemangle,bCaseMangle)
1201 FN_LOCAL_BOOL(lp_status,status)
1202 FN_LOCAL_BOOL(lp_hide_dot_files,bHideDotFiles)
1203 FN_LOCAL_BOOL(lp_browseable,bBrowseable)
1204 FN_LOCAL_BOOL(lp_readonly,bRead_only)
1205 FN_LOCAL_BOOL(lp_no_set_dir,bNo_set_dir)
1206 FN_LOCAL_BOOL(lp_guest_ok,bGuest_ok)
1207 FN_LOCAL_BOOL(lp_guest_only,bGuest_only)
1208 FN_LOCAL_BOOL(lp_print_ok,bPrint_ok)
1209 FN_LOCAL_BOOL(lp_postscript,bPostscript)
1210 FN_LOCAL_BOOL(lp_map_hidden,bMap_hidden)
1211 FN_LOCAL_BOOL(lp_map_archive,bMap_archive)
1212 FN_LOCAL_BOOL(lp_locking,bLocking)
1213 FN_LOCAL_BOOL(lp_strict_locking,bStrictLocking)
1214 FN_LOCAL_BOOL(lp_share_modes,bShareModes)
1215 FN_LOCAL_BOOL(lp_oplocks,bOpLocks)
1216 FN_LOCAL_BOOL(lp_onlyuser,bOnlyUser)
1217 FN_LOCAL_BOOL(lp_manglednames,bMangledNames)
1218 FN_LOCAL_BOOL(lp_widelinks,bWidelinks)
1219 FN_LOCAL_BOOL(lp_symlinks,bSymlinks)
1220 FN_LOCAL_BOOL(lp_syncalways,bSyncAlways)
1221 FN_LOCAL_BOOL(lp_strict_sync,bStrictSync)
1222 FN_LOCAL_BOOL(lp_map_system,bMap_system)
1223 FN_LOCAL_BOOL(lp_delete_readonly,bDeleteReadonly)
1224 FN_LOCAL_BOOL(lp_fake_oplocks,bFakeOplocks)
1225 FN_LOCAL_BOOL(lp_recursive_veto_delete,bDeleteVetoFiles)
1226 FN_LOCAL_BOOL(lp_dos_filetimes,bDosFiletimes)
1227 FN_LOCAL_BOOL(lp_dos_filetime_resolution,bDosFiletimeResolution)
1228 FN_LOCAL_BOOL(lp_fake_dir_create_times,bFakeDirCreateTimes)
1230 FN_LOCAL_INTEGER(lp_create_mode,iCreate_mask)
1231 FN_LOCAL_INTEGER(lp_force_create_mode,iCreate_force_mode)
1232 FN_LOCAL_INTEGER(lp_dir_mode,iDir_mask)
1233 FN_LOCAL_INTEGER(lp_force_dir_mode,iDir_force_mode)
1234 FN_LOCAL_INTEGER(lp_max_connections,iMaxConnections)
1235 FN_LOCAL_INTEGER(lp_defaultcase,iDefaultCase)
1236 FN_LOCAL_INTEGER(lp_minprintspace,iMinPrintSpace)
1237 FN_LOCAL_INTEGER(lp_printing,iPrinting)
1239 FN_LOCAL_CHAR(lp_magicchar,magic_char)
1243 /* local prototypes */
1244 static int strwicmp( char *psz1, char *psz2 );
1245 static int map_parameter( char *pszParmName);
1246 static BOOL set_boolean( BOOL *pb, char *pszParmValue );
1247 static int getservicebyname(char *pszServiceName, service *pserviceDest);
1248 static void copy_service( service *pserviceDest,
1249 service *pserviceSource,
1250 BOOL *pcopymapDest );
1251 static BOOL service_ok(int iService);
1252 static BOOL do_parameter(char *pszParmName, char *pszParmValue);
1253 static BOOL do_section(char *pszSectionName);
1254 static void init_copymap(service *pservice);
1257 /***************************************************************************
1258 initialise a service to the defaults
1259 ***************************************************************************/
1260 static void init_service(service *pservice)
1262 bzero((char *)pservice,sizeof(service));
1263 copy_service(pservice,&sDefault,NULL);
1267 /***************************************************************************
1268 free the dynamically allocated parts of a service struct
1269 ***************************************************************************/
1270 static void free_service(service *pservice)
1276 if(pservice->szService)
1277 DEBUG(5,("free_service: Freeing service %s\n", pservice->szService));
1279 string_free(&pservice->szService);
1280 if (pservice->copymap)
1282 free(pservice->copymap);
1283 pservice->copymap = NULL;
1286 for (i=0;parm_table[i].label;i++)
1287 if ((parm_table[i].type == P_STRING ||
1288 parm_table[i].type == P_USTRING) &&
1289 parm_table[i].class == P_LOCAL)
1290 string_free((char **)(((char *)pservice) + PTR_DIFF(parm_table[i].ptr,&sDefault)));
1293 /***************************************************************************
1294 add a new service to the services array initialising it with the given
1296 ***************************************************************************/
1297 static int add_a_service(service *pservice, char *name)
1301 int num_to_alloc = iNumServices+1;
1303 tservice = *pservice;
1305 /* it might already exist */
1308 i = getservicebyname(name,NULL);
1313 /* find an invalid one */
1314 for (i=0;i<iNumServices;i++)
1315 if (!pSERVICE(i)->valid)
1318 /* if not, then create one */
1319 if (i == iNumServices)
1321 ServicePtrs = (service **)Realloc(ServicePtrs,sizeof(service *)*num_to_alloc);
1323 pSERVICE(iNumServices) = (service *)malloc(sizeof(service));
1325 if (!ServicePtrs || !pSERVICE(iNumServices))
1331 free_service(pSERVICE(i));
1333 pSERVICE(i)->valid = True;
1335 init_service(pSERVICE(i));
1336 copy_service(pSERVICE(i),&tservice,NULL);
1338 string_set(&iSERVICE(i).szService,name);
1343 /***************************************************************************
1344 add a new home service, with the specified home directory, defaults coming
1346 ***************************************************************************/
1347 BOOL lp_add_home(char *pszHomename, int iDefaultService, char *pszHomedir)
1349 int i = add_a_service(pSERVICE(iDefaultService),pszHomename);
1354 if (!(*(iSERVICE(i).szPath)) || strequal(iSERVICE(i).szPath,lp_pathname(-1)))
1355 string_set(&iSERVICE(i).szPath,pszHomedir);
1356 if (!(*(iSERVICE(i).comment)))
1359 slprintf(comment,sizeof(comment)-1,
1360 "Home directory of %s",pszHomename);
1361 string_set(&iSERVICE(i).comment,comment);
1363 iSERVICE(i).bAvailable = sDefault.bAvailable;
1364 iSERVICE(i).bBrowseable = sDefault.bBrowseable;
1366 DEBUG(3,("adding home directory %s at %s\n", pszHomename, pszHomedir));
1371 /***************************************************************************
1372 add a new service, based on an old one
1373 ***************************************************************************/
1374 int lp_add_service(char *pszService, int iDefaultService)
1376 return(add_a_service(pSERVICE(iDefaultService),pszService));
1380 /***************************************************************************
1382 ***************************************************************************/
1383 static BOOL lp_add_ipc(void)
1386 int i = add_a_service(&sDefault,"IPC$");
1391 slprintf(comment,sizeof(comment)-1,
1392 "IPC Service (%s)", Globals.szServerString );
1394 string_set(&iSERVICE(i).szPath,tmpdir());
1395 string_set(&iSERVICE(i).szUsername,"");
1396 string_set(&iSERVICE(i).comment,comment);
1397 iSERVICE(i).status = False;
1398 iSERVICE(i).iMaxConnections = 0;
1399 iSERVICE(i).bAvailable = True;
1400 iSERVICE(i).bRead_only = True;
1401 iSERVICE(i).bGuest_only = False;
1402 iSERVICE(i).bGuest_ok = True;
1403 iSERVICE(i).bPrint_ok = False;
1404 iSERVICE(i).bBrowseable = sDefault.bBrowseable;
1406 DEBUG(3,("adding IPC service\n"));
1412 /***************************************************************************
1413 add a new printer service, with defaults coming from service iFrom
1414 ***************************************************************************/
1415 BOOL lp_add_printer(char *pszPrintername, int iDefaultService)
1417 char *comment = "From Printcap";
1418 int i = add_a_service(pSERVICE(iDefaultService),pszPrintername);
1423 /* note that we do NOT default the availability flag to True - */
1424 /* we take it from the default service passed. This allows all */
1425 /* dynamic printers to be disabled by disabling the [printers] */
1426 /* entry (if/when the 'available' keyword is implemented!). */
1428 /* the printer name is set to the service name. */
1429 string_set(&iSERVICE(i).szPrintername,pszPrintername);
1430 string_set(&iSERVICE(i).comment,comment);
1431 iSERVICE(i).bBrowseable = sDefault.bBrowseable;
1432 /* Printers cannot be read_only. */
1433 iSERVICE(i).bRead_only = False;
1434 /* No share modes on printer services. */
1435 iSERVICE(i).bShareModes = False;
1436 /* No oplocks on printer services. */
1437 iSERVICE(i).bOpLocks = False;
1438 /* Printer services must be printable. */
1439 iSERVICE(i).bPrint_ok = True;
1441 DEBUG(3,("adding printer service %s\n",pszPrintername));
1447 /***************************************************************************
1448 Do a case-insensitive, whitespace-ignoring string compare.
1449 ***************************************************************************/
1450 static int strwicmp(char *psz1, char *psz2)
1452 /* if BOTH strings are NULL, return TRUE, if ONE is NULL return */
1453 /* appropriate value. */
1463 /* sync the strings on first non-whitespace */
1466 while (isspace(*psz1))
1468 while (isspace(*psz2))
1470 if (toupper(*psz1) != toupper(*psz2) || *psz1 == '\0' || *psz2 == '\0')
1475 return (*psz1 - *psz2);
1478 /***************************************************************************
1479 Map a parameter's string representation to something we can use.
1480 Returns False if the parameter string is not recognised, else TRUE.
1481 ***************************************************************************/
1482 static int map_parameter(char *pszParmName)
1486 if (*pszParmName == '-')
1489 for (iIndex = 0; parm_table[iIndex].label; iIndex++)
1490 if (strwicmp(parm_table[iIndex].label, pszParmName) == 0)
1493 DEBUG(0,( "Unknown parameter encountered: \"%s\"\n", pszParmName));
1498 /***************************************************************************
1499 Set a boolean variable from the text value stored in the passed string.
1500 Returns True in success, False if the passed string does not correctly
1501 represent a boolean.
1502 ***************************************************************************/
1503 static BOOL set_boolean(BOOL *pb, char *pszParmValue)
1508 if (strwicmp(pszParmValue, "yes") == 0 ||
1509 strwicmp(pszParmValue, "true") == 0 ||
1510 strwicmp(pszParmValue, "1") == 0)
1513 if (strwicmp(pszParmValue, "no") == 0 ||
1514 strwicmp(pszParmValue, "False") == 0 ||
1515 strwicmp(pszParmValue, "0") == 0)
1519 DEBUG(0,( "Badly formed boolean in configuration file: \"%s\".\n",
1526 /***************************************************************************
1527 Find a service by name. Otherwise works like get_service.
1528 ***************************************************************************/
1529 static int getservicebyname(char *pszServiceName, service *pserviceDest)
1533 for (iService = iNumServices - 1; iService >= 0; iService--)
1534 if (VALID(iService) &&
1535 strwicmp(iSERVICE(iService).szService, pszServiceName) == 0)
1537 if (pserviceDest != NULL)
1538 copy_service(pserviceDest, pSERVICE(iService), NULL);
1547 /***************************************************************************
1548 Copy a service structure to another
1550 If pcopymapDest is NULL then copy all fields
1551 ***************************************************************************/
1552 static void copy_service(service *pserviceDest,
1553 service *pserviceSource,
1557 BOOL bcopyall = (pcopymapDest == NULL);
1559 for (i=0;parm_table[i].label;i++)
1560 if (parm_table[i].ptr && parm_table[i].class == P_LOCAL &&
1561 (bcopyall || pcopymapDest[i]))
1563 void *def_ptr = parm_table[i].ptr;
1565 ((char *)pserviceSource) + PTR_DIFF(def_ptr,&sDefault);
1567 ((char *)pserviceDest) + PTR_DIFF(def_ptr,&sDefault);
1569 switch (parm_table[i].type)
1573 *(BOOL *)dest_ptr = *(BOOL *)src_ptr;
1579 *(int *)dest_ptr = *(int *)src_ptr;
1583 *(char *)dest_ptr = *(char *)src_ptr;
1587 string_set(dest_ptr,*(char **)src_ptr);
1591 string_set(dest_ptr,*(char **)src_ptr);
1592 strupper(*(char **)dest_ptr);
1601 init_copymap(pserviceDest);
1602 if (pserviceSource->copymap)
1603 memcpy((void *)pserviceDest->copymap,
1604 (void *)pserviceSource->copymap,sizeof(BOOL)*NUMPARAMETERS);
1608 /***************************************************************************
1609 Check a service for consistency. Return False if the service is in any way
1610 incomplete or faulty, else True.
1611 ***************************************************************************/
1612 static BOOL service_ok(int iService)
1617 if (iSERVICE(iService).szService[0] == '\0')
1619 DEBUG(0,( "The following message indicates an internal error:\n"));
1620 DEBUG(0,( "No service name in service entry.\n"));
1624 /* The [printers] entry MUST be printable. I'm all for flexibility, but */
1625 /* I can't see why you'd want a non-printable printer service... */
1626 if (strwicmp(iSERVICE(iService).szService,PRINTERS_NAME) == 0)
1627 if (!iSERVICE(iService).bPrint_ok)
1629 DEBUG(0,( "WARNING: [%s] service MUST be printable!\n",
1630 iSERVICE(iService).szService));
1631 iSERVICE(iService).bPrint_ok = True;
1634 if (iSERVICE(iService).szPath[0] == '\0' &&
1635 strwicmp(iSERVICE(iService).szService,HOMES_NAME) != 0)
1637 DEBUG(0,("No path in service %s - using %s\n",iSERVICE(iService).szService,tmpdir()));
1638 string_set(&iSERVICE(iService).szPath,tmpdir());
1641 /* If a service is flagged unavailable, log the fact at level 0. */
1642 if (!iSERVICE(iService).bAvailable)
1643 DEBUG(1,( "NOTE: Service %s is flagged unavailable.\n",
1644 iSERVICE(iService).szService));
1649 static struct file_lists {
1650 struct file_lists *next;
1653 } *file_lists = NULL;
1655 /*******************************************************************
1656 keep a linked list of all config files so we know when one has changed
1657 it's date and needs to be reloaded
1658 ********************************************************************/
1659 static void add_to_file_list(char *fname)
1661 struct file_lists *f=file_lists;
1664 if (f->name && !strcmp(f->name,fname)) break;
1669 f = (struct file_lists *)malloc(sizeof(file_lists[0]));
1671 f->next = file_lists;
1672 f->name = strdup(fname);
1683 standard_sub_basic(n2);
1684 f->modtime = file_modtime(n2);
1689 /*******************************************************************
1690 check if a config file has changed date
1691 ********************************************************************/
1692 BOOL lp_file_list_changed(void)
1694 struct file_lists *f = file_lists;
1695 DEBUG(6,("lp_file_list_changed()\n"));
1702 pstrcpy(n2,f->name);
1703 standard_sub_basic(n2);
1705 DEBUG(6,("file %s -> %s last mod_time: %s\n",
1706 f->name, n2, ctime(&f->modtime)));
1708 mod_time = file_modtime(n2);
1710 if (f->modtime != mod_time) {
1711 DEBUG(6,("file %s modified: %s\n", n2, ctime(&mod_time)));
1712 f->modtime = mod_time;
1720 /***************************************************************************
1721 handle the interpretation of the coding system parameter
1722 *************************************************************************/
1723 static BOOL handle_coding_system(char *pszParmValue,char **ptr)
1725 string_set(ptr,pszParmValue);
1726 interpret_coding_system(pszParmValue);
1730 /***************************************************************************
1731 handle the interpretation of the character set system parameter
1732 ***************************************************************************/
1733 static BOOL handle_character_set(char *pszParmValue,char **ptr)
1735 string_set(ptr,pszParmValue);
1736 interpret_character_set(pszParmValue);
1741 /***************************************************************************
1742 handle the valid chars lines
1743 ***************************************************************************/
1744 static BOOL handle_valid_chars(char *pszParmValue,char **ptr)
1746 string_set(ptr,pszParmValue);
1748 /* A dependency here is that the parameter client code page must be
1749 set before this is called - as calling codepage_initialise()
1750 would overwrite the valid char lines.
1752 codepage_initialise(lp_client_code_page());
1754 add_char_string(pszParmValue);
1759 /***************************************************************************
1760 handle the include operation
1761 ***************************************************************************/
1762 static BOOL handle_include(char *pszParmValue,char **ptr)
1765 pstrcpy(fname,pszParmValue);
1767 add_to_file_list(fname);
1769 standard_sub_basic(fname);
1771 string_set(ptr,fname);
1773 if (file_exist(fname,NULL))
1774 return(pm_process(fname, do_section, do_parameter));
1776 DEBUG(2,("Can't find include file %s\n",fname));
1782 /***************************************************************************
1783 handle the interpretation of the copy parameter
1784 ***************************************************************************/
1785 static BOOL handle_copy(char *pszParmValue,char **ptr)
1789 service serviceTemp;
1791 string_set(ptr,pszParmValue);
1793 init_service(&serviceTemp);
1797 DEBUG(3,("Copying service from service %s\n",pszParmValue));
1799 if ((iTemp = getservicebyname(pszParmValue, &serviceTemp)) >= 0)
1801 if (iTemp == iServiceIndex)
1803 DEBUG(0,("Can't copy service %s - unable to copy self!\n",
1808 copy_service(pSERVICE(iServiceIndex),
1810 iSERVICE(iServiceIndex).copymap);
1816 DEBUG(0,( "Unable to copy service - source not found: %s\n",
1821 free_service(&serviceTemp);
1826 /***************************************************************************
1827 initialise a copymap
1828 ***************************************************************************/
1829 static void init_copymap(service *pservice)
1832 if (pservice->copymap) free(pservice->copymap);
1833 pservice->copymap = (BOOL *)malloc(sizeof(BOOL)*NUMPARAMETERS);
1834 if (!pservice->copymap)
1835 DEBUG(0,("Couldn't allocate copymap!! (size %d)\n",NUMPARAMETERS));
1837 for (i=0;i<NUMPARAMETERS;i++)
1838 pservice->copymap[i] = True;
1842 /***************************************************************************
1843 return the local pointer to a parameter given the service number and the
1844 pointer into the default structure
1845 ***************************************************************************/
1846 void *lp_local_ptr(int snum, void *ptr)
1848 return (void *)(((char *)pSERVICE(snum)) + PTR_DIFF(ptr,&sDefault));
1851 /***************************************************************************
1852 Process a parameter for a particular service number. If snum < 0
1853 then assume we are in the globals
1854 ***************************************************************************/
1855 BOOL lp_do_parameter(int snum, char *pszParmName, char *pszParmValue)
1858 void *parm_ptr=NULL; /* where we are going to store the result */
1861 parmnum = map_parameter(pszParmName);
1865 DEBUG(0,( "Ignoring unknown parameter \"%s\"\n", pszParmName));
1869 def_ptr = parm_table[parmnum].ptr;
1871 /* we might point at a service, the default service or a global */
1875 if (parm_table[parmnum].class == P_GLOBAL) {
1876 DEBUG(0,( "Global parameter %s found in service section!\n",pszParmName));
1879 parm_ptr = ((char *)pSERVICE(snum)) + PTR_DIFF(def_ptr,&sDefault);
1883 if (!iSERVICE(snum).copymap)
1884 init_copymap(pSERVICE(snum));
1886 /* this handles the aliases - set the copymap for other entries with
1887 the same data pointer */
1888 for (i=0;parm_table[i].label;i++)
1889 if (parm_table[i].ptr == parm_table[parmnum].ptr)
1890 iSERVICE(snum).copymap[i] = False;
1893 /* if it is a special case then go ahead */
1894 if (parm_table[parmnum].special) {
1895 parm_table[parmnum].special(pszParmValue,(char **)parm_ptr);
1899 /* now switch on the type of variable it is */
1900 switch (parm_table[parmnum].type)
1903 set_boolean(parm_ptr,pszParmValue);
1907 set_boolean(parm_ptr,pszParmValue);
1908 *(BOOL *)parm_ptr = ! *(BOOL *)parm_ptr;
1912 *(int *)parm_ptr = atoi(pszParmValue);
1916 *(char *)parm_ptr = *pszParmValue;
1920 sscanf(pszParmValue,"%o",(int *)parm_ptr);
1924 string_set(parm_ptr,pszParmValue);
1928 string_set(parm_ptr,pszParmValue);
1929 strupper(*(char **)parm_ptr);
1933 pstrcpy((char *)parm_ptr,pszParmValue);
1937 pstrcpy((char *)parm_ptr,pszParmValue);
1938 strupper((char *)parm_ptr);
1942 for (i=0;parm_table[parmnum].enum_list[i].name;i++) {
1943 if (strequal(pszParmValue, parm_table[parmnum].enum_list[i].name)) {
1944 *(int *)parm_ptr = parm_table[parmnum].enum_list[i].value;
1956 /***************************************************************************
1957 Process a parameter.
1958 ***************************************************************************/
1959 static BOOL do_parameter(char *pszParmName, char *pszParmValue)
1961 if (!bInGlobalSection && bGlobalOnly) return(True);
1963 DEBUG(3,("doing parameter %s = %s\n",pszParmName,pszParmValue));
1965 return lp_do_parameter(bInGlobalSection?-2:iServiceIndex, pszParmName, pszParmValue);
1969 /***************************************************************************
1970 print a parameter of the specified type
1971 ***************************************************************************/
1972 static void print_parameter(struct parm_struct *p,void *ptr, FILE *f)
1977 for (i=0;p->enum_list[i].name;i++) {
1978 if (*(int *)ptr == p->enum_list[i].value) {
1979 fprintf(f,"%s",p->enum_list[i].name);
1986 fprintf(f,"%s",BOOLSTR(*(BOOL *)ptr));
1990 fprintf(f,"%s",BOOLSTR(! *(BOOL *)ptr));
1994 fprintf(f,"%d",*(int *)ptr);
1998 fprintf(f,"%c",*(char *)ptr);
2002 fprintf(f,"0%o",*(int *)ptr);
2008 fprintf(f,"%s",(char *)ptr);
2014 fprintf(f,"%s",*(char **)ptr);
2022 /***************************************************************************
2023 check if two parameters are equal
2024 ***************************************************************************/
2025 static BOOL equal_parameter(parm_type type,void *ptr1,void *ptr2)
2031 return(*((BOOL *)ptr1) == *((BOOL *)ptr2));
2036 return(*((int *)ptr1) == *((int *)ptr2));
2039 return(*((char *)ptr1) == *((char *)ptr2));
2044 char *p1 = (char *)ptr1, *p2 = (char *)ptr2;
2045 if (p1 && !*p1) p1 = NULL;
2046 if (p2 && !*p2) p2 = NULL;
2047 return(p1==p2 || strequal(p1,p2));
2052 char *p1 = *(char **)ptr1, *p2 = *(char **)ptr2;
2053 if (p1 && !*p1) p1 = NULL;
2054 if (p2 && !*p2) p2 = NULL;
2055 return(p1==p2 || strequal(p1,p2));
2063 /***************************************************************************
2064 Process a new section (service). At this stage all sections are services.
2065 Later we'll have special sections that permit server parameters to be set.
2066 Returns True on success, False on failure.
2067 ***************************************************************************/
2068 static BOOL do_section(char *pszSectionName)
2071 BOOL isglobal = ((strwicmp(pszSectionName, GLOBAL_NAME) == 0) ||
2072 (strwicmp(pszSectionName, GLOBAL_NAME2) == 0));
2075 /* if we were in a global section then do the local inits */
2076 if (bInGlobalSection && !isglobal)
2079 /* if we've just struck a global section, note the fact. */
2080 bInGlobalSection = isglobal;
2082 /* check for multiple global sections */
2083 if (bInGlobalSection)
2085 DEBUG(3,( "Processing section \"[%s]\"\n", pszSectionName));
2089 if (!bInGlobalSection && bGlobalOnly) return(True);
2091 /* if we have a current service, tidy it up before moving on */
2094 if (iServiceIndex >= 0)
2095 bRetval = service_ok(iServiceIndex);
2097 /* if all is still well, move to the next record in the services array */
2100 /* We put this here to avoid an odd message order if messages are */
2101 /* issued by the post-processing of a previous section. */
2102 DEBUG(2,( "Processing section \"[%s]\"\n", pszSectionName));
2104 if ((iServiceIndex=add_a_service(&sDefault,pszSectionName)) < 0)
2106 DEBUG(0,("Failed to add a new service\n"));
2115 /***************************************************************************
2116 determine if a partcular base parameter is currently set to the default value.
2117 ***************************************************************************/
2118 static BOOL is_default(int i)
2120 if (!defaults_saved) return False;
2121 switch (parm_table[i].type) {
2124 return strequal(parm_table[i].def.svalue,*(char **)parm_table[i].ptr);
2127 return strequal(parm_table[i].def.svalue,(char *)parm_table[i].ptr);
2130 return parm_table[i].def.bvalue == *(BOOL *)parm_table[i].ptr;
2132 return parm_table[i].def.cvalue == *(char *)parm_table[i].ptr;
2136 return parm_table[i].def.ivalue == *(int *)parm_table[i].ptr;
2144 /***************************************************************************
2145 Display the contents of the global structure.
2146 ***************************************************************************/
2147 static void dump_globals(FILE *f)
2150 fprintf(f, "# Global parameters\n");
2152 for (i=0;parm_table[i].label;i++)
2153 if (parm_table[i].class == P_GLOBAL &&
2154 parm_table[i].ptr &&
2155 (i == 0 || (parm_table[i].ptr != parm_table[i-1].ptr))) {
2156 if (defaults_saved && is_default(i)) continue;
2157 fprintf(f,"\t%s = ",parm_table[i].label);
2158 print_parameter(&parm_table[i],parm_table[i].ptr, f);
2163 /***************************************************************************
2164 return True if a local parameter is currently set to the global default
2165 ***************************************************************************/
2166 BOOL lp_is_default(int snum, struct parm_struct *parm)
2168 int pdiff = PTR_DIFF(parm->ptr,&sDefault);
2170 return equal_parameter(parm->type,
2171 ((char *)pSERVICE(snum)) + pdiff,
2172 ((char *)&sDefault) + pdiff);
2176 /***************************************************************************
2177 Display the contents of a single services record.
2178 ***************************************************************************/
2179 static void dump_a_service(service *pService, FILE *f)
2182 if (pService != &sDefault)
2183 fprintf(f,"\n[%s]\n",pService->szService);
2185 for (i=0;parm_table[i].label;i++)
2186 if (parm_table[i].class == P_LOCAL &&
2187 parm_table[i].ptr &&
2188 (*parm_table[i].label != '-') &&
2189 (i == 0 || (parm_table[i].ptr != parm_table[i-1].ptr))) {
2190 int pdiff = PTR_DIFF(parm_table[i].ptr,&sDefault);
2192 if (pService == &sDefault) {
2193 if (defaults_saved && is_default(i)) continue;
2195 if (equal_parameter(parm_table[i].type,
2196 ((char *)pService) + pdiff,
2197 ((char *)&sDefault) + pdiff))
2201 fprintf(f,"\t%s = ",parm_table[i].label);
2202 print_parameter(&parm_table[i],
2203 ((char *)pService) + pdiff, f);
2209 /***************************************************************************
2210 return info about the next service in a service. snum==-1 gives the globals
2212 return NULL when out of parameters
2213 ***************************************************************************/
2214 struct parm_struct *lp_next_parameter(int snum, int *i, int allparameters)
2217 /* do the globals */
2218 for (;parm_table[*i].label;(*i)++) {
2219 if (parm_table[*i].class == P_SEPARATOR)
2220 return &parm_table[(*i)++];
2222 if (!parm_table[*i].ptr || (*parm_table[*i].label == '-'))
2225 if ((*i) > 0 && (parm_table[*i].ptr == parm_table[(*i)-1].ptr))
2228 return &parm_table[(*i)++];
2231 service *pService = pSERVICE(snum);
2233 for (;parm_table[*i].label;(*i)++) {
2234 if (parm_table[*i].class == P_SEPARATOR)
2235 return &parm_table[(*i)++];
2237 if (parm_table[*i].class == P_LOCAL &&
2238 parm_table[*i].ptr &&
2239 (*parm_table[*i].label != '-') &&
2241 (parm_table[*i].ptr != parm_table[(*i)-1].ptr))) {
2242 int pdiff = PTR_DIFF(parm_table[*i].ptr,&sDefault);
2244 if (allparameters ||
2245 !equal_parameter(parm_table[*i].type,
2246 ((char *)pService) + pdiff,
2247 ((char *)&sDefault) + pdiff)) {
2248 return &parm_table[(*i)++];
2259 /***************************************************************************
2260 Display the contents of a single copy structure.
2261 ***************************************************************************/
2262 static void dump_copy_map(BOOL *pcopymap)
2265 if (!pcopymap) return;
2267 printf("\n\tNon-Copied parameters:\n");
2269 for (i=0;parm_table[i].label;i++)
2270 if (parm_table[i].class == P_LOCAL &&
2271 parm_table[i].ptr && !pcopymap[i] &&
2272 (i == 0 || (parm_table[i].ptr != parm_table[i-1].ptr)))
2274 printf("\t\t%s\n",parm_table[i].label);
2279 /***************************************************************************
2280 Return TRUE if the passed service number is within range.
2281 ***************************************************************************/
2282 BOOL lp_snum_ok(int iService)
2284 return (LP_SNUM_OK(iService) && iSERVICE(iService).bAvailable);
2288 /***************************************************************************
2289 auto-load some homes and printer services
2290 ***************************************************************************/
2291 static void lp_add_auto_services(char *str)
2295 int homes, printers;
2303 homes = lp_servicenumber(HOMES_NAME);
2304 printers = lp_servicenumber(PRINTERS_NAME);
2306 for (p=strtok(s,LIST_SEP);p;p=strtok(NULL,LIST_SEP))
2308 char *home = get_home_dir(p);
2310 if (lp_servicenumber(p) >= 0) continue;
2312 if (home && homes >= 0)
2314 lp_add_home(p,homes,home);
2318 if (printers >= 0 && pcap_printername_ok(p,NULL))
2319 lp_add_printer(p,printers);
2324 /***************************************************************************
2325 auto-load one printer
2326 ***************************************************************************/
2327 static void lp_add_one_printer(char *name,char *comment)
2329 int printers = lp_servicenumber(PRINTERS_NAME);
2332 if (lp_servicenumber(name) < 0)
2334 lp_add_printer(name,printers);
2335 if ((i=lp_servicenumber(name)) >= 0)
2336 string_set(&iSERVICE(i).comment,comment);
2341 /***************************************************************************
2342 auto-load printer services
2343 ***************************************************************************/
2344 static void lp_add_all_printers(void)
2346 int printers = lp_servicenumber(PRINTERS_NAME);
2348 if (printers < 0) return;
2350 pcap_printer_fn(lp_add_one_printer);
2353 /***************************************************************************
2354 have we loaded a services file yet?
2355 ***************************************************************************/
2356 BOOL lp_loaded(void)
2361 /***************************************************************************
2362 unload unused services
2363 ***************************************************************************/
2364 void lp_killunused(BOOL (*snumused)(int ))
2367 for (i=0;i<iNumServices;i++)
2368 if (VALID(i) && (!snumused || !snumused(i)))
2370 iSERVICE(i).valid = False;
2371 free_service(pSERVICE(i));
2376 /***************************************************************************
2377 save the curent values of all global and sDefault parameters into the
2378 defaults union. This allows swat and testparm to show only the
2379 changed (ie. non-default) parameters.
2380 ***************************************************************************/
2381 static void lp_save_defaults(void)
2384 for (i = 0; parm_table[i].label; i++) {
2385 if (i>0 && parm_table[i].ptr == parm_table[i-1].ptr) continue;
2386 switch (parm_table[i].type) {
2389 parm_table[i].def.svalue = strdup(*(char **)parm_table[i].ptr);
2393 parm_table[i].def.svalue = strdup((char *)parm_table[i].ptr);
2397 parm_table[i].def.bvalue = *(BOOL *)parm_table[i].ptr;
2400 parm_table[i].def.cvalue = *(char *)parm_table[i].ptr;
2405 parm_table[i].def.ivalue = *(int *)parm_table[i].ptr;
2411 defaults_saved = True;
2415 /***************************************************************************
2416 Load the services array from the services file. Return True on success,
2418 ***************************************************************************/
2419 BOOL lp_load(char *pszFname,BOOL global_only, BOOL save_defaults, BOOL add_ipc)
2424 add_to_file_list(pszFname);
2428 bInGlobalSection = True;
2429 bGlobalOnly = global_only;
2433 if (save_defaults) {
2438 pstrcpy(n2,pszFname);
2439 standard_sub_basic(n2);
2441 /* We get sections first, so have to start 'behind' to make up */
2443 bRetval = pm_process(n2, do_section, do_parameter);
2445 /* finish up the last section */
2446 DEBUG(3,("pm_process() returned %s\n", BOOLSTR(bRetval)));
2448 if (iServiceIndex >= 0)
2449 bRetval = service_ok(iServiceIndex);
2451 lp_add_auto_services(lp_auto_services());
2452 if (lp_load_printers())
2453 lp_add_all_printers();
2458 set_default_server_announce_type();
2466 /***************************************************************************
2467 return the max number of services
2468 ***************************************************************************/
2469 int lp_numservices(void)
2471 return(iNumServices);
2474 /***************************************************************************
2475 Display the contents of the services array in human-readable form.
2476 ***************************************************************************/
2477 void lp_dump(FILE *f, BOOL show_defaults)
2481 if (show_defaults) {
2482 defaults_saved = False;
2487 dump_a_service(&sDefault, f);
2489 for (iService = 0; iService < iNumServices; iService++)
2491 if (VALID(iService))
2493 if (iSERVICE(iService).szService[0] == '\0')
2495 dump_a_service(pSERVICE(iService), f);
2501 /***************************************************************************
2502 Return the number of the service with the given name, or -1 if it doesn't
2503 exist. Note that this is a DIFFERENT ANIMAL from the internal function
2504 getservicebyname()! This works ONLY if all services have been loaded, and
2505 does not copy the found service.
2506 ***************************************************************************/
2507 int lp_servicenumber(char *pszServiceName)
2511 for (iService = iNumServices - 1; iService >= 0; iService--)
2512 if (VALID(iService) &&
2513 strequal(lp_servicename(iService), pszServiceName))
2517 DEBUG(7,("lp_servicenumber: couldn't find %s\n",pszServiceName));
2522 /*******************************************************************
2523 a useful volume label function
2524 ******************************************************************/
2525 char *volume_label(int snum)
2527 char *ret = lp_volume(snum);
2528 if (!*ret) return(lp_servicename(snum));
2534 * nmbd only loads the global section. There seems to be no way to
2535 * determine exactly is a service is printable by only looking at the
2536 * [global] section so for now always announce as a print server. This
2537 * will need looking at in the future. Jeremy (jallison@whistle.com).
2539 /*******************************************************************
2540 Return true if any printer services are defined.
2541 ******************************************************************/
2542 static BOOL lp_printer_services(void)
2546 for (iService = iNumServices - 1; iService >= 0; iService--)
2547 if (VALID(iService) && iSERVICE(iService).bPrint_ok)
2553 /*******************************************************************
2554 Set the server type we will announce as via nmbd.
2555 ********************************************************************/
2556 static void set_default_server_announce_type()
2558 default_server_announce = (SV_TYPE_WORKSTATION | SV_TYPE_SERVER |
2559 SV_TYPE_SERVER_UNIX | SV_TYPE_PRINTQ_SERVER);
2560 if(lp_announce_as() == ANNOUNCE_AS_NT)
2561 default_server_announce |= (SV_TYPE_SERVER_NT | SV_TYPE_NT);
2562 else if(lp_announce_as() == ANNOUNCE_AS_WIN95)
2563 default_server_announce |= SV_TYPE_WIN95_PLUS;
2564 else if(lp_announce_as() == ANNOUNCE_AS_WFW)
2565 default_server_announce |= SV_TYPE_WFW;
2566 default_server_announce |= (lp_time_server() ? SV_TYPE_TIME_SOURCE : 0);
2568 * nmbd only loads the [global] section. There seems to be no way to
2569 * determine exactly if any service is printable by only looking at the
2570 * [global] section so for now always announce as a print server. This
2571 * will need looking at in the future. Jeremy (jallison@whistle.com).
2574 default_server_announce |= (lp_printer_services() ? SV_TYPE_PRINTQ_SERVER : 0);
2579 /*******************************************************************
2581 ********************************************************************/
2582 void lp_rename_service(int snum, char *new_name)
2584 string_set(&pSERVICE(snum)->szService, new_name);
2587 /*******************************************************************
2589 ********************************************************************/
2590 void lp_remove_service(int snum)
2592 pSERVICE(snum)->valid = False;
2595 /*******************************************************************
2597 ********************************************************************/
2598 void lp_copy_service(int snum, char *new_name)
2600 char *oldname = lp_servicename(snum);
2601 do_section(new_name);
2603 snum = lp_servicenumber(new_name);
2605 lp_do_parameter(snum, "copy", oldname);
2610 /*******************************************************************
2611 Get the default server type we will announce as via nmbd.
2612 ********************************************************************/
2613 int lp_default_server_announce(void)
2615 return default_server_announce;
2618 /*******************************************************************
2619 Split the announce version into major and minor numbers.
2620 ********************************************************************/
2621 int lp_major_announce_version(void)
2623 static BOOL got_major = False;
2624 static int major_version = DEFAULT_MAJOR_VERSION;
2629 return major_version;
2632 if((vers = lp_announce_version()) == NULL)
2633 return major_version;
2635 if((p = strchr(vers, '.')) == 0)
2636 return major_version;
2639 major_version = atoi(vers);
2640 return major_version;
2643 int lp_minor_announce_version(void)
2645 static BOOL got_minor = False;
2646 static int minor_version = DEFAULT_MINOR_VERSION;
2651 return minor_version;
2654 if((vers = lp_announce_version()) == NULL)
2655 return minor_version;
2657 if((p = strchr(vers, '.')) == 0)
2658 return minor_version;
2661 minor_version = atoi(p);
2662 return minor_version;
2665 /***********************************************************
2666 Set the global name resolution order (used in smbclient).
2667 ************************************************************/
2669 void lp_set_name_resolve_order(char *new_order)
2671 Globals.szNameResolveOrder = new_order;