Exploring Samba's new registry-based configuration

New Dance


Samba's new registry-based configuration system conserves resources and lets the administrator configure entire clusters with a single command.

By Michael Adam

Eric Gevaert, 123RF

As most Linux users know, Samba [1] is an open source file and print system that provides interoperability with Windows environments. For more that 15 years, Samba has managed configuration settings through the plain-text file smb.conf. With the release of Samba 3.2.0 in July 2008, this paradigm of plain-text-only configuration is no longer the only option. A new configuration back end can store the configuration data in Samba's internal registry database. The default behavior is the same as before, but if you explicitly enable registry-based configuration through smb.conf, you can manage your Samba settings through a Windows-style registry.

Registry-based configuration opens many new options, such as remote administration and administration of Samba from Windows computers.

Why a Registry?

Samba has always maintained a registry database so that Windows clients could access the registry over the WINREG RPC interface to retrieve information for the connection. (Figure 1 shows WINREG access of a Windows client connecting to a Windows server.) Until recently, however, Samba did not use the registry for any other purposes.

Figure 1: Wireshark reveals registry access as a Windows client accesses a Windows server.

The conventional text-based configuration system (see the box titled "Traditional Samba") is very flexible, very convenient, and very easy to use. In fact, you can configure your Samba implementation with nothing more than your favorite text editor. However, some special use cases create new demands that reduce the effectiveness of the text configuration model.

Traditional Samba

Samba's traditional plain-text configuration uses the very simple syntax of INI files well known to Windows users. This approach is also used by several Linux/Unix programs.

The smb.conf configuration file consists of sections and parameters. The file format is line oriented: Each line represents a comment, a configuration parameter, or the beginning of a new section.

  • Lines starting with a semicolon (;) or a hash sign (#) are comment lines.
  • A new section is initiated by a name in brackets: [share1].
  • A parameter consists of a parameter name and the assigned parameter value, separated by an equals sign (=), and it is associated with the last section started. The value can be a boolean value (yes/no), an integer value, or a general string.

Sections can be started multiple times, and the same parameter can be specified several times. The last occurrence of a parameter in one section overrides earlier instances of it in the same section.

The section [global] has a special meaning. Whereas all other sections define shared resources, the [global] section contains the parameters that control the overall behavior of the Samba daemon and the default values for the share parameters. The two other share names that have a special meaning are [homes] and [printers]. These sections dynamically create shares when they are configured appropriately. The manual page of the smb.conf configuration file has all the details on the syntax and the semantics.

The text configuration can be structured with the meta directives include and config file. Whereas config file simply drops all configuration data read so far and switches the configuration source to the specified file, the include directive builds up a whole tree of config files. An include file is parsed when its include statement is encountered within the parent file. The options read from the included file are activated in place of the include file. This means that options read before the include could be overwritten by parameters inside the include; on the other hand, side parameters set inside the include can be overwritten by parameters that occur after the include.

An interesting dynamic aspect is added with the possibility of expanding run-time macros in the configuration file. Table 1 shows some of the most important macros. These macros are useful for tasks such as configuring individual logging for specific clients.

Listing 1 shows an example configuration file that demonstrates sections, comments, includes, and macros. It should be noted that the server reads the complete configuration at startup and builds up the list of shares. Then the server periodically checks to see whether one of the configuration files has changed and, if so, reloads the whole configuration.

Listing 1: Sample smb.conf
01 [global]
02     netbios name = fileserver
03     work group = samba
04     passdb backend = user
05
06     ; debugging options
07     log level = 3
08     max log size = 10000
09     debug hires timestamp = yes
10
11     # include client specific configuration
12     include = /etc/samba/smb.conf.%I
13
14 [homes]
15     valid users = %S
16     brosweable = no
17     writeable = yes
18
19 [share1]
20     path = /data/share1
21     read only = no

One disadvantage that often appears on large networks is memory consumption: A client is only connected to one share, but the Samba daemon process that serves this connection builds up the entire list of shares the same. On a 64-bit machine, a share structure internally consumes about 1KB of memory. So when the configuration contains a thousand shares, the smbd daemon wastes around 1MB of RAM. When a thousand clients are connected to the server, 1GB of RAM is wasted.

Worse still, when the configuration file is changed, a thousand clients will start re-reading smb.conf, which will be some 250KB or more. All these near-simultaneous read operations will have a noticeable effect not only on the I/O performance of the server, but also on the CPU load because the thousand shares read from the file must be compared with and integrated into the internal list of shares already constructed the first time. These performance problems have hit production servers in the past, and admins have created workarounds, but these improvised solutions are just band-aids.

Usability issues include:

These disadvantages disappear when the configuration parameters are stored in a database. The cluster configuration would suggest a Trival Database (TDB) [3] structure, which could then be distributed to all cluster nodes automatically by CTDB [4]. The approach that had been started in 2007 and was officially released in July 2008 with Samba 3.2 is to use Samba's registry database, because it has a data model that fits pretty nicely on the schema of sections and parameters of smb.conf. Samba stores its registry in a TDB database called registry.tdb

The Windows Registry

The registry organizes its data in a tree structure of keys: a registry key consists of a name, a list of its subkeys, and a list of its registry values. A value comprises a name and the value data. Samba now stores the configuration data in the following registry key

HKLM\Software\Samba\smbconf

which is sometimes called the smbconf key. The sections in an smb.conf file correspond to the subkeys in this key; the configuration parameters match the registry values in the corresponding subkey.

One should imagine the contents of the smbconf key as a parsed but not otherwise interpreted or activated smb.conf file. Just like the smb.conf file syntax, the registry does not differentiate between the global section and the share definitions. Because the registry is a database with keys and values, it does not support a fixed order or multiple parameter records.

The include statements need special treatment - they are not configuration parameters as such, but meta directives that are activated at the time of parsing. An include directive can be specified multiple times with different values, and the order and placement of the real parameters are very important in this case. Because the parameters stored in the registry do not have a guaranteed order, registry configuration can only offer a compromise with respect to the treatment of include statements: For registry configuration, Samba maintains one ordered list of include statements per section that is only evaluated at the end of the section, after the parameters have been activated.

Activating Registry Configuration

In current Samba code, the smb.conf text configuration file is still the initial source of configuration. The administrator can enable the registry configuration in three stages, always starting with smb.conf.

The parameter registry shares = yes in the [global] section of smb.conf tells Samba to read share definitions from the registry. In contrast to the text-based configuration, smbd does not read all registry-based share definitions when launching; it only picks up the individual shares at run time - a share is loaded just as the client connects to it.

This approach solves the memory consumption problem. If a share is defined in the registry and also in smb.conf, these definitions are not merged, and the text-based variant wins.

smbd does not pick this list up from the registry when launching, in contrast to shares defined in a configuration file, but loads it at run time. If shares with the same name are in the registry and in smb.conf, the text-based variant wins. So when registry shares are active, it is advisable not to use text-defined shares at all in order to avoid confusion.

A special new semantic for the directive include = registry in the [global] section of the smb.conf file, which is frequently used for clustering, mixes global registry options with the text-based configuration. The full semantics of the include statement are kept for the global options: parameters that occur before include = registry in smb.conf can be overwritten by registry parameters, and global parameters from the registry can be overwritten by global parameters from smb.conf that are specified after include = registry.

Setting include = registry implicitly activates registry shares. Be careful when you mix text and registry-based configurations - for example, the lock directory parameter is a sure-fire way of telling the registry to shoot itself in the foot because, among other things, it sets the location where Samba looks for its registry database.

The recommended way of using include = registry is to have an initial portion of configuration in the [global] section of smb.conf and conclude the section and the file with include = registry. Listing 2 shows a minimal configuration for use in clustered environments.

Listing 2: smb.conf for a Cluster
01 [global]
02 clustering = yes
03 include = registry

To change the whole configuration file using config file, admins can use a new meta directive, config backend = registry in the global section of smb.conf, to stipulate a registry-only configuration. This directive tells Samba to discard any settings it has parsed from smb.conf and rely entirely on the global parameters read from the registry. Again, the directive implies registry shares = yes.

Registry Configuration in the Cluster

A cluster setup faces the inherent chicken and egg problem: The registry is stored in the registry.tdb database, and CTDB has to distribute it across the cluster. To enable distribution of the registry, the administrator initially needs to configure Samba with the clustering = yes option set before registry globals are read. So unfortunately, the registry-only configuration with config backend = registry is not an option here. Instead, the admin should copy the minimal smb.conf file in Listing 2 as a default configuration to all cluster nodes once. Afterwards, the whole Samba cluster can be configured centrally through the registry.

Accessing Registry Configuration Data

Samba provides several approaches for editing the registry. Before you can modify the Samba registry, you need to enable remote access for your designated management account using the following command:

net rpc rights grant user SeDiskOperatorPrivilege

regedit.exe

Because the registry is available remotely over the WINREG RPC interface when the Samba daemon smbd is running, the most obvious method of access is through the Windows registry editor regedit.exe (Figure 2).

Figure 2: Editing the Samba 3.2 configuration with the registry editor, regedit.exe.

The advantage of the registry editor is that it gives the Windows admin the opportunity to configure a samba server with familiar tools. But in the long run, this method will probably be too awkward, even for hard-core Windows addicts.

net (rpc) registry

Samba's swiss army knife net basically has built-in command line versions of regedit: net registry to access the local registry and net rpc registry to access a remote registry over RPC. Although these tools are almost as clumsy as regedit, they do allow the administrator to produce more convenient custom tools with Unix shell scripts. Table 2 shows the available subcommands of net registry, and Listing 3 demonstrates an example of configuration tasks. The use of net rpc registry is completely analogous - you just call it as net -Uuser rpc registry ... or even net -Uuser%password rpc registry ... when it is too inconvenient to type the password at the prompt for each call.

Listing 3: Example net registry Session
01 # net registry
02 enumerate HKLM/software/samba/smbconf
03 Keyname   = share1
04 Modtime   = Thu, 01 Jan 1970 01:00:00 CET
05
06 Keyname   = global
07 Modtime   = Thu, 01 Jan 1970 01:00:00 CET
08
09 # net registry enumerate HKLM/software/samba/smbconf/global
10 Valuename  = netbios name
11 Type       = REG_SZ
12 Value      = "nirvana"
13
14 Valuename  = workgroup
15 Type       = REG_SZ
16 Value      = "samba"
17
18 Valuename  = security
19 Type       = REG_SZ
20 Value      = "user"
21
22 # net registry setvalue HKLM/software/samba/smbconf/global "passdb backend" SZ tdbsam
23 # net registry enumerate HKLM/software/samba/smbconf/global
24 Valuename  = netbios name
25 Type       = REG_SZ
26 Value      = "nirvana"
27
28 Valuename  = workgroup
29 Type       = REG_SZ
30 Value      = "samba"
31
32 Valuename  = security
33 Type       = REG_SZ
34 Value      = "user"
35
36 Valuename  = passdb backend
37 Type       = REG_SZ
38 Value      = "tdbsam"
39
40 # net registry deletevalue HKLM/software/samba/smbconf/global security
41 # net registry enumerate HKLM/software/samba/smbconf/global
42 Valuename  = netbios name
43 Type       = REG_SZ
44 Value      = "nirvana"
45
46 Valuename  = workgroup
47 Type       = REG_SZ
48 Value      = "samba"
49
50 Valuename  = passdb backend
51 Type       = REG_SZ
52 Value      = "tdbsam"

net conf

net registry is pretty chatty and clumsy for day-to-day administration tasks, so net now comes with a dedicated registry configuration interface offered by the new net conf command. Table 3 provides a summary of net conf options.

The net conf list command outputs the complete configuration in smb.conf format, whereas net conf import imports a smb.conf text file into the registry, dropping all previous data. This way, one can easily switch back and forth between registry- and text-based configuration if necessary (Listing 4).

Listing 4: Example net conf Session
01 # net conf list
02 # cat smb.conf.input
03 [global]
04         netbios name = nirvana
05         workgroup = samba
06         passdb backend = tdbsam
07         security = user
08
09 [share1]
10         path = /data/samba/shares/share1
11         read only = no
12         vfs objects = recycle
13
14 # net conf import smb.conf.input
15 # net conf list
16 [global]
17         netbios name = nirvana
18         workgroup = samba
19         passdb backend = tdbsam
20         security = user
21
22 [share1]
23         path = /data/samba/shares/share1
24         read only = no
25         vfs objects = recycle
26
27 # net conf setparm global "log level" 10
28 # net conf delparm global security
29 # net conf setincludes global /etc/samba/smb.conf.%I
30 # net conf setparm share2 path /data/samba/shares/share2
31 # net conf list
32 [global]
33         netbios name = nirvana
34         workgroup = samba
35         passdb backend = tdbsam
36         log level = 10
37         include = /etc/samba/smb.conf.%I
38
39 [share1]
40         path = /data/samba/shares/share1
41         read only = no
42         vfs objects = recycle
43
44 [share2]
45         path = /data/samba/shares/share2
46
47 # net conf drop
48 # net conf list
49 #

Writing GUIs

An abstraction layer called libsmbconf presents all necessary methods to access Samba's registry configuration from C code. net conf and the server use libsmbconf to access the registry. The Samba project site has more details on the API [5]. libsmbconf is not published as a shared library because of linking dependencies to a lot of Samba internal code that is not yet properly chopped into shared libraries. Eventually the idea is to release libsmbconf so that it's easy to write third-party applications to configure Samba. A first example application called netdomjoin-gui is available with the Samba code. netdomjoin-gui is a Gtk program that joins your Samba into an active directory domain, modifying the registry configuration accordingly. It is modeled on the native Windows join dialog. The code is under lib/netapi/examples/netdomjoin-gui in Samba's source tree.

To compile the application, use make -C lib/netapi/examples; afterwards, you will find the binary in lib/netapi/examples/bin/netdomjoin-gui. Starting with a smb.conf file that contains config backend = registry and an empty registry configuration, the administrator calls netdomjoin-gui (Figure 3). Listing 5 shows the registry configuration after the process is finished.

Figure 3: Launching the GUI to join an Active Directory domain.
Listing 5: Registry Configuration after the Join
01 [global]
02         workgroup = ADSVMW
03         security = ads
04         realm = ads.vmware.private

Conclusion

With Samba 3.2 and newer, the administrator can choose between traditional text-based configuration and the new registry configuration that brings many new features and opens up many new options. Even though the configuration is stored in a database, net conf lets you manage the configuration easily. This feature is extremely convenient in clustered environments with CTDB. The new configuration system also allows for remote configuration of Samba servers.

With additional work, it will be possible to create dedicated Samba configuration tools for Windows that use the remote registry interface. Then a Windows admin could configure samba servers without learning too much about the underlying Unix systems. At that stage, you might wonder whether you have reached too much interoperability.

INFO
[1] Samba project: http://www.samba.org/
[2] Samba team: http://www.samba.org/samba/team/
[3] TDB: http://tdb.samba.org/
[4] CTDB project: http://ctdb.samba.org
[5] "Samba's New Registry Based Configuration" by Michael Adam http://www.samba.org/~obnox/presentations/linux-kongress-2008/lk2008-obnox.pdf
THE AUTHOR

Michael Adam is a member of the international Samba developer team [2] and also the maintainer of the Samba software branches with cluster extensions. He works as a software developer and consultant for SerNet GmbH in Göttingen, Germany. He spends his leisure time with his wonderful wife and kids.