Kernel Configuration

You configure the OpenBSD kernel via text files. Like 4.4BSD, OpenBSD doesn’t offer a fancy graphical kernel configuration utility or menu-driven system. Each kernel configuration is on a single line, along with a label indicating the type of entry and a description. Pound signs (#) mark comments.

Configuration Entries

Kernel configuration entries fall into four general categories: options, device drivers, pseudo-devices, and keywords.

Options

Options are hardware-independent kernel functions. Options handle things like filesystems, networking protocols, and compatibility layers.

Option entries look like this:

option     FFS         # UFS
option     INET        # IP + ICMP + TCP + UDP
option     CRYPTO      # Cryptographic framework

To learn more about options, read the options(4) man page.

Device Drivers

Device drivers give the kernel the necessary software to interact with a piece of hardware. If you want your kernel to support a piece of hardware, it must include the appropriate device driver.

Device driver kernel configuration entries can be quite long. They might include flags or settings that tell the kernel where to find the device and how to initialize it. (ISA cards usually have a hard-coded IRQ and/or memory address.)

Device drivers have no common label, but their entry starts with the device name.

mainbus0 at root
cpu0     at mainbus?
fxp*     at pci?                         # EtherExpress 10/100B ethernet
wd*      at wdc? flags 0x0000
ec0      at isa? port 0x250 iomem 0xd8000 irq 9  # 3C503 ethernet

Pseudo-Devices

Pseudo-devices behave much like devices, but have no real hardware attached to them. Pseudo-devices are frequently abstractions that can be opened, read from, written to, and closed in the same way as real hardware.

For example, the loopback interface is a pseudo-device used for network connections to the local machine. (Your computer has no loopback network card, but the loopback interface behaves just like a real network card with an unusual MTU value.)

Pseudo-devices are labeled with pseudo-device.

pseudo-device   loop    # network loopback
pseudo-device   pf      # packet filter
pseudo-device   gre     # GRE encapsulation interface

Keywords

Finally, a handful of other keywords appear only once or rarely. These one-offs change how the kernel runs or how it’s built, and defy easy categorization. The following keywords may appear:

  • The machine keyword tells the kernel which architecture it should run on.

  • The makeoptions keyword tells the compiler how to build the kernel.

  • The include keyword means pull in another configuration file.

  • The maxusers value sets the size of some in-kernel tables.

You’ll find even less common keywords scattered in different kernel configurations.

machine         amd64
makeoptions     DEBUG="-g"  # compile full symbol table
include         "../../../conf/GENERIC"
maxusers        80          # estimated number of users

All of these affect the kernel in wildly different ways. You’ll find several of these keywords in any kernel, even GENERIC.

Configuring GENERIC

Let’s look at an actual kernel configuration. OpenBSD divides kernel configuration into machine-independent and machine-dependent files.

Machine-Independent Configuration

The machine-independent kernel configuration files are in /usr/src/sys/conf. The file /usr/src/sys/conf/GENERIC contains the machine-independent kernel configuration, which describes all of the features that OpenBSD supports on all hardware platforms. Every GENERIC kernel contains the configuration in this file. If you change this file, it will affect every kernel built that includes this file.

The machine-independent configuration file doesn’t contain device drivers; instead, devices are tied to particular hardware. This file won’t contain any special building instructions, because they vary from platform to platform. Nor will it include hard-coded system limits, data structure sizes, and so on, as OpenBSD running on a 25-year-old VAX has considerably fewer resources than a brand-new amd64 system. The /usr/src/sys/conf/GENERIC file contains mostly options and pseudo-devices. Every OpenBSD kernel must support a filesystem, or it won’t be able to write to disk or anything disk-like.

A kernel based on this file doesn’t yet know what sort of hardware the filesystem will run on, but it knows how to make a filesystem. It doesn’t know what kind of network card it will have, but once you give it a network card, it can create a TCP data stream and serve your web pages. You’ll need the machine-dependent configuration to make a kernel that can function in the real world.

Machine-Dependent Configuration

Each platform has its own machine-dependent kernel directory under /usr/src/sys/arch. Here’s where you’ll find a subdirectory for every platform OpenBSD supports, as well as a directory for any platforms under development. Separate directories contain platform-specific code, as well as further conf subdirectories for the kernel configuration file.

I’m using amd64 as an example, so the kernel configuration directory is /usr/src/sys/arch/amd64/conf. While we’ll focus on the common i386 and amd64 architectures, the kernel-building process is the same across all hardware platforms.

A traditional kernel configuration filename is in all capital letters. You’ll see the GENERIC configuration, as well as the RAMDISK* files used for the installation disks. (The GENERIC.MP kernel is the multiprocessor kernel.) We’ll start with the GENERIC kernel configuration file:

machine         amd64
include         "../../../conf/GENERIC"

The first entry in this kernel configuration defines the machine.The machine definition tells the kernel configuration parser the kind of hardware you’re running, and defines core hardware characteristics and constraints, such as how many bits are in an integer and how much memory the system can support.

The second entry pulls in the machine-independent kernel configuration (described in the previous section), defining all of the protocols and tools that make OpenBSD OpenBSD. The amd64 kernel inherits the filesystems and network stacks from this entry.

Following these two lines you’ll see the devices OpenBSD supports on amd64 hardware. Take a moment and skim the file. It’s the same mix of devices and attachments as described earlier in this chapter.

Your Kernel Configuration

In order to build your own kernel, you’ll need a configuration file. Here, we’ll look at how to create your configuration file. (Do not just edit either GENERIC kernel file.)

Minor Changes

If your kernel adds only a couple of items to the GENERIC kernel, use the GENERIC configuration as a basis for your new one. For example, here’s the multiprocessor kernel configuration, GENERIC.MP:

 include  "arch/amd64/conf/GENERIC"
option          MULTIPROCESSOR  # Multiple processor support
cpu*            at mainbus?

The multiprocessor kernel builds on GENERIC, adding only one option and one device attachment. You can use this model to define your own kernel configuration.

For example, suppose you want to enable the experimental SCSI multipathing feature on a kernel. You could create a kernel configuration file in your platform directory, and simply copy the commented-out multipathing entries from the machine-independent GENERIC kernel, like this:

include    "arch/amd64/conf/GENERIC"
mpath0     at root
scsibus*   at mpath?

This creates a custom kernel that closely resembles GENERIC, with these two extra devices.

Removing Options

To strip options from your kernel, use the rmoption keyword. For example, to create a minimal kernel based on GENERIC, you could use the rmoption keyword to remove some kernel options, as in this example:

include "arch/amd64/conf/GENERIC"
rmoption    NTFS
rmoption    HIBERNATE
…

One advantage to creating a configuration by including the default kernel is that when you update your source code, your custom kernel configuration will probably still be valid. However, the more options you remove from the kernel, the greater the chance that the kernel will fail to compile, or if it compiles, that it might not boot. And if it boots, it might eat your hard drive.

When removing options, keep in mind that some options are more important than you might think. For example, removing the INET6 option (aka IPv6) can create a nonfunctional system. Removing options doesn’t save you much memory, and it might cripple any number of programs.

Removing Devices

If you want to remove a lot of stuff from a machine-dependent kernel configuration, while retaining the options for base OpenBSD functions, copy the machine-dependent GENERIC configuration file to a new text file and make your changes in that file.

Wholesale Butchery

If you want to commit wholesale butchery on the kernel, you’ll want a configuration that includes both the machine-independent and machine-dependent parts. Start by copying the existing GENERIC kernel configurations into one file, in the platform’s kernel configuration. Here, I call my new kernel TREBLE, after the hostname:

# cd /usr/src/sys/arch/amd64/conf
# cp ../../../conf/GENERIC TREBLE
# cat GENERIC >> TREBLE

Before making any other changes, remove the line that includes the machine-independent kernel configuration file. Then slice out everything that makes the system functional, and try to build the new kernel. Next, add stuff back in until the kernel builds. (Although removing drivers won’t save much memory, doing so will make booting a tiny bit faster.)

Note

You might be tempted to use the man pages to create your own kernel configuration from scratch. You’re certainly free to do that, if you’re either a Kernel Lord or an irremediable doofus. Feel free to try it. Every sysadmin can use such a valuable lesson in humility.

Stripping Down the Kernel

Every device driver and option in the kernel uses memory. If you’re trying to cram OpenBSD onto a tiny computer, or you’re doing any sort of embedded development, you might want to build a custom kernel that includes as few device drivers as possible by editing /var/run/dmesg.boot, where every entry matches a line in the kernel configuration.

The simplest way to trim out unnecessary device drivers is to remove everything that’s not in your computer. The kernel includes dozens of network card drivers, but you need only one or two. If you’re unsure about a device, keep it in the configuration. (The ACPI and BIOS devices in particular are tightly interrelated, and you’ll probably have a really hard time building a bootable custom kernel without the complete set of ACPI and BIOS devices.)

Gutting the Kernel

If removing device drivers doesn’t create a sufficiently small kernel for you, try removing machine-independent options. Many of these options are interdependent, however, and removing them can create a kernel you can’t compile. If you can compile the kernel, it might not boot, and if it boots, it might not function correctly.

Testing Your Kernel Configuration with config(8)

Is your custom kernel configuration internally consistent? To test your kernel and prepare the files needed to compile it, use config(8).

While still in the kernel configuration directory, give config the kernel configuration filename as an argument, like this:

# config TREBLE

If you get any error messages, read them. For example, config might tell you that you need to run make clean before building your new kernel, or that your kernel configuration is internally inconsistent and will not compile. If there’s a problem, config will often give a line number where you made an error. Follow any advice config offers.

The following are some of the more common types of errors.

Orphaned Devices

One common way that config fails is if you’re missing a device that’s needed by another device. Here’s an example:

# config TREBLE
TREBLE:36: cpu0 at mainbus? is orphaned
 (nothing matching mainbus? declared)
TREBLE:37: bios0 at mainbus0 is orphaned
 (no mainbus0 declared)
TREBLE:38: ioapic* at mainbus? is orphaned
 (nothing matching mainbus? declared)
TREBLE:82: pci* at mainbus0 is orphaned
 (no mainbus0 declared)
*** Stop.

Your configuration attaches various devices to mainbus0, but there’s no mainbus0 entry in your configuration. Kernels that include devices that aren’t attached don’t make sense and cannot compile.

To address this, examine your hardware again. Figure out how these devices are supposed to attach to the system, and fix your kernel configuration.

Bogus Hardware

Another common problem is including nonexistent device drivers, which generates the following error.

# config TREBLE
TREBLE:36: cpe0: unknown device `cpe'
*** Stop.

config shows me the error and the line number where it occurs. There is no cpe device, but there is a cpu device. My bad.

The error checking performed by config does not guarantee that your kernel will compile or run as expected. The only errors it catches are ones where the configuration is either internally inconsistent or flat-out wrong. The first real test comes when you try to actually build your configured kernel.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
13.59.141.75