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;
179 int change_notify_timeout;
182 #endif /* WITH_LDAP */
185 char *sslHostsRequire;
186 char *sslHostsResign;
192 char *sslClientPrivKey;
195 BOOL sslReqClientCert;
196 BOOL sslReqServerCert;
197 BOOL sslCompatibility;
198 #endif /* WITH_SSL */
203 BOOL bPreferredMaster;
204 BOOL bDomainController;
207 BOOL bEncryptPasswords;
215 BOOL bReadPrediction;
222 BOOL bBindInterfacesOnly;
223 BOOL bNetWkstaUserLogon;
224 BOOL bUnixPasswdSync;
225 BOOL bPasswdChatDebug;
226 BOOL bOleLockingCompat;
230 static global Globals;
235 * This structure describes a single service.
243 char *szGuestaccount;
244 char *szInvalidUsers;
252 char *szRootPostExec;
253 char *szPrintcommand;
256 char *szLppausecommand;
257 char *szLpresumecommand;
258 char *szQueuepausecommand;
259 char *szQueueresumecommand;
261 char *szPrinterDriver;
262 char *szPrinterDriverLocation;
271 char *szVetoOplockFiles;
280 int iCreate_force_mode;
290 BOOL bShortCasePreserve;
317 BOOL bDeleteReadonly;
319 BOOL bDeleteVetoFiles;
321 BOOL bDosFiletimeResolution;
322 BOOL bFakeDirCreateTimes;
323 char dummy[3]; /* for alignment */
327 /* This is a default service used to prime a services structure */
328 static service sDefault =
331 NULL, /* szService */
333 NULL, /* szUsername */
334 NULL, /* szGuestAccount - this is set in init_globals() */
335 NULL, /* szInvalidUsers */
336 NULL, /* szValidUsers */
337 NULL, /* szAdminUsers */
339 NULL, /* szInclude */
340 NULL, /* szPreExec */
341 NULL, /* szPostExec */
342 NULL, /* szRootPreExec */
343 NULL, /* szRootPostExec */
344 NULL, /* szPrintcommand */
345 NULL, /* szLpqcommand */
346 NULL, /* szLprmcommand */
347 NULL, /* szLppausecommand */
348 NULL, /* szLpresumecommand */
349 NULL, /* szQueuepausecommand */
350 NULL, /* szQueueresumecommand */
351 NULL, /* szPrintername */
352 NULL, /* szPrinterDriver - this is set in init_globals() */
353 NULL, /* szPrinterDriverLocation */
354 NULL, /* szDontdescend */
355 NULL, /* szHostsallow */
356 NULL, /* szHostsdeny */
357 NULL, /* szMagicScript */
358 NULL, /* szMagicOutput */
359 NULL, /* szMangledMap */
360 NULL, /* szVetoFiles */
361 NULL, /* szHideFiles */
362 NULL, /* szVetoOplockFiles */
364 NULL, /* force user */
365 NULL, /* force group */
367 NULL, /* writelist */
369 0, /* iMinPrintSpace */
370 0744, /* iCreate_mask */
371 0000, /* iCreate_force_mode */
372 0755, /* iDir_mask */
373 0000, /* iDir_force_mode */
374 0, /* iMaxConnections */
375 CASE_LOWER, /* iDefaultCase */
376 DEFAULT_PRINTING, /* iPrinting */
377 False, /* bAlternatePerm */
378 False, /* revalidate */
379 False, /* case sensitive */
380 True, /* case preserve */
381 True, /* short case preserve */
382 False, /* case mangle */
384 True, /* bHideDotFiles */
385 True, /* bBrowseable */
386 True, /* bAvailable */
387 True, /* bRead_only */
388 True, /* bNo_set_dir */
389 False, /* bGuest_only */
390 False, /* bGuest_ok */
391 False, /* bPrint_ok */
392 False, /* bPostscript */
393 False, /* bMap_system */
394 False, /* bMap_hidden */
395 True, /* bMap_archive */
397 False, /* bStrictLocking */
398 True, /* bShareModes */
400 False, /* bOnlyUser */
401 True, /* bMangledNames */
402 True, /* bWidelinks */
403 True, /* bSymlinks */
404 False, /* bSyncAlways */
405 False, /* bStrictSync */
406 '~', /* magic char */
408 False, /* bDeleteReadonly */
409 False, /* bFakeOplocks */
410 False, /* bDeleteVetoFiles */
411 False, /* bDosFiletimes */
412 False, /* bDosFiletimeResolution */
413 False, /* bFakeDirCreateTimes */
419 /* local variables */
420 static service **ServicePtrs = NULL;
421 static int iNumServices = 0;
422 static int iServiceIndex = 0;
423 static BOOL bInGlobalSection = True;
424 static BOOL bGlobalOnly = False;
425 static int default_server_announce;
427 #define NUMPARAMETERS (sizeof(parm_table) / sizeof(struct parm_struct))
429 /* prototypes for the special type handlers */
430 static BOOL handle_valid_chars(char *pszParmValue, char **ptr);
431 static BOOL handle_include(char *pszParmValue, char **ptr);
432 static BOOL handle_copy(char *pszParmValue, char **ptr);
433 static BOOL handle_character_set(char *pszParmValue,char **ptr);
434 static BOOL handle_coding_system(char *pszParmValue,char **ptr);
436 static void set_default_server_announce_type(void);
438 static struct enum_list enum_protocol[] = {{PROTOCOL_NT1, "NT1"}, {PROTOCOL_LANMAN2, "LANMAN2"},
439 {PROTOCOL_LANMAN1, "LANMAN1"}, {PROTOCOL_CORE,"CORE"},
440 {PROTOCOL_COREPLUS, "COREPLUS"},
441 {PROTOCOL_COREPLUS, "CORE+"}, {-1, NULL}};
443 static struct enum_list enum_security[] = {{SEC_SHARE, "SHARE"}, {SEC_USER, "USER"},
444 {SEC_SERVER, "SERVER"}, {SEC_DOMAIN, "DOMAIN"},
447 static struct enum_list enum_printing[] = {{PRINT_SYSV, "sysv"}, {PRINT_AIX, "aix"},
448 {PRINT_HPUX, "hpux"}, {PRINT_BSD, "bsd"},
449 {PRINT_QNX, "qnx"}, {PRINT_PLP, "plp"},
450 {PRINT_LPRNG, "lprng"}, {PRINT_SOFTQ, "softq"},
453 static struct enum_list enum_announce_as[] = {{ANNOUNCE_AS_NT, "NT"}, {ANNOUNCE_AS_WIN95, "win95"},
454 {ANNOUNCE_AS_WFW, "WfW"}, {-1, NULL}};
456 static struct enum_list enum_case[] = {{CASE_LOWER, "lower"}, {CASE_UPPER, "upper"}, {-1, NULL}};
458 static struct enum_list enum_lm_announce[] = {{0, "False"}, {1, "True"}, {2, "Auto"}, {-1, NULL}};
461 static struct enum_list enum_ssl_version[] = {{SMB_SSL_V2, "ssl2"}, {SMB_SSL_V3, "ssl3"},
462 {SMB_SSL_V23, "ssl2or3"}, {SMB_SSL_TLS1, "tls1"}, {-1, NULL}};
465 /* note that we do not initialise the defaults union - it is not allowed in ANSI C */
466 static struct parm_struct parm_table[] =
468 {"Base Options", P_SEP, P_SEPARATOR},
469 {"comment", P_STRING, P_LOCAL, &sDefault.comment, NULL, NULL, FLAG_BASIC|FLAG_PRINT},
470 {"path", P_STRING, P_LOCAL, &sDefault.szPath, NULL, NULL, FLAG_BASIC|FLAG_PRINT},
471 {"directory", P_STRING, P_LOCAL, &sDefault.szPath, NULL, NULL, 0},
472 {"workgroup", P_USTRING, P_GLOBAL, &Globals.szWorkGroup, NULL, NULL, FLAG_BASIC},
473 {"netbios name", P_UGSTRING,P_GLOBAL, global_myname, NULL, NULL, FLAG_BASIC},
474 {"netbios aliases", P_STRING, P_GLOBAL, &Globals.szNetbiosAliases, NULL, NULL, 0},
475 {"server string", P_STRING, P_GLOBAL, &Globals.szServerString, NULL, NULL, FLAG_BASIC},
476 {"interfaces", P_STRING, P_GLOBAL, &Globals.szInterfaces, NULL, NULL, FLAG_BASIC},
477 {"bind interfaces only", P_BOOL,P_GLOBAL, &Globals.bBindInterfacesOnly,NULL, NULL, 0},
479 {"Security Options", P_SEP, P_SEPARATOR},
480 {"security", P_ENUM, P_GLOBAL, &Globals.security, NULL, enum_security, FLAG_BASIC},
481 {"encrypt passwords",P_BOOL, P_GLOBAL, &Globals.bEncryptPasswords, NULL, NULL, FLAG_BASIC},
482 {"update encrypted", P_BOOL, P_GLOBAL, &Globals.bUpdateEncrypt, NULL, NULL, FLAG_BASIC},
483 {"use rhosts", P_BOOL, P_GLOBAL, &Globals.bUseRhosts, NULL, NULL, 0},
484 {"null passwords", P_BOOL, P_GLOBAL, &Globals.bNullPasswords, NULL, NULL, 0},
485 {"password server", P_STRING, P_GLOBAL, &Globals.szPasswordServer, NULL, NULL, 0},
486 {"smb passwd file", P_STRING, P_GLOBAL, &Globals.szSMBPasswdFile, NULL, NULL, 0},
487 {"hosts equiv", P_STRING, P_GLOBAL, &Globals.szHostsEquiv, NULL, NULL, 0},
488 {"root directory", P_STRING, P_GLOBAL, &Globals.szRootdir, NULL, NULL, 0},
489 {"root dir", P_STRING, P_GLOBAL, &Globals.szRootdir, NULL, NULL, 0},
490 {"root", P_STRING, P_GLOBAL, &Globals.szRootdir, NULL, NULL, 0},
491 {"passwd program", P_STRING, P_GLOBAL, &Globals.szPasswdProgram, NULL, NULL, 0},
492 {"passwd chat", P_STRING, P_GLOBAL, &Globals.szPasswdChat, NULL, NULL, 0},
493 {"passwd chat debug",P_BOOL, P_GLOBAL, &Globals.bPasswdChatDebug, NULL, NULL, 0},
494 {"username map", P_STRING, P_GLOBAL, &Globals.szUsernameMap, NULL, NULL, 0},
495 {"password level", P_INTEGER, P_GLOBAL, &Globals.pwordlevel, NULL, NULL, 0},
496 {"username level", P_INTEGER, P_GLOBAL, &Globals.unamelevel, NULL, NULL, 0},
497 {"unix password sync", P_BOOL, P_GLOBAL, &Globals.bUnixPasswdSync, NULL, NULL, 0},
498 {"alternate permissions",P_BOOL,P_LOCAL, &sDefault.bAlternatePerm, NULL, NULL, FLAG_GLOBAL},
499 {"revalidate", P_BOOL, P_LOCAL, &sDefault.bRevalidate, NULL, NULL, FLAG_GLOBAL},
500 {"username", P_STRING, P_LOCAL, &sDefault.szUsername, NULL, NULL, FLAG_GLOBAL},
501 {"user", P_STRING, P_LOCAL, &sDefault.szUsername, NULL, NULL, 0},
502 {"users", P_STRING, P_LOCAL, &sDefault.szUsername, NULL, NULL, 0},
503 {"guest account", P_STRING, P_LOCAL, &sDefault.szGuestaccount, NULL, NULL, FLAG_BASIC|FLAG_PRINT|FLAG_GLOBAL},
504 {"invalid users", P_STRING, P_LOCAL, &sDefault.szInvalidUsers, NULL, NULL, FLAG_GLOBAL},
505 {"valid users", P_STRING, P_LOCAL, &sDefault.szValidUsers, NULL, NULL, FLAG_GLOBAL},
506 {"admin users", P_STRING, P_LOCAL, &sDefault.szAdminUsers, NULL, NULL, FLAG_GLOBAL},
507 {"read list", P_STRING, P_LOCAL, &sDefault.readlist, NULL, NULL, FLAG_GLOBAL},
508 {"write list", P_STRING, P_LOCAL, &sDefault.writelist, NULL, NULL, FLAG_GLOBAL},
509 {"force user", P_STRING, P_LOCAL, &sDefault.force_user, NULL, NULL, 0},
510 {"force group", P_STRING, P_LOCAL, &sDefault.force_group, NULL, NULL, 0},
511 {"group", P_STRING, P_LOCAL, &sDefault.force_group, NULL, NULL, 0},
512 {"read only", P_BOOL, P_LOCAL, &sDefault.bRead_only, NULL, NULL, FLAG_BASIC},
513 {"write ok", P_BOOLREV, P_LOCAL, &sDefault.bRead_only, NULL, NULL, 0},
514 {"writeable", P_BOOLREV, P_LOCAL, &sDefault.bRead_only, NULL, NULL, 0},
515 {"writable", P_BOOLREV, P_LOCAL, &sDefault.bRead_only, NULL, NULL, 0},
516 {"create mask", P_OCTAL, P_LOCAL, &sDefault.iCreate_mask, NULL, NULL, FLAG_GLOBAL},
517 {"create mode", P_OCTAL, P_LOCAL, &sDefault.iCreate_mask, NULL, NULL, FLAG_GLOBAL},
518 {"force create mode",P_OCTAL, P_LOCAL, &sDefault.iCreate_force_mode, NULL, NULL, FLAG_GLOBAL},
519 {"directory mask", P_OCTAL, P_LOCAL, &sDefault.iDir_mask, NULL, NULL, FLAG_GLOBAL},
520 {"directory mode", P_OCTAL, P_LOCAL, &sDefault.iDir_mask, NULL, NULL, FLAG_GLOBAL},
521 {"force directory mode", P_OCTAL, P_LOCAL, &sDefault.iDir_force_mode, NULL, NULL, FLAG_GLOBAL},
522 {"guest only", P_BOOL, P_LOCAL, &sDefault.bGuest_only, NULL, NULL, 0},
523 {"only guest", P_BOOL, P_LOCAL, &sDefault.bGuest_only, NULL, NULL, 0},
524 {"guest ok", P_BOOL, P_LOCAL, &sDefault.bGuest_ok, NULL, NULL, FLAG_BASIC|FLAG_PRINT},
525 {"public", P_BOOL, P_LOCAL, &sDefault.bGuest_ok, NULL, NULL, 0},
526 {"only user", P_BOOL, P_LOCAL, &sDefault.bOnlyUser, NULL, NULL, 0},
527 {"hosts allow", P_STRING, P_LOCAL, &sDefault.szHostsallow, NULL, NULL, FLAG_GLOBAL|FLAG_BASIC|FLAG_PRINT},
528 {"allow hosts", P_STRING, P_LOCAL, &sDefault.szHostsallow, NULL, NULL, 0},
529 {"hosts deny", P_STRING, P_LOCAL, &sDefault.szHostsdeny, NULL, NULL, FLAG_GLOBAL|FLAG_BASIC|FLAG_PRINT},
530 {"deny hosts", P_STRING, P_LOCAL, &sDefault.szHostsdeny, NULL, NULL, 0},
533 {"Secure Socket Layer Options", P_SEP, P_SEPARATOR},
534 {"ssl", P_BOOL, P_GLOBAL, &Globals.sslEnabled, NULL, NULL, 0 },
535 {"ssl hosts", P_STRING, P_GLOBAL, &Globals.sslHostsRequire, NULL, NULL, 0 },
536 {"ssl hosts resign", P_STRING, P_GLOBAL, &Globals.sslHostsResign, NULL, NULL, 0} ,
537 {"ssl CA certDir", P_STRING, P_GLOBAL, &Globals.sslCaCertDir, NULL, NULL, 0 },
538 {"ssl CA certFile", P_STRING, P_GLOBAL, &Globals.sslCaCertFile, NULL, NULL, 0 },
539 {"ssl server cert", P_STRING, P_GLOBAL, &Globals.sslCert, NULL, NULL, 0 },
540 {"ssl server key", P_STRING, P_GLOBAL, &Globals.sslPrivKey, NULL, NULL, 0 },
541 {"ssl client cert", P_STRING, P_GLOBAL, &Globals.sslClientCert, NULL, NULL, 0 },
542 {"ssl client key", P_STRING, P_GLOBAL, &Globals.sslClientPrivKey, NULL, NULL, 0 },
543 {"ssl require clientcert", P_BOOL, P_GLOBAL, &Globals.sslReqClientCert, NULL, NULL , 0},
544 {"ssl require servercert", P_BOOL, P_GLOBAL, &Globals.sslReqServerCert, NULL, NULL , 0},
545 {"ssl ciphers", P_STRING, P_GLOBAL, &Globals.sslCiphers, NULL, NULL, 0 },
546 {"ssl version", P_ENUM, P_GLOBAL, &Globals.sslVersion, NULL, enum_ssl_version, 0},
547 {"ssl compatibility", P_BOOL, P_GLOBAL, &Globals.sslCompatibility, NULL, NULL, 0 },
548 #endif /* WITH_SSL */
550 {"Logging Options", P_SEP, P_SEPARATOR},
551 {"log level", P_INTEGER, P_GLOBAL, &DEBUGLEVEL, NULL, NULL, FLAG_BASIC},
552 {"debuglevel", P_INTEGER, P_GLOBAL, &DEBUGLEVEL, NULL, NULL, 0},
553 {"syslog", P_INTEGER, P_GLOBAL, &Globals.syslog, NULL, NULL, 0},
554 {"syslog only", P_BOOL, P_GLOBAL, &Globals.bSyslogOnly, NULL, NULL, 0},
555 {"log file", P_STRING, P_GLOBAL, &Globals.szLogFile, NULL, NULL, 0},
556 {"max log size", P_INTEGER, P_GLOBAL, &Globals.max_log_size, NULL, NULL, 0},
557 {"timestamp logs", P_BOOL, P_GLOBAL, &Globals.bTimestampLogs, NULL, NULL, 0},
558 {"debug timestamp", P_BOOL, P_GLOBAL, &Globals.bTimestampLogs, NULL, NULL, 0},
559 {"status", P_BOOL, P_LOCAL, &sDefault.status, NULL, NULL, FLAG_GLOBAL},
561 {"Protocol Options", P_SEP, P_SEPARATOR},
562 {"protocol", P_ENUM, P_GLOBAL, &Globals.maxprotocol, NULL, enum_protocol, 0},
563 {"read bmpx", P_BOOL, P_GLOBAL, &Globals.bReadbmpx, NULL, NULL, 0},
564 {"read raw", P_BOOL, P_GLOBAL, &Globals.bReadRaw, NULL, NULL, 0},
565 {"write raw", P_BOOL, P_GLOBAL, &Globals.bWriteRaw, NULL, NULL, 0},
566 {"networkstation user login", P_BOOL,P_GLOBAL, &Globals.bNetWkstaUserLogon,NULL, NULL, 0},
567 {"announce version", P_STRING, P_GLOBAL, &Globals.szAnnounceVersion, NULL, NULL, 0},
568 {"announce as", P_ENUM, P_GLOBAL, &Globals.announce_as, NULL, enum_announce_as, 0},
569 {"max mux", P_INTEGER, P_GLOBAL, &Globals.max_mux, NULL, NULL, 0},
570 {"max xmit", P_INTEGER, P_GLOBAL, &Globals.max_xmit, NULL, NULL, 0},
571 {"name resolve order", P_STRING, P_GLOBAL, &Globals.szNameResolveOrder, NULL, NULL, 0},
572 {"max packet", P_INTEGER, P_GLOBAL, &Globals.max_packet, NULL, NULL, 0},
573 {"packet size", P_INTEGER, P_GLOBAL, &Globals.max_packet, NULL, NULL, 0},
574 {"max ttl", P_INTEGER, P_GLOBAL, &Globals.max_ttl, NULL, NULL, 0},
575 {"max wins ttl", P_INTEGER, P_GLOBAL, &Globals.max_wins_ttl, NULL, NULL, 0},
576 {"min wins ttl", P_INTEGER, P_GLOBAL, &Globals.min_wins_ttl, NULL, NULL, 0},
577 {"time server", P_BOOL, P_GLOBAL, &Globals.bTimeServer, NULL, NULL, 0},
579 {"Tuning Options", P_SEP, P_SEPARATOR},
580 {"change notify timeout", P_INTEGER, P_GLOBAL, &Globals.change_notify_timeout, NULL, NULL, 0},
581 {"max disk size", P_INTEGER, P_GLOBAL, &Globals.maxdisksize, NULL, NULL, 0},
582 {"lpq cache time", P_INTEGER, P_GLOBAL, &Globals.lpqcachetime, NULL, NULL, 0},
583 {"getwd cache", P_BOOL, P_GLOBAL, &use_getwd_cache, NULL, NULL, 0},
584 {"read prediction", P_BOOL, P_GLOBAL, &Globals.bReadPrediction, NULL, NULL, 0},
585 {"socket options", P_GSTRING, P_GLOBAL, user_socket_options, NULL, NULL, 0},
586 {"keepalive", P_INTEGER, P_GLOBAL, &keepalive, NULL, NULL, 0},
587 {"deadtime", P_INTEGER, P_GLOBAL, &Globals.deadtime, NULL, NULL, 0},
588 {"read size", P_INTEGER, P_GLOBAL, &Globals.ReadSize, NULL, NULL, 0},
589 {"shared mem size", P_INTEGER, P_GLOBAL, &Globals.shmem_size, NULL, NULL, 0},
590 {"max connections", P_INTEGER, P_LOCAL, &sDefault.iMaxConnections, NULL, NULL, 0},
591 {"min print space", P_INTEGER, P_LOCAL, &sDefault.iMinPrintSpace, NULL, NULL, 0},
592 {"sync always", P_BOOL, P_LOCAL, &sDefault.bSyncAlways, NULL, NULL, 0},
593 {"strict sync", P_BOOL, P_LOCAL, &sDefault.bStrictSync, NULL, NULL, 0},
595 {"Printing Options", P_SEP, P_SEPARATOR},
596 {"load printers", P_BOOL, P_GLOBAL, &Globals.bLoadPrinters, NULL, NULL, 0},
597 {"printcap name", P_STRING, P_GLOBAL, &Globals.szPrintcapname, NULL, NULL, 0},
598 {"printcap", P_STRING, P_GLOBAL, &Globals.szPrintcapname, NULL, NULL, 0},
599 {"printer driver file", P_STRING, P_GLOBAL, &Globals.szDriverFile, NULL, NULL, 0},
600 {"print ok", P_BOOL, P_LOCAL, &sDefault.bPrint_ok, NULL, NULL, 0},
601 {"printable", P_BOOL, P_LOCAL, &sDefault.bPrint_ok, NULL, NULL, 0},
602 {"postscript", P_BOOL, P_LOCAL, &sDefault.bPostscript, NULL, NULL, FLAG_PRINT},
603 {"printing", P_ENUM, P_LOCAL, &sDefault.iPrinting, NULL, enum_printing, FLAG_PRINT|FLAG_GLOBAL},
604 {"print command", P_STRING, P_LOCAL, &sDefault.szPrintcommand, NULL, NULL, FLAG_PRINT|FLAG_GLOBAL},
605 {"lpq command", P_STRING, P_LOCAL, &sDefault.szLpqcommand, NULL, NULL, FLAG_PRINT|FLAG_GLOBAL},
606 {"lprm command", P_STRING, P_LOCAL, &sDefault.szLprmcommand, NULL, NULL, FLAG_PRINT|FLAG_GLOBAL},
607 {"lppause command", P_STRING, P_LOCAL, &sDefault.szLppausecommand, NULL, NULL, FLAG_GLOBAL},
608 {"lpresume command", P_STRING, P_LOCAL, &sDefault.szLpresumecommand,NULL, NULL, FLAG_GLOBAL},
609 {"queuepause command", P_STRING, P_LOCAL, &sDefault.szQueuepausecommand, NULL, NULL, FLAG_GLOBAL},
610 {"queueresume command", P_STRING, P_LOCAL, &sDefault.szQueueresumecommand, NULL, NULL, FLAG_GLOBAL},
612 {"printer name", P_STRING, P_LOCAL, &sDefault.szPrintername, NULL, NULL, FLAG_PRINT},
613 {"printer", P_STRING, P_LOCAL, &sDefault.szPrintername, NULL, NULL, 0},
614 {"printer driver", P_STRING, P_LOCAL, &sDefault.szPrinterDriver, NULL, NULL, 0},
615 {"printer driver location", P_STRING, P_LOCAL, &sDefault.szPrinterDriverLocation, NULL, NULL, FLAG_GLOBAL},
618 {"Filename Handling", P_SEP, P_SEPARATOR},
619 {"strip dot", P_BOOL, P_GLOBAL, &Globals.bStripDot, NULL, NULL, 0},
620 {"character set", P_STRING, P_GLOBAL, &Globals.szCharacterSet, handle_character_set, NULL, 0},
621 {"mangled stack", P_INTEGER, P_GLOBAL, &Globals.mangled_stack, NULL, NULL, 0},
622 {"coding system", P_STRING, P_GLOBAL, &Globals.szCodingSystem, handle_coding_system, NULL, 0},
623 {"client code page", P_INTEGER, P_GLOBAL, &Globals.client_code_page, NULL, NULL, 0},
624 {"default case", P_ENUM, P_LOCAL, &sDefault.iDefaultCase, NULL, enum_case, 0},
625 {"case sensitive", P_BOOL, P_LOCAL, &sDefault.bCaseSensitive, NULL, NULL, FLAG_GLOBAL},
626 {"casesignames", P_BOOL, P_LOCAL, &sDefault.bCaseSensitive, NULL, NULL, 0},
627 {"preserve case", P_BOOL, P_LOCAL, &sDefault.bCasePreserve, NULL, NULL, FLAG_GLOBAL},
628 {"short preserve case",P_BOOL, P_LOCAL, &sDefault.bShortCasePreserve,NULL, NULL, FLAG_GLOBAL},
629 {"mangle case", P_BOOL, P_LOCAL, &sDefault.bCaseMangle, NULL, NULL, FLAG_GLOBAL},
630 {"mangling char", P_CHAR, P_LOCAL, &sDefault.magic_char, NULL, NULL, FLAG_GLOBAL},
631 {"hide dot files", P_BOOL, P_LOCAL, &sDefault.bHideDotFiles, NULL, NULL, FLAG_GLOBAL},
632 {"delete veto files",P_BOOL, P_LOCAL, &sDefault.bDeleteVetoFiles, NULL, NULL, FLAG_GLOBAL},
633 {"veto files", P_STRING, P_LOCAL, &sDefault.szVetoFiles, NULL, NULL, FLAG_GLOBAL},
634 {"hide files", P_STRING, P_LOCAL, &sDefault.szHideFiles, NULL, NULL, FLAG_GLOBAL},
635 {"veto oplock files",P_STRING, P_LOCAL, &sDefault.szVetoOplockFiles,NULL, NULL, FLAG_GLOBAL},
636 {"map system", P_BOOL, P_LOCAL, &sDefault.bMap_system, NULL, NULL, FLAG_GLOBAL},
637 {"map hidden", P_BOOL, P_LOCAL, &sDefault.bMap_hidden, NULL, NULL, FLAG_GLOBAL},
638 {"map archive", P_BOOL, P_LOCAL, &sDefault.bMap_archive, NULL, NULL, FLAG_GLOBAL},
639 {"mangled names", P_BOOL, P_LOCAL, &sDefault.bMangledNames, NULL, NULL, FLAG_GLOBAL},
640 {"mangled map", P_STRING, P_LOCAL, &sDefault.szMangledMap, NULL, NULL, FLAG_GLOBAL},
642 {"Domain Options", P_SEP, P_SEPARATOR},
643 {"domain sid", P_USTRING, P_GLOBAL, &Globals.szDomainSID, NULL, NULL, 0},
644 {"domain groups", P_STRING, P_GLOBAL, &Globals.szDomainGroups, NULL, NULL, 0},
645 {"domain controller",P_BOOL , P_GLOBAL, &Globals.bDomainController,NULL, NULL, 0},
646 {"domain admin group",P_STRING, P_GLOBAL, &Globals.szDomainAdminGroup, NULL, NULL, 0},
647 {"domain guest group",P_STRING, P_GLOBAL, &Globals.szDomainGuestGroup, NULL, NULL, 0},
648 {"domain admin users",P_STRING, P_GLOBAL, &Globals.szDomainAdminUsers, NULL, NULL, 0},
649 {"domain guest users",P_STRING, P_GLOBAL, &Globals.szDomainGuestUsers, NULL, NULL, 0},
650 {"groupname map", P_STRING, P_GLOBAL, &Globals.szGroupnameMap, NULL, NULL, 0},
651 {"machine password timeout", P_INTEGER, P_GLOBAL, &Globals.machine_password_timeout, NULL, NULL, 0},
653 {"Logon Options", P_SEP, P_SEPARATOR},
654 {"logon script", P_STRING, P_GLOBAL, &Globals.szLogonScript, NULL, NULL, 0},
655 {"logon path", P_STRING, P_GLOBAL, &Globals.szLogonPath, NULL, NULL, 0},
656 {"logon drive", P_STRING, P_GLOBAL, &Globals.szLogonDrive, NULL, NULL, 0},
657 {"logon home", P_STRING, P_GLOBAL, &Globals.szLogonHome, NULL, NULL, 0},
658 {"domain logons", P_BOOL, P_GLOBAL, &Globals.bDomainLogons, NULL, NULL, 0},
660 {"Browse Options", P_SEP, P_SEPARATOR},
661 {"os level", P_INTEGER, P_GLOBAL, &Globals.os_level, NULL, NULL, FLAG_BASIC},
662 {"lm announce", P_ENUM, P_GLOBAL, &Globals.lm_announce, NULL, enum_lm_announce, 0},
663 {"lm interval", P_INTEGER, P_GLOBAL, &Globals.lm_interval, NULL, NULL, 0},
664 {"preferred master", P_BOOL, P_GLOBAL, &Globals.bPreferredMaster, NULL, NULL, FLAG_BASIC},
665 {"prefered master", P_BOOL, P_GLOBAL, &Globals.bPreferredMaster, NULL, NULL, 0},
666 {"local master", P_BOOL, P_GLOBAL, &Globals.bLocalMaster, NULL, NULL, FLAG_BASIC},
667 {"domain master", P_BOOL, P_GLOBAL, &Globals.bDomainMaster, NULL, NULL, FLAG_BASIC},
668 {"browse list", P_BOOL, P_GLOBAL, &Globals.bBrowseList, NULL, NULL, 0},
669 {"browseable", P_BOOL, P_LOCAL, &sDefault.bBrowseable, NULL, NULL, 0},
670 {"browsable", P_BOOL, P_LOCAL, &sDefault.bBrowseable, NULL, NULL, 0},
672 {"WINS Options", P_SEP, P_SEPARATOR},
673 {"dns proxy", P_BOOL, P_GLOBAL, &Globals.bDNSproxy, NULL, NULL, 0},
674 {"wins support", P_BOOL, P_GLOBAL, &Globals.bWINSsupport, NULL, NULL, FLAG_BASIC},
675 {"wins proxy", P_BOOL, P_GLOBAL, &Globals.bWINSproxy, NULL, NULL, 0},
676 {"wins server", P_STRING, P_GLOBAL, &Globals.szWINSserver, NULL, NULL, FLAG_BASIC},
678 {"Locking Options", P_SEP, P_SEPARATOR},
679 {"locking", P_BOOL, P_LOCAL, &sDefault.bLocking, NULL, NULL, FLAG_GLOBAL},
680 {"strict locking", P_BOOL, P_LOCAL, &sDefault.bStrictLocking, NULL, NULL, FLAG_GLOBAL},
681 {"share modes", P_BOOL, P_LOCAL, &sDefault.bShareModes, NULL, NULL, FLAG_GLOBAL},
682 {"oplocks", P_BOOL, P_LOCAL, &sDefault.bOpLocks, NULL, NULL, FLAG_GLOBAL},
683 {"fake oplocks", P_BOOL, P_LOCAL, &sDefault.bFakeOplocks, NULL, NULL, 0},
684 {"ole locking compatibility", P_BOOL, P_GLOBAL, &Globals.bOleLockingCompat, NULL, NULL, FLAG_GLOBAL},
687 {"Ldap Options", P_SEP, P_SEPARATOR},
688 {"ldap server", P_STRING, P_GLOBAL, &Globals.szLdapServer, NULL, NULL, 0},
689 {"ldap port", P_INTEGER, P_GLOBAL, &Globals.ldap_port, NULL, NULL, 0},
690 {"ldap suffix", P_STRING, P_GLOBAL, &Globals.szLdapSuffix, NULL, NULL, 0},
691 {"ldap filter", P_STRING, P_GLOBAL, &Globals.szLdapFilter, NULL, NULL, 0},
692 {"ldap root", P_STRING, P_GLOBAL, &Globals.szLdapRoot, NULL, NULL, 0},
693 {"ldap root passwd", P_STRING, P_GLOBAL, &Globals.szLdapRootPassword,NULL, NULL, 0},
694 #endif /* WITH_LDAP */
697 {"Miscellaneous Options", P_SEP, P_SEPARATOR},
698 {"smbrun", P_STRING, P_GLOBAL, &Globals.szSmbrun, NULL, NULL, 0},
699 {"config file", P_STRING, P_GLOBAL, &Globals.szConfigFile, NULL, NULL, FLAG_HIDE},
700 {"preload", P_STRING, P_GLOBAL, &Globals.szAutoServices, NULL, NULL, 0},
701 {"auto services", P_STRING, P_GLOBAL, &Globals.szAutoServices, NULL, NULL, 0},
702 {"lock dir", P_STRING, P_GLOBAL, &Globals.szLockDir, NULL, NULL, 0},
703 {"lock directory", P_STRING, P_GLOBAL, &Globals.szLockDir, NULL, NULL, 0},
704 {"default service", P_STRING, P_GLOBAL, &Globals.szDefaultService, NULL, NULL, 0},
705 {"default", P_STRING, P_GLOBAL, &Globals.szDefaultService, NULL, NULL, 0},
706 {"message command", P_STRING, P_GLOBAL, &Globals.szMsgCommand, NULL, NULL, 0},
707 {"dfree command", P_STRING, P_GLOBAL, &Globals.szDfree, NULL, NULL, 0},
708 {"valid chars", P_STRING, P_GLOBAL, &Globals.szValidChars, handle_valid_chars, NULL, 0},
709 {"remote announce", P_STRING, P_GLOBAL, &Globals.szRemoteAnnounce, NULL, NULL, 0},
710 {"remote browse sync",P_STRING, P_GLOBAL, &Globals.szRemoteBrowseSync,NULL, NULL, 0},
711 {"socket address", P_STRING, P_GLOBAL, &Globals.szSocketAddress, NULL, NULL, 0},
712 {"homedir map", P_STRING, P_GLOBAL, &Globals.szNISHomeMapName, NULL, NULL, 0},
713 {"time offset", P_INTEGER, P_GLOBAL, &extra_time_offset, NULL, NULL, 0},
714 {"unix realname", P_BOOL, P_GLOBAL, &Globals.bUnixRealname, NULL, NULL, 0},
715 {"NIS homedir", P_BOOL, P_GLOBAL, &Globals.bNISHomeMap, NULL, NULL, 0},
716 {"-valid", P_BOOL, P_LOCAL, &sDefault.valid, NULL, NULL, FLAG_HIDE},
717 {"copy", P_STRING, P_LOCAL, &sDefault.szCopy, handle_copy, NULL, FLAG_HIDE},
718 {"include", P_STRING, P_LOCAL, &sDefault.szInclude, handle_include, NULL, FLAG_HIDE},
719 {"exec", P_STRING, P_LOCAL, &sDefault.szPreExec, NULL, NULL, 0},
720 {"preexec", P_STRING, P_LOCAL, &sDefault.szPreExec, NULL, NULL, 0},
721 {"postexec", P_STRING, P_LOCAL, &sDefault.szPostExec, NULL, NULL, 0},
722 {"root preexec", P_STRING, P_LOCAL, &sDefault.szRootPreExec, NULL, NULL, 0},
723 {"root postexec", P_STRING, P_LOCAL, &sDefault.szRootPostExec, NULL, NULL, 0},
724 {"available", P_BOOL, P_LOCAL, &sDefault.bAvailable, NULL, NULL, 0},
725 {"volume", P_STRING, P_LOCAL, &sDefault.volume, NULL, NULL, 0},
726 {"set directory", P_BOOLREV, P_LOCAL, &sDefault.bNo_set_dir, NULL, NULL, 0},
727 {"wide links", P_BOOL, P_LOCAL, &sDefault.bWidelinks, NULL, NULL, FLAG_GLOBAL},
728 {"follow symlinks", P_BOOL, P_LOCAL, &sDefault.bSymlinks, NULL, NULL, FLAG_GLOBAL},
729 {"dont descend", P_STRING, P_LOCAL, &sDefault.szDontdescend, NULL, NULL, 0},
730 {"magic script", P_STRING, P_LOCAL, &sDefault.szMagicScript, NULL, NULL, 0},
731 {"magic output", P_STRING, P_LOCAL, &sDefault.szMagicOutput, NULL, NULL, 0},
732 {"delete readonly", P_BOOL, P_LOCAL, &sDefault.bDeleteReadonly, NULL, NULL, FLAG_GLOBAL},
733 {"dos filetimes", P_BOOL, P_LOCAL, &sDefault.bDosFiletimes, NULL, NULL, FLAG_GLOBAL},
734 {"dos filetime resolution",P_BOOL,P_LOCAL,&sDefault.bDosFiletimeResolution, NULL, NULL, FLAG_GLOBAL},
736 {"fake directory create times", P_BOOL,P_LOCAL, &sDefault.bFakeDirCreateTimes, NULL, NULL, FLAG_GLOBAL},
737 {NULL, P_BOOL, P_NONE, NULL, NULL, NULL, 0}
742 /***************************************************************************
743 Initialise the global parameter structure.
744 ***************************************************************************/
745 static void init_globals(void)
747 static BOOL done_init = False;
753 bzero((void *)&Globals,sizeof(Globals));
755 for (i = 0; parm_table[i].label; i++)
756 if ((parm_table[i].type == P_STRING ||
757 parm_table[i].type == P_USTRING) &&
759 string_init(parm_table[i].ptr,"");
761 string_set(&sDefault.szGuestaccount, GUEST_ACCOUNT);
762 string_set(&sDefault.szPrinterDriver, "NULL");
768 DEBUG(3,("Initialising global parameters\n"));
770 string_set(&Globals.szSMBPasswdFile, SMB_PASSWD_FILE);
771 string_set(&Globals.szPasswdChat,"*old*password* %o\\n *new*password* %n\\n *new*password* %n\\n *changed*");
772 string_set(&Globals.szWorkGroup, WORKGROUP);
773 string_set(&Globals.szPasswdProgram, SMB_PASSWD);
774 string_set(&Globals.szPrintcapname, PRINTCAP_NAME);
775 string_set(&Globals.szDriverFile, DRIVERFILE);
776 string_set(&Globals.szLockDir, LOCKDIR);
777 string_set(&Globals.szRootdir, "/");
778 string_set(&Globals.szSmbrun, SMBRUN);
779 string_set(&Globals.szSocketAddress, "0.0.0.0");
780 pstrcpy(s, "Samba ");
782 string_set(&Globals.szServerString,s);
783 slprintf(s,sizeof(s)-1, "%d.%d", DEFAULT_MAJOR_VERSION, DEFAULT_MINOR_VERSION);
784 string_set(&Globals.szAnnounceVersion,s);
786 string_set(&Globals.szLogonDrive, "");
787 /* %N is the NIS auto.home server if -DAUTOHOME is used, else same as %L */
788 string_set(&Globals.szLogonHome, "\\\\%N\\%U");
789 string_set(&Globals.szLogonPath, "\\\\%N\\%U\\profile");
791 string_set(&Globals.szNameResolveOrder, "lmhosts host wins bcast");
793 Globals.bLoadPrinters = True;
794 Globals.bUseRhosts = False;
795 Globals.max_packet = 65535;
796 Globals.mangled_stack = 50;
797 Globals.max_xmit = 65535;
798 Globals.max_mux = 50; /* This is *needed* for profile support. */
799 Globals.lpqcachetime = 10;
800 Globals.pwordlevel = 0;
801 Globals.unamelevel = 0;
802 Globals.deadtime = 0;
803 Globals.max_log_size = 5000;
804 Globals.maxprotocol = PROTOCOL_NT1;
805 Globals.security = SEC_USER;
806 Globals.bEncryptPasswords = False;
807 Globals.bUpdateEncrypt = False;
808 Globals.bReadRaw = True;
809 Globals.bWriteRaw = True;
810 Globals.bReadPrediction = False;
811 Globals.bReadbmpx = True;
812 Globals.bNullPasswords = False;
813 Globals.bStripDot = False;
815 Globals.bSyslogOnly = False;
816 Globals.bTimestampLogs = True;
817 Globals.os_level = 0;
818 Globals.max_ttl = 60*60*24*3; /* 3 days default. */
819 Globals.max_wins_ttl = 60*60*24*6; /* 6 days default. */
820 Globals.min_wins_ttl = 60*60*6; /* 6 hours default. */
821 Globals.machine_password_timeout = 60*60*24*7; /* 7 days default. */
822 Globals.change_notify_timeout = 60; /* 1 minute default. */
823 Globals.ReadSize = 16*1024;
824 Globals.lm_announce = 2; /* = Auto: send only if LM clients found */
825 Globals.lm_interval = 60;
826 Globals.shmem_size = SHMEM_SIZE;
827 Globals.announce_as = ANNOUNCE_AS_NT;
828 Globals.bUnixRealname = False;
829 #if (defined(HAVE_NETGROUP) && defined(WITH_AUTOMOUNT))
830 Globals.bNISHomeMap = False;
831 #ifdef WITH_NISPLUS_HOME
832 string_set(&Globals.szNISHomeMapName, "auto_home.org_dir");
834 string_set(&Globals.szNISHomeMapName, "auto.home");
837 Globals.client_code_page = DEFAULT_CLIENT_CODE_PAGE;
838 Globals.bTimeServer = False;
839 Globals.bBindInterfacesOnly = False;
840 Globals.bNetWkstaUserLogon = False; /* This is now set to false by default as
841 the code in password.c protects us from this bug. */
842 Globals.bUnixPasswdSync = False;
843 Globals.bPasswdChatDebug = False;
844 Globals.bOleLockingCompat = True;
847 /* default values for ldap */
848 string_set(&Globals.szLdapServer, "localhost");
849 Globals.ldap_port=389;
850 #endif /* WITH_LDAP */
853 Globals.sslVersion = SMB_SSL_V23;
854 Globals.sslHostsRequire = NULL;
855 Globals.sslHostsResign = NULL;
856 Globals.sslCaCertDir = NULL;
857 Globals.sslCaCertFile = NULL;
858 Globals.sslCert = NULL;
859 Globals.sslPrivKey = NULL;
860 Globals.sslClientCert = NULL;
861 Globals.sslClientPrivKey = NULL;
862 Globals.sslCiphers = NULL;
863 Globals.sslEnabled = False;
864 Globals.sslReqClientCert = False;
865 Globals.sslReqServerCert = False;
866 Globals.sslCompatibility = False;
867 #endif /* WITH_SSL */
869 /* these parameters are set to defaults that are more appropriate
870 for the increasing samba install base:
872 as a member of the workgroup, that will possibly become a
873 _local_ master browser (lm = True). this is opposed to a forced
874 local master browser startup (pm = True).
876 doesn't provide WINS server service by default (wsupp = False),
877 and doesn't provide domain master browser services by default, either.
881 Globals.bPreferredMaster = False;
882 Globals.bLocalMaster = True;
883 Globals.bDomainMaster = False;
884 Globals.bDomainLogons = False;
885 Globals.bBrowseList = True;
886 Globals.bWINSsupport = False;
887 Globals.bWINSproxy = False;
889 Globals.bDNSproxy = True;
892 * This must be done last as it checks the value in
896 interpret_coding_system(KANJI);
899 /***************************************************************************
900 check if a string is initialised and if not then initialise it
901 ***************************************************************************/
902 static void string_initial(char **s,char *v)
909 /***************************************************************************
910 Initialise the sDefault parameter structure.
911 ***************************************************************************/
912 static void init_locals(void)
914 /* choose defaults depending on the type of printing */
915 switch (sDefault.iPrinting)
921 string_initial(&sDefault.szLpqcommand,"lpq -P%p");
922 string_initial(&sDefault.szLprmcommand,"lprm -P%p %j");
923 string_initial(&sDefault.szPrintcommand,"lpr -r -P%p %s");
928 string_initial(&sDefault.szLpqcommand,"lpstat -o%p");
929 string_initial(&sDefault.szLprmcommand,"cancel %p-%j");
930 string_initial(&sDefault.szPrintcommand,"lp -c -d%p %s; rm %s");
932 string_initial(&sDefault.szLppausecommand,"lp -i %p-%j -H hold");
933 string_initial(&sDefault.szLpresumecommand,"lp -i %p-%j -H resume");
934 string_initial(&sDefault.szQueuepausecommand, "lpc stop %p");
935 string_initial(&sDefault.szQueueresumecommand, "lpc start %p");
937 string_initial(&sDefault.szQueuepausecommand, "disable %p");
938 string_initial(&sDefault.szQueueresumecommand, "enable %p");
943 string_initial(&sDefault.szLpqcommand,"lpq -P%p");
944 string_initial(&sDefault.szLprmcommand,"lprm -P%p %j");
945 string_initial(&sDefault.szPrintcommand,"lp -r -P%p %s");
949 string_initial(&sDefault.szLpqcommand,"qstat -l -d%p");
950 string_initial(&sDefault.szLprmcommand,"qstat -s -j%j -c");
951 string_initial(&sDefault.szPrintcommand,"lp -d%p -s %s; rm %s");
952 string_initial(&sDefault.szLppausecommand,"qstat -s -j%j -h");
953 string_initial(&sDefault.szLpresumecommand,"qstat -s -j%j -r");
960 /******************************************************************* a
961 convenience routine to grab string parameters into a rotating buffer,
962 and run standard_sub_basic on them. The buffers can be written to by
963 callers without affecting the source string.
964 ********************************************************************/
965 char *lp_string(char *s)
967 static char *bufs[10];
968 static int buflen[10];
969 static int next = -1;
972 int len = s?strlen(s):0;
983 len = MAX(len+100,sizeof(pstring)); /* the +100 is for some
986 if (buflen[next] != len) {
988 if (bufs[next]) free(bufs[next]);
989 bufs[next] = (char *)malloc(len);
991 DEBUG(0,("out of memory in lp_string()"));
996 ret = &bufs[next][0];
1004 trim_string(ret, "\"", "\"");
1006 standard_sub_basic(ret);
1012 In this section all the functions that are used to access the
1013 parameters from the rest of the program are defined
1016 #define FN_GLOBAL_STRING(fn_name,ptr) \
1017 char *fn_name(void) {return(lp_string(*(char **)(ptr) ? *(char **)(ptr) : ""));}
1018 #define FN_GLOBAL_BOOL(fn_name,ptr) \
1019 BOOL fn_name(void) {return(*(BOOL *)(ptr));}
1020 #define FN_GLOBAL_CHAR(fn_name,ptr) \
1021 char fn_name(void) {return(*(char *)(ptr));}
1022 #define FN_GLOBAL_INTEGER(fn_name,ptr) \
1023 int fn_name(void) {return(*(int *)(ptr));}
1025 #define FN_LOCAL_STRING(fn_name,val) \
1026 char *fn_name(int i) {return(lp_string((LP_SNUM_OK(i)&&pSERVICE(i)->val)?pSERVICE(i)->val : sDefault.val));}
1027 #define FN_LOCAL_BOOL(fn_name,val) \
1028 BOOL fn_name(int i) {return(LP_SNUM_OK(i)? pSERVICE(i)->val : sDefault.val);}
1029 #define FN_LOCAL_CHAR(fn_name,val) \
1030 char fn_name(int i) {return(LP_SNUM_OK(i)? pSERVICE(i)->val : sDefault.val);}
1031 #define FN_LOCAL_INTEGER(fn_name,val) \
1032 int fn_name(int i) {return(LP_SNUM_OK(i)? pSERVICE(i)->val : sDefault.val);}
1034 FN_GLOBAL_STRING(lp_logfile,&Globals.szLogFile)
1035 FN_GLOBAL_STRING(lp_smbrun,&Globals.szSmbrun)
1036 FN_GLOBAL_STRING(lp_configfile,&Globals.szConfigFile)
1037 FN_GLOBAL_STRING(lp_smb_passwd_file,&Globals.szSMBPasswdFile)
1038 FN_GLOBAL_STRING(lp_serverstring,&Globals.szServerString)
1039 FN_GLOBAL_STRING(lp_printcapname,&Globals.szPrintcapname)
1040 FN_GLOBAL_STRING(lp_lockdir,&Globals.szLockDir)
1041 FN_GLOBAL_STRING(lp_rootdir,&Globals.szRootdir)
1042 FN_GLOBAL_STRING(lp_defaultservice,&Globals.szDefaultService)
1043 FN_GLOBAL_STRING(lp_msg_command,&Globals.szMsgCommand)
1044 FN_GLOBAL_STRING(lp_dfree_command,&Globals.szDfree)
1045 FN_GLOBAL_STRING(lp_hosts_equiv,&Globals.szHostsEquiv)
1046 FN_GLOBAL_STRING(lp_auto_services,&Globals.szAutoServices)
1047 FN_GLOBAL_STRING(lp_passwd_program,&Globals.szPasswdProgram)
1048 FN_GLOBAL_STRING(lp_passwd_chat,&Globals.szPasswdChat)
1049 FN_GLOBAL_STRING(lp_passwordserver,&Globals.szPasswordServer)
1050 FN_GLOBAL_STRING(lp_name_resolve_order,&Globals.szNameResolveOrder)
1051 FN_GLOBAL_STRING(lp_workgroup,&Globals.szWorkGroup)
1052 FN_GLOBAL_STRING(lp_username_map,&Globals.szUsernameMap)
1053 FN_GLOBAL_STRING(lp_groupname_map,&Globals.szGroupnameMap)
1054 FN_GLOBAL_STRING(lp_character_set,&Globals.szCharacterSet)
1055 FN_GLOBAL_STRING(lp_logon_script,&Globals.szLogonScript)
1056 FN_GLOBAL_STRING(lp_logon_path,&Globals.szLogonPath)
1057 FN_GLOBAL_STRING(lp_logon_drive,&Globals.szLogonDrive)
1058 FN_GLOBAL_STRING(lp_logon_home,&Globals.szLogonHome)
1059 FN_GLOBAL_STRING(lp_remote_announce,&Globals.szRemoteAnnounce)
1060 FN_GLOBAL_STRING(lp_remote_browse_sync,&Globals.szRemoteBrowseSync)
1061 FN_GLOBAL_STRING(lp_wins_server,&Globals.szWINSserver)
1062 FN_GLOBAL_STRING(lp_interfaces,&Globals.szInterfaces)
1063 FN_GLOBAL_STRING(lp_socket_address,&Globals.szSocketAddress)
1064 FN_GLOBAL_STRING(lp_nis_home_map_name,&Globals.szNISHomeMapName)
1065 FN_GLOBAL_STRING(lp_announce_version,&Globals.szAnnounceVersion)
1066 FN_GLOBAL_STRING(lp_netbios_aliases,&Globals.szNetbiosAliases)
1067 FN_GLOBAL_STRING(lp_driverfile,&Globals.szDriverFile)
1069 FN_GLOBAL_STRING(lp_domain_sid,&Globals.szDomainSID)
1070 FN_GLOBAL_STRING(lp_domain_other_sids,&Globals.szDomainOtherSIDs)
1071 FN_GLOBAL_STRING(lp_domain_groups,&Globals.szDomainGroups)
1072 FN_GLOBAL_STRING(lp_domain_admin_group,&Globals.szDomainAdminGroup)
1073 FN_GLOBAL_STRING(lp_domain_guest_group,&Globals.szDomainGuestGroup)
1074 FN_GLOBAL_STRING(lp_domain_admin_users,&Globals.szDomainAdminUsers)
1075 FN_GLOBAL_STRING(lp_domain_guest_users,&Globals.szDomainGuestUsers)
1076 FN_GLOBAL_STRING(lp_domain_hostsallow,&Globals.szDomainHostsallow)
1077 FN_GLOBAL_STRING(lp_domain_hostsdeny,&Globals.szDomainHostsdeny)
1080 FN_GLOBAL_STRING(lp_ldap_server,&Globals.szLdapServer);
1081 FN_GLOBAL_STRING(lp_ldap_suffix,&Globals.szLdapSuffix);
1082 FN_GLOBAL_STRING(lp_ldap_filter,&Globals.szLdapFilter);
1083 FN_GLOBAL_STRING(lp_ldap_root,&Globals.szLdapRoot);
1084 FN_GLOBAL_STRING(lp_ldap_rootpasswd,&Globals.szLdapRootPassword);
1085 #endif /* WITH_LDAP */
1088 FN_GLOBAL_INTEGER(lp_ssl_version,&Globals.sslVersion);
1089 FN_GLOBAL_STRING(lp_ssl_hosts,&Globals.sslHostsRequire);
1090 FN_GLOBAL_STRING(lp_ssl_hosts_resign,&Globals.sslHostsResign);
1091 FN_GLOBAL_STRING(lp_ssl_cacertdir,&Globals.sslCaCertDir);
1092 FN_GLOBAL_STRING(lp_ssl_cacertfile,&Globals.sslCaCertFile);
1093 FN_GLOBAL_STRING(lp_ssl_cert,&Globals.sslCert);
1094 FN_GLOBAL_STRING(lp_ssl_privkey,&Globals.sslPrivKey);
1095 FN_GLOBAL_STRING(lp_ssl_client_cert,&Globals.sslClientCert);
1096 FN_GLOBAL_STRING(lp_ssl_client_privkey,&Globals.sslClientPrivKey);
1097 FN_GLOBAL_STRING(lp_ssl_ciphers,&Globals.sslCiphers);
1098 FN_GLOBAL_BOOL(lp_ssl_enabled,&Globals.sslEnabled);
1099 FN_GLOBAL_BOOL(lp_ssl_reqClientCert,&Globals.sslReqClientCert);
1100 FN_GLOBAL_BOOL(lp_ssl_reqServerCert,&Globals.sslReqServerCert);
1101 FN_GLOBAL_BOOL(lp_ssl_compatibility,&Globals.sslCompatibility);
1102 #endif /* WITH_SSL */
1104 FN_GLOBAL_BOOL(lp_dns_proxy,&Globals.bDNSproxy)
1105 FN_GLOBAL_BOOL(lp_wins_support,&Globals.bWINSsupport)
1106 FN_GLOBAL_BOOL(lp_we_are_a_wins_server,&Globals.bWINSsupport)
1107 FN_GLOBAL_BOOL(lp_wins_proxy,&Globals.bWINSproxy)
1108 FN_GLOBAL_BOOL(lp_local_master,&Globals.bLocalMaster)
1109 FN_GLOBAL_BOOL(lp_domain_controller,&Globals.bDomainController)
1110 FN_GLOBAL_BOOL(lp_domain_master,&Globals.bDomainMaster)
1111 FN_GLOBAL_BOOL(lp_domain_logons,&Globals.bDomainLogons)
1112 FN_GLOBAL_BOOL(lp_preferred_master,&Globals.bPreferredMaster)
1113 FN_GLOBAL_BOOL(lp_load_printers,&Globals.bLoadPrinters)
1114 FN_GLOBAL_BOOL(lp_use_rhosts,&Globals.bUseRhosts)
1115 FN_GLOBAL_BOOL(lp_getwdcache,&use_getwd_cache)
1116 FN_GLOBAL_BOOL(lp_readprediction,&Globals.bReadPrediction)
1117 FN_GLOBAL_BOOL(lp_readbmpx,&Globals.bReadbmpx)
1118 FN_GLOBAL_BOOL(lp_readraw,&Globals.bReadRaw)
1119 FN_GLOBAL_BOOL(lp_writeraw,&Globals.bWriteRaw)
1120 FN_GLOBAL_BOOL(lp_null_passwords,&Globals.bNullPasswords)
1121 FN_GLOBAL_BOOL(lp_strip_dot,&Globals.bStripDot)
1122 FN_GLOBAL_BOOL(lp_encrypted_passwords,&Globals.bEncryptPasswords)
1123 FN_GLOBAL_BOOL(lp_update_encrypted,&Globals.bUpdateEncrypt)
1124 FN_GLOBAL_BOOL(lp_syslog_only,&Globals.bSyslogOnly)
1125 FN_GLOBAL_BOOL(lp_timestamp_logs,&Globals.bTimestampLogs)
1126 FN_GLOBAL_BOOL(lp_browse_list,&Globals.bBrowseList)
1127 FN_GLOBAL_BOOL(lp_unix_realname,&Globals.bUnixRealname)
1128 FN_GLOBAL_BOOL(lp_nis_home_map,&Globals.bNISHomeMap)
1129 FN_GLOBAL_BOOL(lp_time_server,&Globals.bTimeServer)
1130 FN_GLOBAL_BOOL(lp_bind_interfaces_only,&Globals.bBindInterfacesOnly)
1131 FN_GLOBAL_BOOL(lp_net_wksta_user_logon,&Globals.bNetWkstaUserLogon)
1132 FN_GLOBAL_BOOL(lp_unix_password_sync,&Globals.bUnixPasswdSync)
1133 FN_GLOBAL_BOOL(lp_passwd_chat_debug,&Globals.bPasswdChatDebug)
1134 FN_GLOBAL_BOOL(lp_ole_locking_compat,&Globals.bOleLockingCompat)
1136 FN_GLOBAL_INTEGER(lp_os_level,&Globals.os_level)
1137 FN_GLOBAL_INTEGER(lp_max_ttl,&Globals.max_ttl)
1138 FN_GLOBAL_INTEGER(lp_max_wins_ttl,&Globals.max_wins_ttl)
1139 FN_GLOBAL_INTEGER(lp_min_wins_ttl,&Globals.max_wins_ttl)
1140 FN_GLOBAL_INTEGER(lp_max_log_size,&Globals.max_log_size)
1141 FN_GLOBAL_INTEGER(lp_mangledstack,&Globals.mangled_stack)
1142 FN_GLOBAL_INTEGER(lp_maxxmit,&Globals.max_xmit)
1143 FN_GLOBAL_INTEGER(lp_maxmux,&Globals.max_mux)
1144 FN_GLOBAL_INTEGER(lp_maxpacket,&Globals.max_packet)
1145 FN_GLOBAL_INTEGER(lp_keepalive,&keepalive)
1146 FN_GLOBAL_INTEGER(lp_passwordlevel,&Globals.pwordlevel)
1147 FN_GLOBAL_INTEGER(lp_usernamelevel,&Globals.unamelevel)
1148 FN_GLOBAL_INTEGER(lp_readsize,&Globals.ReadSize)
1149 FN_GLOBAL_INTEGER(lp_shmem_size,&Globals.shmem_size)
1150 FN_GLOBAL_INTEGER(lp_deadtime,&Globals.deadtime)
1151 FN_GLOBAL_INTEGER(lp_maxprotocol,&Globals.maxprotocol)
1152 FN_GLOBAL_INTEGER(lp_security,&Globals.security)
1153 FN_GLOBAL_INTEGER(lp_maxdisksize,&Globals.maxdisksize)
1154 FN_GLOBAL_INTEGER(lp_lpqcachetime,&Globals.lpqcachetime)
1155 FN_GLOBAL_INTEGER(lp_syslog,&Globals.syslog)
1156 FN_GLOBAL_INTEGER(lp_client_code_page,&Globals.client_code_page)
1157 FN_GLOBAL_INTEGER(lp_announce_as,&Globals.announce_as)
1158 FN_GLOBAL_INTEGER(lp_lm_announce,&Globals.lm_announce)
1159 FN_GLOBAL_INTEGER(lp_lm_interval,&Globals.lm_interval)
1160 FN_GLOBAL_INTEGER(lp_machine_password_timeout,&Globals.machine_password_timeout)
1161 FN_GLOBAL_INTEGER(lp_change_notify_timeout,&Globals.change_notify_timeout)
1164 FN_GLOBAL_INTEGER(lp_ldap_port,&Globals.ldap_port)
1165 #endif /* WITH_LDAP */
1167 FN_LOCAL_STRING(lp_preexec,szPreExec)
1168 FN_LOCAL_STRING(lp_postexec,szPostExec)
1169 FN_LOCAL_STRING(lp_rootpreexec,szRootPreExec)
1170 FN_LOCAL_STRING(lp_rootpostexec,szRootPostExec)
1171 FN_LOCAL_STRING(lp_servicename,szService)
1172 FN_LOCAL_STRING(lp_pathname,szPath)
1173 FN_LOCAL_STRING(lp_dontdescend,szDontdescend)
1174 FN_LOCAL_STRING(lp_username,szUsername)
1175 FN_LOCAL_STRING(lp_guestaccount,szGuestaccount)
1176 FN_LOCAL_STRING(lp_invalid_users,szInvalidUsers)
1177 FN_LOCAL_STRING(lp_valid_users,szValidUsers)
1178 FN_LOCAL_STRING(lp_admin_users,szAdminUsers)
1179 FN_LOCAL_STRING(lp_printcommand,szPrintcommand)
1180 FN_LOCAL_STRING(lp_lpqcommand,szLpqcommand)
1181 FN_LOCAL_STRING(lp_lprmcommand,szLprmcommand)
1182 FN_LOCAL_STRING(lp_lppausecommand,szLppausecommand)
1183 FN_LOCAL_STRING(lp_lpresumecommand,szLpresumecommand)
1184 FN_LOCAL_STRING(lp_queuepausecommand,szQueuepausecommand)
1185 FN_LOCAL_STRING(lp_queueresumecommand,szQueueresumecommand)
1186 FN_LOCAL_STRING(lp_printername,szPrintername)
1187 FN_LOCAL_STRING(lp_printerdriver,szPrinterDriver)
1188 FN_LOCAL_STRING(lp_hostsallow,szHostsallow)
1189 FN_LOCAL_STRING(lp_hostsdeny,szHostsdeny)
1190 FN_LOCAL_STRING(lp_magicscript,szMagicScript)
1191 FN_LOCAL_STRING(lp_magicoutput,szMagicOutput)
1192 FN_LOCAL_STRING(lp_comment,comment)
1193 FN_LOCAL_STRING(lp_force_user,force_user)
1194 FN_LOCAL_STRING(lp_force_group,force_group)
1195 FN_LOCAL_STRING(lp_readlist,readlist)
1196 FN_LOCAL_STRING(lp_writelist,writelist)
1197 FN_LOCAL_STRING(lp_volume,volume)
1198 FN_LOCAL_STRING(lp_mangled_map,szMangledMap)
1199 FN_LOCAL_STRING(lp_veto_files,szVetoFiles)
1200 FN_LOCAL_STRING(lp_hide_files,szHideFiles)
1201 FN_LOCAL_STRING(lp_veto_oplocks,szVetoOplockFiles)
1202 FN_LOCAL_STRING(lp_driverlocation,szPrinterDriverLocation)
1204 FN_LOCAL_BOOL(lp_alternate_permissions,bAlternatePerm)
1205 FN_LOCAL_BOOL(lp_revalidate,bRevalidate)
1206 FN_LOCAL_BOOL(lp_casesensitive,bCaseSensitive)
1207 FN_LOCAL_BOOL(lp_preservecase,bCasePreserve)
1208 FN_LOCAL_BOOL(lp_shortpreservecase,bShortCasePreserve)
1209 FN_LOCAL_BOOL(lp_casemangle,bCaseMangle)
1210 FN_LOCAL_BOOL(lp_status,status)
1211 FN_LOCAL_BOOL(lp_hide_dot_files,bHideDotFiles)
1212 FN_LOCAL_BOOL(lp_browseable,bBrowseable)
1213 FN_LOCAL_BOOL(lp_readonly,bRead_only)
1214 FN_LOCAL_BOOL(lp_no_set_dir,bNo_set_dir)
1215 FN_LOCAL_BOOL(lp_guest_ok,bGuest_ok)
1216 FN_LOCAL_BOOL(lp_guest_only,bGuest_only)
1217 FN_LOCAL_BOOL(lp_print_ok,bPrint_ok)
1218 FN_LOCAL_BOOL(lp_postscript,bPostscript)
1219 FN_LOCAL_BOOL(lp_map_hidden,bMap_hidden)
1220 FN_LOCAL_BOOL(lp_map_archive,bMap_archive)
1221 FN_LOCAL_BOOL(lp_locking,bLocking)
1222 FN_LOCAL_BOOL(lp_strict_locking,bStrictLocking)
1223 FN_LOCAL_BOOL(lp_share_modes,bShareModes)
1224 FN_LOCAL_BOOL(lp_oplocks,bOpLocks)
1225 FN_LOCAL_BOOL(lp_onlyuser,bOnlyUser)
1226 FN_LOCAL_BOOL(lp_manglednames,bMangledNames)
1227 FN_LOCAL_BOOL(lp_widelinks,bWidelinks)
1228 FN_LOCAL_BOOL(lp_symlinks,bSymlinks)
1229 FN_LOCAL_BOOL(lp_syncalways,bSyncAlways)
1230 FN_LOCAL_BOOL(lp_strict_sync,bStrictSync)
1231 FN_LOCAL_BOOL(lp_map_system,bMap_system)
1232 FN_LOCAL_BOOL(lp_delete_readonly,bDeleteReadonly)
1233 FN_LOCAL_BOOL(lp_fake_oplocks,bFakeOplocks)
1234 FN_LOCAL_BOOL(lp_recursive_veto_delete,bDeleteVetoFiles)
1235 FN_LOCAL_BOOL(lp_dos_filetimes,bDosFiletimes)
1236 FN_LOCAL_BOOL(lp_dos_filetime_resolution,bDosFiletimeResolution)
1237 FN_LOCAL_BOOL(lp_fake_dir_create_times,bFakeDirCreateTimes)
1239 FN_LOCAL_INTEGER(lp_create_mode,iCreate_mask)
1240 FN_LOCAL_INTEGER(lp_force_create_mode,iCreate_force_mode)
1241 FN_LOCAL_INTEGER(lp_dir_mode,iDir_mask)
1242 FN_LOCAL_INTEGER(lp_force_dir_mode,iDir_force_mode)
1243 FN_LOCAL_INTEGER(lp_max_connections,iMaxConnections)
1244 FN_LOCAL_INTEGER(lp_defaultcase,iDefaultCase)
1245 FN_LOCAL_INTEGER(lp_minprintspace,iMinPrintSpace)
1246 FN_LOCAL_INTEGER(lp_printing,iPrinting)
1248 FN_LOCAL_CHAR(lp_magicchar,magic_char)
1252 /* local prototypes */
1253 static int strwicmp( char *psz1, char *psz2 );
1254 static int map_parameter( char *pszParmName);
1255 static BOOL set_boolean( BOOL *pb, char *pszParmValue );
1256 static int getservicebyname(char *pszServiceName, service *pserviceDest);
1257 static void copy_service( service *pserviceDest,
1258 service *pserviceSource,
1259 BOOL *pcopymapDest );
1260 static BOOL service_ok(int iService);
1261 static BOOL do_parameter(char *pszParmName, char *pszParmValue);
1262 static BOOL do_section(char *pszSectionName);
1263 static void init_copymap(service *pservice);
1266 /***************************************************************************
1267 initialise a service to the defaults
1268 ***************************************************************************/
1269 static void init_service(service *pservice)
1271 bzero((char *)pservice,sizeof(service));
1272 copy_service(pservice,&sDefault,NULL);
1276 /***************************************************************************
1277 free the dynamically allocated parts of a service struct
1278 ***************************************************************************/
1279 static void free_service(service *pservice)
1285 if(pservice->szService)
1286 DEBUG(5,("free_service: Freeing service %s\n", pservice->szService));
1288 string_free(&pservice->szService);
1289 if (pservice->copymap)
1291 free(pservice->copymap);
1292 pservice->copymap = NULL;
1295 for (i=0;parm_table[i].label;i++)
1296 if ((parm_table[i].type == P_STRING ||
1297 parm_table[i].type == P_USTRING) &&
1298 parm_table[i].class == P_LOCAL)
1299 string_free((char **)(((char *)pservice) + PTR_DIFF(parm_table[i].ptr,&sDefault)));
1302 /***************************************************************************
1303 add a new service to the services array initialising it with the given
1305 ***************************************************************************/
1306 static int add_a_service(service *pservice, char *name)
1310 int num_to_alloc = iNumServices+1;
1312 tservice = *pservice;
1314 /* it might already exist */
1317 i = getservicebyname(name,NULL);
1322 /* find an invalid one */
1323 for (i=0;i<iNumServices;i++)
1324 if (!pSERVICE(i)->valid)
1327 /* if not, then create one */
1328 if (i == iNumServices)
1330 ServicePtrs = (service **)Realloc(ServicePtrs,sizeof(service *)*num_to_alloc);
1332 pSERVICE(iNumServices) = (service *)malloc(sizeof(service));
1334 if (!ServicePtrs || !pSERVICE(iNumServices))
1340 free_service(pSERVICE(i));
1342 pSERVICE(i)->valid = True;
1344 init_service(pSERVICE(i));
1345 copy_service(pSERVICE(i),&tservice,NULL);
1347 string_set(&iSERVICE(i).szService,name);
1352 /***************************************************************************
1353 add a new home service, with the specified home directory, defaults coming
1355 ***************************************************************************/
1356 BOOL lp_add_home(char *pszHomename, int iDefaultService, char *pszHomedir)
1358 int i = add_a_service(pSERVICE(iDefaultService),pszHomename);
1363 if (!(*(iSERVICE(i).szPath)) || strequal(iSERVICE(i).szPath,lp_pathname(-1)))
1364 string_set(&iSERVICE(i).szPath,pszHomedir);
1365 if (!(*(iSERVICE(i).comment)))
1368 slprintf(comment,sizeof(comment)-1,
1369 "Home directory of %s",pszHomename);
1370 string_set(&iSERVICE(i).comment,comment);
1372 iSERVICE(i).bAvailable = sDefault.bAvailable;
1373 iSERVICE(i).bBrowseable = sDefault.bBrowseable;
1375 DEBUG(3,("adding home directory %s at %s\n", pszHomename, pszHomedir));
1380 /***************************************************************************
1381 add a new service, based on an old one
1382 ***************************************************************************/
1383 int lp_add_service(char *pszService, int iDefaultService)
1385 return(add_a_service(pSERVICE(iDefaultService),pszService));
1389 /***************************************************************************
1391 ***************************************************************************/
1392 static BOOL lp_add_ipc(void)
1395 int i = add_a_service(&sDefault,"IPC$");
1400 slprintf(comment,sizeof(comment)-1,
1401 "IPC Service (%s)", Globals.szServerString );
1403 string_set(&iSERVICE(i).szPath,tmpdir());
1404 string_set(&iSERVICE(i).szUsername,"");
1405 string_set(&iSERVICE(i).comment,comment);
1406 iSERVICE(i).status = False;
1407 iSERVICE(i).iMaxConnections = 0;
1408 iSERVICE(i).bAvailable = True;
1409 iSERVICE(i).bRead_only = True;
1410 iSERVICE(i).bGuest_only = False;
1411 iSERVICE(i).bGuest_ok = True;
1412 iSERVICE(i).bPrint_ok = False;
1413 iSERVICE(i).bBrowseable = sDefault.bBrowseable;
1415 DEBUG(3,("adding IPC service\n"));
1421 /***************************************************************************
1422 add a new printer service, with defaults coming from service iFrom
1423 ***************************************************************************/
1424 BOOL lp_add_printer(char *pszPrintername, int iDefaultService)
1426 char *comment = "From Printcap";
1427 int i = add_a_service(pSERVICE(iDefaultService),pszPrintername);
1432 /* note that we do NOT default the availability flag to True - */
1433 /* we take it from the default service passed. This allows all */
1434 /* dynamic printers to be disabled by disabling the [printers] */
1435 /* entry (if/when the 'available' keyword is implemented!). */
1437 /* the printer name is set to the service name. */
1438 string_set(&iSERVICE(i).szPrintername,pszPrintername);
1439 string_set(&iSERVICE(i).comment,comment);
1440 iSERVICE(i).bBrowseable = sDefault.bBrowseable;
1441 /* Printers cannot be read_only. */
1442 iSERVICE(i).bRead_only = False;
1443 /* No share modes on printer services. */
1444 iSERVICE(i).bShareModes = False;
1445 /* No oplocks on printer services. */
1446 iSERVICE(i).bOpLocks = False;
1447 /* Printer services must be printable. */
1448 iSERVICE(i).bPrint_ok = True;
1450 DEBUG(3,("adding printer service %s\n",pszPrintername));
1456 /***************************************************************************
1457 Do a case-insensitive, whitespace-ignoring string compare.
1458 ***************************************************************************/
1459 static int strwicmp(char *psz1, char *psz2)
1461 /* if BOTH strings are NULL, return TRUE, if ONE is NULL return */
1462 /* appropriate value. */
1472 /* sync the strings on first non-whitespace */
1475 while (isspace(*psz1))
1477 while (isspace(*psz2))
1479 if (toupper(*psz1) != toupper(*psz2) || *psz1 == '\0' || *psz2 == '\0')
1484 return (*psz1 - *psz2);
1487 /***************************************************************************
1488 Map a parameter's string representation to something we can use.
1489 Returns False if the parameter string is not recognised, else TRUE.
1490 ***************************************************************************/
1491 static int map_parameter(char *pszParmName)
1495 if (*pszParmName == '-')
1498 for (iIndex = 0; parm_table[iIndex].label; iIndex++)
1499 if (strwicmp(parm_table[iIndex].label, pszParmName) == 0)
1502 DEBUG(0,( "Unknown parameter encountered: \"%s\"\n", pszParmName));
1507 /***************************************************************************
1508 Set a boolean variable from the text value stored in the passed string.
1509 Returns True in success, False if the passed string does not correctly
1510 represent a boolean.
1511 ***************************************************************************/
1512 static BOOL set_boolean(BOOL *pb, char *pszParmValue)
1517 if (strwicmp(pszParmValue, "yes") == 0 ||
1518 strwicmp(pszParmValue, "true") == 0 ||
1519 strwicmp(pszParmValue, "1") == 0)
1522 if (strwicmp(pszParmValue, "no") == 0 ||
1523 strwicmp(pszParmValue, "False") == 0 ||
1524 strwicmp(pszParmValue, "0") == 0)
1528 DEBUG(0,( "Badly formed boolean in configuration file: \"%s\".\n",
1535 /***************************************************************************
1536 Find a service by name. Otherwise works like get_service.
1537 ***************************************************************************/
1538 static int getservicebyname(char *pszServiceName, service *pserviceDest)
1542 for (iService = iNumServices - 1; iService >= 0; iService--)
1543 if (VALID(iService) &&
1544 strwicmp(iSERVICE(iService).szService, pszServiceName) == 0)
1546 if (pserviceDest != NULL)
1547 copy_service(pserviceDest, pSERVICE(iService), NULL);
1556 /***************************************************************************
1557 Copy a service structure to another
1559 If pcopymapDest is NULL then copy all fields
1560 ***************************************************************************/
1561 static void copy_service(service *pserviceDest,
1562 service *pserviceSource,
1566 BOOL bcopyall = (pcopymapDest == NULL);
1568 for (i=0;parm_table[i].label;i++)
1569 if (parm_table[i].ptr && parm_table[i].class == P_LOCAL &&
1570 (bcopyall || pcopymapDest[i]))
1572 void *def_ptr = parm_table[i].ptr;
1574 ((char *)pserviceSource) + PTR_DIFF(def_ptr,&sDefault);
1576 ((char *)pserviceDest) + PTR_DIFF(def_ptr,&sDefault);
1578 switch (parm_table[i].type)
1582 *(BOOL *)dest_ptr = *(BOOL *)src_ptr;
1588 *(int *)dest_ptr = *(int *)src_ptr;
1592 *(char *)dest_ptr = *(char *)src_ptr;
1596 string_set(dest_ptr,*(char **)src_ptr);
1600 string_set(dest_ptr,*(char **)src_ptr);
1601 strupper(*(char **)dest_ptr);
1610 init_copymap(pserviceDest);
1611 if (pserviceSource->copymap)
1612 memcpy((void *)pserviceDest->copymap,
1613 (void *)pserviceSource->copymap,sizeof(BOOL)*NUMPARAMETERS);
1617 /***************************************************************************
1618 Check a service for consistency. Return False if the service is in any way
1619 incomplete or faulty, else True.
1620 ***************************************************************************/
1621 static BOOL service_ok(int iService)
1626 if (iSERVICE(iService).szService[0] == '\0')
1628 DEBUG(0,( "The following message indicates an internal error:\n"));
1629 DEBUG(0,( "No service name in service entry.\n"));
1633 /* The [printers] entry MUST be printable. I'm all for flexibility, but */
1634 /* I can't see why you'd want a non-printable printer service... */
1635 if (strwicmp(iSERVICE(iService).szService,PRINTERS_NAME) == 0)
1636 if (!iSERVICE(iService).bPrint_ok)
1638 DEBUG(0,( "WARNING: [%s] service MUST be printable!\n",
1639 iSERVICE(iService).szService));
1640 iSERVICE(iService).bPrint_ok = True;
1643 if (iSERVICE(iService).szPath[0] == '\0' &&
1644 strwicmp(iSERVICE(iService).szService,HOMES_NAME) != 0)
1646 DEBUG(0,("No path in service %s - using %s\n",iSERVICE(iService).szService,tmpdir()));
1647 string_set(&iSERVICE(iService).szPath,tmpdir());
1650 /* If a service is flagged unavailable, log the fact at level 0. */
1651 if (!iSERVICE(iService).bAvailable)
1652 DEBUG(1,( "NOTE: Service %s is flagged unavailable.\n",
1653 iSERVICE(iService).szService));
1658 static struct file_lists {
1659 struct file_lists *next;
1662 } *file_lists = NULL;
1664 /*******************************************************************
1665 keep a linked list of all config files so we know when one has changed
1666 it's date and needs to be reloaded
1667 ********************************************************************/
1668 static void add_to_file_list(char *fname)
1670 struct file_lists *f=file_lists;
1673 if (f->name && !strcmp(f->name,fname)) break;
1678 f = (struct file_lists *)malloc(sizeof(file_lists[0]));
1680 f->next = file_lists;
1681 f->name = strdup(fname);
1692 standard_sub_basic(n2);
1693 f->modtime = file_modtime(n2);
1698 /*******************************************************************
1699 check if a config file has changed date
1700 ********************************************************************/
1701 BOOL lp_file_list_changed(void)
1703 struct file_lists *f = file_lists;
1704 DEBUG(6,("lp_file_list_changed()\n"));
1711 pstrcpy(n2,f->name);
1712 standard_sub_basic(n2);
1714 DEBUGADD( 6, ( "file %s -> %s last mod_time: %s\n",
1715 f->name, n2, ctime(&f->modtime) ) );
1717 mod_time = file_modtime(n2);
1719 if (f->modtime != mod_time) {
1720 DEBUGADD(6,("file %s modified: %s\n", n2, ctime(&mod_time)));
1721 f->modtime = mod_time;
1729 /***************************************************************************
1730 handle the interpretation of the coding system parameter
1731 *************************************************************************/
1732 static BOOL handle_coding_system(char *pszParmValue,char **ptr)
1734 string_set(ptr,pszParmValue);
1735 interpret_coding_system(pszParmValue);
1739 /***************************************************************************
1740 handle the interpretation of the character set system parameter
1741 ***************************************************************************/
1742 static BOOL handle_character_set(char *pszParmValue,char **ptr)
1744 string_set(ptr,pszParmValue);
1745 interpret_character_set(pszParmValue);
1750 /***************************************************************************
1751 handle the valid chars lines
1752 ***************************************************************************/
1753 static BOOL handle_valid_chars(char *pszParmValue,char **ptr)
1755 string_set(ptr,pszParmValue);
1757 /* A dependency here is that the parameter client code page must be
1758 set before this is called - as calling codepage_initialise()
1759 would overwrite the valid char lines.
1761 codepage_initialise(lp_client_code_page());
1763 add_char_string(pszParmValue);
1768 /***************************************************************************
1769 handle the include operation
1770 ***************************************************************************/
1771 static BOOL handle_include(char *pszParmValue,char **ptr)
1774 pstrcpy(fname,pszParmValue);
1776 add_to_file_list(fname);
1778 standard_sub_basic(fname);
1780 string_set(ptr,fname);
1782 if (file_exist(fname,NULL))
1783 return(pm_process(fname, do_section, do_parameter));
1785 DEBUG(2,("Can't find include file %s\n",fname));
1791 /***************************************************************************
1792 handle the interpretation of the copy parameter
1793 ***************************************************************************/
1794 static BOOL handle_copy(char *pszParmValue,char **ptr)
1798 service serviceTemp;
1800 string_set(ptr,pszParmValue);
1802 init_service(&serviceTemp);
1806 DEBUG(3,("Copying service from service %s\n",pszParmValue));
1808 if ((iTemp = getservicebyname(pszParmValue, &serviceTemp)) >= 0)
1810 if (iTemp == iServiceIndex)
1812 DEBUG(0,("Can't copy service %s - unable to copy self!\n",
1817 copy_service(pSERVICE(iServiceIndex),
1819 iSERVICE(iServiceIndex).copymap);
1825 DEBUG(0,( "Unable to copy service - source not found: %s\n",
1830 free_service(&serviceTemp);
1835 /***************************************************************************
1836 initialise a copymap
1837 ***************************************************************************/
1838 static void init_copymap(service *pservice)
1841 if (pservice->copymap) free(pservice->copymap);
1842 pservice->copymap = (BOOL *)malloc(sizeof(BOOL)*NUMPARAMETERS);
1843 if (!pservice->copymap)
1844 DEBUG(0,("Couldn't allocate copymap!! (size %d)\n",NUMPARAMETERS));
1846 for (i=0;i<NUMPARAMETERS;i++)
1847 pservice->copymap[i] = True;
1851 /***************************************************************************
1852 return the local pointer to a parameter given the service number and the
1853 pointer into the default structure
1854 ***************************************************************************/
1855 void *lp_local_ptr(int snum, void *ptr)
1857 return (void *)(((char *)pSERVICE(snum)) + PTR_DIFF(ptr,&sDefault));
1860 /***************************************************************************
1861 Process a parameter for a particular service number. If snum < 0
1862 then assume we are in the globals
1863 ***************************************************************************/
1864 BOOL lp_do_parameter(int snum, char *pszParmName, char *pszParmValue)
1867 void *parm_ptr=NULL; /* where we are going to store the result */
1870 parmnum = map_parameter(pszParmName);
1874 DEBUG(0,( "Ignoring unknown parameter \"%s\"\n", pszParmName));
1878 def_ptr = parm_table[parmnum].ptr;
1880 /* we might point at a service, the default service or a global */
1884 if (parm_table[parmnum].class == P_GLOBAL) {
1885 DEBUG(0,( "Global parameter %s found in service section!\n",pszParmName));
1888 parm_ptr = ((char *)pSERVICE(snum)) + PTR_DIFF(def_ptr,&sDefault);
1892 if (!iSERVICE(snum).copymap)
1893 init_copymap(pSERVICE(snum));
1895 /* this handles the aliases - set the copymap for other entries with
1896 the same data pointer */
1897 for (i=0;parm_table[i].label;i++)
1898 if (parm_table[i].ptr == parm_table[parmnum].ptr)
1899 iSERVICE(snum).copymap[i] = False;
1902 /* if it is a special case then go ahead */
1903 if (parm_table[parmnum].special) {
1904 parm_table[parmnum].special(pszParmValue,(char **)parm_ptr);
1908 /* now switch on the type of variable it is */
1909 switch (parm_table[parmnum].type)
1912 set_boolean(parm_ptr,pszParmValue);
1916 set_boolean(parm_ptr,pszParmValue);
1917 *(BOOL *)parm_ptr = ! *(BOOL *)parm_ptr;
1921 *(int *)parm_ptr = atoi(pszParmValue);
1925 *(char *)parm_ptr = *pszParmValue;
1929 sscanf(pszParmValue,"%o",(int *)parm_ptr);
1933 string_set(parm_ptr,pszParmValue);
1937 string_set(parm_ptr,pszParmValue);
1938 strupper(*(char **)parm_ptr);
1942 pstrcpy((char *)parm_ptr,pszParmValue);
1946 pstrcpy((char *)parm_ptr,pszParmValue);
1947 strupper((char *)parm_ptr);
1951 for (i=0;parm_table[parmnum].enum_list[i].name;i++) {
1952 if (strequal(pszParmValue, parm_table[parmnum].enum_list[i].name)) {
1953 *(int *)parm_ptr = parm_table[parmnum].enum_list[i].value;
1965 /***************************************************************************
1966 Process a parameter.
1967 ***************************************************************************/
1968 static BOOL do_parameter( char *pszParmName, char *pszParmValue )
1970 if( !bInGlobalSection && bGlobalOnly )
1973 DEBUGADD( 3, ( "doing parameter %s = %s\n", pszParmName, pszParmValue ) );
1975 return( lp_do_parameter( bInGlobalSection ? -2 : iServiceIndex,
1981 /***************************************************************************
1982 print a parameter of the specified type
1983 ***************************************************************************/
1984 static void print_parameter(struct parm_struct *p,void *ptr, FILE *f)
1989 for (i=0;p->enum_list[i].name;i++) {
1990 if (*(int *)ptr == p->enum_list[i].value) {
1991 fprintf(f,"%s",p->enum_list[i].name);
1998 fprintf(f,"%s",BOOLSTR(*(BOOL *)ptr));
2002 fprintf(f,"%s",BOOLSTR(! *(BOOL *)ptr));
2006 fprintf(f,"%d",*(int *)ptr);
2010 fprintf(f,"%c",*(char *)ptr);
2014 fprintf(f,"0%o",*(int *)ptr);
2020 fprintf(f,"%s",(char *)ptr);
2026 fprintf(f,"%s",*(char **)ptr);
2034 /***************************************************************************
2035 check if two parameters are equal
2036 ***************************************************************************/
2037 static BOOL equal_parameter(parm_type type,void *ptr1,void *ptr2)
2043 return(*((BOOL *)ptr1) == *((BOOL *)ptr2));
2048 return(*((int *)ptr1) == *((int *)ptr2));
2051 return(*((char *)ptr1) == *((char *)ptr2));
2056 char *p1 = (char *)ptr1, *p2 = (char *)ptr2;
2057 if (p1 && !*p1) p1 = NULL;
2058 if (p2 && !*p2) p2 = NULL;
2059 return(p1==p2 || strequal(p1,p2));
2064 char *p1 = *(char **)ptr1, *p2 = *(char **)ptr2;
2065 if (p1 && !*p1) p1 = NULL;
2066 if (p2 && !*p2) p2 = NULL;
2067 return(p1==p2 || strequal(p1,p2));
2075 /***************************************************************************
2076 Process a new section (service). At this stage all sections are services.
2077 Later we'll have special sections that permit server parameters to be set.
2078 Returns True on success, False on failure.
2079 ***************************************************************************/
2080 static BOOL do_section(char *pszSectionName)
2083 BOOL isglobal = ((strwicmp(pszSectionName, GLOBAL_NAME) == 0) ||
2084 (strwicmp(pszSectionName, GLOBAL_NAME2) == 0));
2087 /* if we were in a global section then do the local inits */
2088 if (bInGlobalSection && !isglobal)
2091 /* if we've just struck a global section, note the fact. */
2092 bInGlobalSection = isglobal;
2094 /* check for multiple global sections */
2095 if (bInGlobalSection)
2097 DEBUG( 3, ( "Processing section \"[%s]\"\n", pszSectionName ) );
2101 if (!bInGlobalSection && bGlobalOnly) return(True);
2103 /* if we have a current service, tidy it up before moving on */
2106 if (iServiceIndex >= 0)
2107 bRetval = service_ok(iServiceIndex);
2109 /* if all is still well, move to the next record in the services array */
2112 /* We put this here to avoid an odd message order if messages are */
2113 /* issued by the post-processing of a previous section. */
2114 DEBUG(2,( "Processing section \"[%s]\"\n", pszSectionName));
2116 if ((iServiceIndex=add_a_service(&sDefault,pszSectionName)) < 0)
2118 DEBUG(0,("Failed to add a new service\n"));
2127 /***************************************************************************
2128 determine if a partcular base parameter is currently set to the default value.
2129 ***************************************************************************/
2130 static BOOL is_default(int i)
2132 if (!defaults_saved) return False;
2133 switch (parm_table[i].type) {
2136 return strequal(parm_table[i].def.svalue,*(char **)parm_table[i].ptr);
2139 return strequal(parm_table[i].def.svalue,(char *)parm_table[i].ptr);
2142 return parm_table[i].def.bvalue == *(BOOL *)parm_table[i].ptr;
2144 return parm_table[i].def.cvalue == *(char *)parm_table[i].ptr;
2148 return parm_table[i].def.ivalue == *(int *)parm_table[i].ptr;
2156 /***************************************************************************
2157 Display the contents of the global structure.
2158 ***************************************************************************/
2159 static void dump_globals(FILE *f)
2162 fprintf(f, "# Global parameters\n");
2164 for (i=0;parm_table[i].label;i++)
2165 if (parm_table[i].class == P_GLOBAL &&
2166 parm_table[i].ptr &&
2167 (i == 0 || (parm_table[i].ptr != parm_table[i-1].ptr))) {
2168 if (defaults_saved && is_default(i)) continue;
2169 fprintf(f,"\t%s = ",parm_table[i].label);
2170 print_parameter(&parm_table[i],parm_table[i].ptr, f);
2175 /***************************************************************************
2176 return True if a local parameter is currently set to the global default
2177 ***************************************************************************/
2178 BOOL lp_is_default(int snum, struct parm_struct *parm)
2180 int pdiff = PTR_DIFF(parm->ptr,&sDefault);
2182 return equal_parameter(parm->type,
2183 ((char *)pSERVICE(snum)) + pdiff,
2184 ((char *)&sDefault) + pdiff);
2188 /***************************************************************************
2189 Display the contents of a single services record.
2190 ***************************************************************************/
2191 static void dump_a_service(service *pService, FILE *f)
2194 if (pService != &sDefault)
2195 fprintf(f,"\n[%s]\n",pService->szService);
2197 for (i=0;parm_table[i].label;i++)
2198 if (parm_table[i].class == P_LOCAL &&
2199 parm_table[i].ptr &&
2200 (*parm_table[i].label != '-') &&
2201 (i == 0 || (parm_table[i].ptr != parm_table[i-1].ptr))) {
2202 int pdiff = PTR_DIFF(parm_table[i].ptr,&sDefault);
2204 if (pService == &sDefault) {
2205 if (defaults_saved && is_default(i)) continue;
2207 if (equal_parameter(parm_table[i].type,
2208 ((char *)pService) + pdiff,
2209 ((char *)&sDefault) + pdiff))
2213 fprintf(f,"\t%s = ",parm_table[i].label);
2214 print_parameter(&parm_table[i],
2215 ((char *)pService) + pdiff, f);
2221 /***************************************************************************
2222 return info about the next service in a service. snum==-1 gives the globals
2224 return NULL when out of parameters
2225 ***************************************************************************/
2226 struct parm_struct *lp_next_parameter(int snum, int *i, int allparameters)
2229 /* do the globals */
2230 for (;parm_table[*i].label;(*i)++) {
2231 if (parm_table[*i].class == P_SEPARATOR)
2232 return &parm_table[(*i)++];
2234 if (!parm_table[*i].ptr || (*parm_table[*i].label == '-'))
2237 if ((*i) > 0 && (parm_table[*i].ptr == parm_table[(*i)-1].ptr))
2240 return &parm_table[(*i)++];
2243 service *pService = pSERVICE(snum);
2245 for (;parm_table[*i].label;(*i)++) {
2246 if (parm_table[*i].class == P_SEPARATOR)
2247 return &parm_table[(*i)++];
2249 if (parm_table[*i].class == P_LOCAL &&
2250 parm_table[*i].ptr &&
2251 (*parm_table[*i].label != '-') &&
2253 (parm_table[*i].ptr != parm_table[(*i)-1].ptr))) {
2254 int pdiff = PTR_DIFF(parm_table[*i].ptr,&sDefault);
2256 if (allparameters ||
2257 !equal_parameter(parm_table[*i].type,
2258 ((char *)pService) + pdiff,
2259 ((char *)&sDefault) + pdiff)) {
2260 return &parm_table[(*i)++];
2271 /***************************************************************************
2272 Display the contents of a single copy structure.
2273 ***************************************************************************/
2274 static void dump_copy_map(BOOL *pcopymap)
2277 if (!pcopymap) return;
2279 printf("\n\tNon-Copied parameters:\n");
2281 for (i=0;parm_table[i].label;i++)
2282 if (parm_table[i].class == P_LOCAL &&
2283 parm_table[i].ptr && !pcopymap[i] &&
2284 (i == 0 || (parm_table[i].ptr != parm_table[i-1].ptr)))
2286 printf("\t\t%s\n",parm_table[i].label);
2291 /***************************************************************************
2292 Return TRUE if the passed service number is within range.
2293 ***************************************************************************/
2294 BOOL lp_snum_ok(int iService)
2296 return (LP_SNUM_OK(iService) && iSERVICE(iService).bAvailable);
2300 /***************************************************************************
2301 auto-load some homes and printer services
2302 ***************************************************************************/
2303 static void lp_add_auto_services(char *str)
2307 int homes, printers;
2315 homes = lp_servicenumber(HOMES_NAME);
2316 printers = lp_servicenumber(PRINTERS_NAME);
2318 for (p=strtok(s,LIST_SEP);p;p=strtok(NULL,LIST_SEP))
2320 char *home = get_home_dir(p);
2322 if (lp_servicenumber(p) >= 0) continue;
2324 if (home && homes >= 0)
2326 lp_add_home(p,homes,home);
2330 if (printers >= 0 && pcap_printername_ok(p,NULL))
2331 lp_add_printer(p,printers);
2336 /***************************************************************************
2337 auto-load one printer
2338 ***************************************************************************/
2339 static void lp_add_one_printer(char *name,char *comment)
2341 int printers = lp_servicenumber(PRINTERS_NAME);
2344 if (lp_servicenumber(name) < 0)
2346 lp_add_printer(name,printers);
2347 if ((i=lp_servicenumber(name)) >= 0)
2348 string_set(&iSERVICE(i).comment,comment);
2353 /***************************************************************************
2354 auto-load printer services
2355 ***************************************************************************/
2356 static void lp_add_all_printers(void)
2358 int printers = lp_servicenumber(PRINTERS_NAME);
2360 if (printers < 0) return;
2362 pcap_printer_fn(lp_add_one_printer);
2365 /***************************************************************************
2366 have we loaded a services file yet?
2367 ***************************************************************************/
2368 BOOL lp_loaded(void)
2373 /***************************************************************************
2374 unload unused services
2375 ***************************************************************************/
2376 void lp_killunused(BOOL (*snumused)(int ))
2379 for (i=0;i<iNumServices;i++)
2380 if (VALID(i) && (!snumused || !snumused(i)))
2382 iSERVICE(i).valid = False;
2383 free_service(pSERVICE(i));
2388 /***************************************************************************
2389 save the curent values of all global and sDefault parameters into the
2390 defaults union. This allows swat and testparm to show only the
2391 changed (ie. non-default) parameters.
2392 ***************************************************************************/
2393 static void lp_save_defaults(void)
2396 for (i = 0; parm_table[i].label; i++) {
2397 if (i>0 && parm_table[i].ptr == parm_table[i-1].ptr) continue;
2398 switch (parm_table[i].type) {
2401 parm_table[i].def.svalue = strdup(*(char **)parm_table[i].ptr);
2405 parm_table[i].def.svalue = strdup((char *)parm_table[i].ptr);
2409 parm_table[i].def.bvalue = *(BOOL *)parm_table[i].ptr;
2412 parm_table[i].def.cvalue = *(char *)parm_table[i].ptr;
2417 parm_table[i].def.ivalue = *(int *)parm_table[i].ptr;
2423 defaults_saved = True;
2427 /***************************************************************************
2428 Load the services array from the services file. Return True on success,
2430 ***************************************************************************/
2431 BOOL lp_load(char *pszFname,BOOL global_only, BOOL save_defaults, BOOL add_ipc)
2436 add_to_file_list(pszFname);
2440 bInGlobalSection = True;
2441 bGlobalOnly = global_only;
2445 if (save_defaults) {
2450 pstrcpy(n2,pszFname);
2451 standard_sub_basic(n2);
2453 /* We get sections first, so have to start 'behind' to make up */
2455 bRetval = pm_process(n2, do_section, do_parameter);
2457 /* finish up the last section */
2458 DEBUG(3,("pm_process() returned %s\n", BOOLSTR(bRetval)));
2460 if (iServiceIndex >= 0)
2461 bRetval = service_ok(iServiceIndex);
2463 lp_add_auto_services(lp_auto_services());
2464 if (lp_load_printers())
2465 lp_add_all_printers();
2470 set_default_server_announce_type();
2478 /***************************************************************************
2479 return the max number of services
2480 ***************************************************************************/
2481 int lp_numservices(void)
2483 return(iNumServices);
2486 /***************************************************************************
2487 Display the contents of the services array in human-readable form.
2488 ***************************************************************************/
2489 void lp_dump(FILE *f, BOOL show_defaults)
2493 if (show_defaults) {
2494 defaults_saved = False;
2499 dump_a_service(&sDefault, f);
2501 for (iService = 0; iService < iNumServices; iService++)
2503 if (VALID(iService))
2505 if (iSERVICE(iService).szService[0] == '\0')
2507 dump_a_service(pSERVICE(iService), f);
2513 /***************************************************************************
2514 Return the number of the service with the given name, or -1 if it doesn't
2515 exist. Note that this is a DIFFERENT ANIMAL from the internal function
2516 getservicebyname()! This works ONLY if all services have been loaded, and
2517 does not copy the found service.
2518 ***************************************************************************/
2519 int lp_servicenumber(char *pszServiceName)
2523 for (iService = iNumServices - 1; iService >= 0; iService--)
2524 if (VALID(iService) &&
2525 strequal(lp_servicename(iService), pszServiceName))
2529 DEBUG(7,("lp_servicenumber: couldn't find %s\n",pszServiceName));
2534 /*******************************************************************
2535 a useful volume label function
2536 ******************************************************************/
2537 char *volume_label(int snum)
2539 char *ret = lp_volume(snum);
2540 if (!*ret) return(lp_servicename(snum));
2546 * nmbd only loads the global section. There seems to be no way to
2547 * determine exactly is a service is printable by only looking at the
2548 * [global] section so for now always announce as a print server. This
2549 * will need looking at in the future. Jeremy (jallison@whistle.com).
2551 /*******************************************************************
2552 Return true if any printer services are defined.
2553 ******************************************************************/
2554 static BOOL lp_printer_services(void)
2558 for (iService = iNumServices - 1; iService >= 0; iService--)
2559 if (VALID(iService) && iSERVICE(iService).bPrint_ok)
2565 /*******************************************************************
2566 Set the server type we will announce as via nmbd.
2567 ********************************************************************/
2568 static void set_default_server_announce_type()
2570 default_server_announce = (SV_TYPE_WORKSTATION | SV_TYPE_SERVER |
2571 SV_TYPE_SERVER_UNIX | SV_TYPE_PRINTQ_SERVER);
2572 if(lp_announce_as() == ANNOUNCE_AS_NT)
2573 default_server_announce |= (SV_TYPE_SERVER_NT | SV_TYPE_NT);
2574 else if(lp_announce_as() == ANNOUNCE_AS_WIN95)
2575 default_server_announce |= SV_TYPE_WIN95_PLUS;
2576 else if(lp_announce_as() == ANNOUNCE_AS_WFW)
2577 default_server_announce |= SV_TYPE_WFW;
2578 default_server_announce |= (lp_time_server() ? SV_TYPE_TIME_SOURCE : 0);
2580 * nmbd only loads the [global] section. There seems to be no way to
2581 * determine exactly if any service is printable by only looking at the
2582 * [global] section so for now always announce as a print server. This
2583 * will need looking at in the future. Jeremy (jallison@whistle.com).
2586 default_server_announce |= (lp_printer_services() ? SV_TYPE_PRINTQ_SERVER : 0);
2591 /*******************************************************************
2593 ********************************************************************/
2594 void lp_rename_service(int snum, char *new_name)
2596 string_set(&pSERVICE(snum)->szService, new_name);
2599 /*******************************************************************
2601 ********************************************************************/
2602 void lp_remove_service(int snum)
2604 pSERVICE(snum)->valid = False;
2607 /*******************************************************************
2609 ********************************************************************/
2610 void lp_copy_service(int snum, char *new_name)
2612 char *oldname = lp_servicename(snum);
2613 do_section(new_name);
2615 snum = lp_servicenumber(new_name);
2617 lp_do_parameter(snum, "copy", oldname);
2622 /*******************************************************************
2623 Get the default server type we will announce as via nmbd.
2624 ********************************************************************/
2625 int lp_default_server_announce(void)
2627 return default_server_announce;
2630 /*******************************************************************
2631 Split the announce version into major and minor numbers.
2632 ********************************************************************/
2633 int lp_major_announce_version(void)
2635 static BOOL got_major = False;
2636 static int major_version = DEFAULT_MAJOR_VERSION;
2641 return major_version;
2644 if((vers = lp_announce_version()) == NULL)
2645 return major_version;
2647 if((p = strchr(vers, '.')) == 0)
2648 return major_version;
2651 major_version = atoi(vers);
2652 return major_version;
2655 int lp_minor_announce_version(void)
2657 static BOOL got_minor = False;
2658 static int minor_version = DEFAULT_MINOR_VERSION;
2663 return minor_version;
2666 if((vers = lp_announce_version()) == NULL)
2667 return minor_version;
2669 if((p = strchr(vers, '.')) == 0)
2670 return minor_version;
2673 minor_version = atoi(p);
2674 return minor_version;
2677 /***********************************************************
2678 Set the global name resolution order (used in smbclient).
2679 ************************************************************/
2681 void lp_set_name_resolve_order(char *new_order)
2683 Globals.szNameResolveOrder = new_order;