As we continue to evolve and improve the Oracle Linux user experience, one of our recent focuses was on enhancing the packaging model for Unbreakable Enterprise Kernel (UEK) 8. In this blog post, we delve into the details of the new packaging changes in UEK 8.

Introduction to UEK 8 packaging

In UEK 8 we’ve partitioned the kernel modules into several subpackages, thereby providing system administrators, or users, with greater control over the installation and management of kernel modules. This also provides a mechanism to reduce the potential attack surface.

New Subpackages in UEK 8

With the UEK 7 release, we have these packages:

Package Name
Description
kernel-uek
A meta package that doesn’t contain any files, but expresses a dependency on other kernel-uek-* RPMs, defining a set equal to the same in earlier UEK releases
kernel-uek-core
Provides core files of the UEK kernel – including vmlinux, config files, System.map files, initramfs and so on. These files reside in the /boot directory on installing the RPM
kernel-uek-modules-core
A minimal set of modules required for Oracle engineered systems
kernel-uek-modules
Provides frequently used modules for servers
kernel-uek-modules-extra
Provides rarely used modules

These packages offer limited control over the specific modules to be installed, which can make it challenging to minimize the attack surface or disk usage by selectively installing only the necessary modules.

With UEK8, the above packages continue to exist, while these new ones are introduced:

Package Name
Description
kernel-uek-modules-desktop
Provides modules used in desktop-type hardware (HID, touchscreens, and so on.)
kernel-uek-modules-usb
Provides USB drivers
kernel-uek-modules-wireless
Provides wireless drivers
kernel-uek-modules-extra-netfilter
Provides lesser-used netfilter modules
kernel-uek-modules-deprecated
Provides modules that are likely to be removed in future releases

This figure provides an overview of the structure of these packages:

UEK 8 packages layout

The need for new subpackages

The new set of subpackages provide a way for the user to retain only those kernel-uek-modules* packages that they require and to remove any kernel-uek-modules* packages that they don’t need.

Modules classified as desktop use – such as laptop drivers, webcam drivers, video drivers, and sound drivers – which aren’t commonly used on servers, are now moved to the kernel-uek-modules-desktop subpackage.

Similarly, USB drivers are moved to the kernel-uek-modules-usb subpackage, and wireless drivers are moved to the kernel-uek-modules-wireless subpackage.

Many netfilter modules now have modern alternatives that are more actively maintained. Rather than removing these modules altogether, we’ve moved the less-commonly used into the kernel-uek-modules-extra-netfilter subpackage.

As we continually enable new features and integrate new drivers from the upstream Linux kernel, we also identify instances where certain drivers have been retired, or removed entirely, in newer Linux releases. To address this, we proactively monitor these changes and move such drivers to the kernel-uek-modules-deprecated subpackage to provide users with some advance notice of modules that will be retired in a future UEK release.

As mentioned before, it’s possible to reduce the number of modules installed on a system running UEK 8. For example, on a server system, it’s likely that certain classes of drivers, such as those for webcams, touchscreens, or other desktop-specific hardware, are unnecessary. In such cases, users can remove the kernel-uek-modules-desktop subpackage, which can help minimize the attack surface by eliminating potential exposure through unused drivers.

As we’ve discussed, the introduction of these subpackages offers users greater flexibility and control over their system configuration. By providing a modular approach, users can optimize their systems for specific use cases, making it easier to manage their environment.

Module mapping and a modprobe enhancement

Module mapping

To make it easier for users to navigate the increased number of packages, a mapping of modules to their corresponding subpackages is provided in a file within the kernel-uek-core package. This file, named modules.packages, contains the mapping of module to its subpackage name – each line has the format:

module_name subpackage_rpm_name

The modules.packages file is in the /lib/modules/$(uname -r) directory:

$ cat /lib/modules/6.12.0-0.20.20.el9uek.x86_64/modules.packages

8021q kernel-uek-modules-core-6.12.0-0.20.20.el9uek.x86_64
acpi-cpufreq kernel-uek-modules-core-6.12.0-0.20.20.el9uek.x86_64
acpi_extlog kernel-uek-modules-core-6.12.0-0.20.20.el9uek.x86_64
acpi_ipmi kernel-uek-modules-core-6.12.0-0.20.20.el9uek.x86_64
...
tca6416-keypad kernel-uek-modules-desktop-6.12.0-0.20.20.el9uek.x86_64
tda7432 kernel-uek-modules-desktop-6.12.0-0.20.20.el9uek.x86_64
...
wil6210 kernel-uek-modules-wireless-6.12.0-0.20.20.el9uek.x86_64
zd1211rw kernel-uek-modules-wireless-6.12.0-0.20.20.el9uek.x86_64

modprobe enhancement

We’ve also enhanced modprobe to be aware of the new packaging structure. So, when a module is installed, modprobe automatically loads it. If the corresponding package containing the module isn’t installed, modprobe now displays the name of the subpackage containing the module, providing users with clear guidance on which package to install.

For example, on a system with UEK 8 running, and where the kernel-uek-modules-desktop subpackage hasn’t been installed, we can try to load a module from that package to see whether this functionality works correctly.

First, check that we’re running UEK 8:

[opc@uek8-vm ~]$ uname -r
6.12.0-0.20.20.el9uek.x86_64

Next let’s load the 8021q module to check that module loading is working correctly:

[opc@uek8-vm ~]$ lsmod | grep 8021q
[opc@uek8-vm ~]$ sudo modprobe 8021q
[opc@uek8-vm ~]$ lsmod | grep 8021q
8021q                  53248  0
garp                   20480  1 8021q
mrp                    20480  1 8021q

Now, let’s try to load a module that’s not installed, such as tca6416-keypad:

[opc@hamogala-vm-4 ~]$ sudo modprobe tca6416-keypad
modprobe: FATAL: Module tca6416-keypad not found in directory /lib/modules/6.12.0-0.20.20.el9uek.x86_64,
ensure the following package is installed: kernel-uek-modules-desktop-6.12.0-0.20.20.el9uek.x86_64

As shown, the updated modprobe is now aware of the packaging structure and provides the user with a clear suggestion with regard to the required package to install, kernel-uek-modules-desktop, which contains the tca6416-keypad module.

Sample script to harden the system

Putting everything together, it is now possible to identify packages which can be removed for a given system as they do not provide any module that is actively in use.

Warning: Example Script Only

The following script is a simplified example and should not be used in production without thorough testing and validation. The script is intended to illustrate the basic concept of identifying kernel module packages with no loaded modules, but might not be comprehensive or correct in all scenarios.

#!/bin/bash
# Sample script only

kernel_version="$(uname -r)"
module_mapping="/lib/modules/${kernel_version}/modules.packages"
kernel_subpackages="$(cut -d' ' -f2 "${module_mapping}" | sort -u)"
loaded_modules="$(lsmod | tail -n +2 | cut -d' ' -f1)"

echo "Kernel module RPMs with no loaded modules for kernel version ${kernel_version}:"
echo

rv=0
for rpm in ${kernel_subpackages}; do
    num_loaded="$(grep "$rpm" "${module_mapping}" | cut -d' ' -f1 | grep -c -x -f <(echo "$loaded_modules"))"
    if [[ $num_loaded -eq 0 ]]; then
        echo "  $rpm"
        rv=$(( rv + 1 ))
    fi
done

if [[ $rv -eq 0 ]]; then
    echo
    echo "  No kernel module RPMs with no loaded modules found."
    echo
else
    echo
    echo "${rv} kernel module RPMs may be removed."
    echo
fi

exit ${rv}

And a sample output from the script might look something such as this:

Kernel module RPMs with no loaded modules for kernel version 6.12.0-0.20.20.el9uek.x86_64:

  kernel-uek-modules-6.12.0-0.20.20.el9uek.x86_64
  kernel-uek-modules-deprecated-6.12.0-0.20.20.el9uek.x86_64
  kernel-uek-modules-extra-6.12.0-0.20.20.el9uek.x86_64
  kernel-uek-modules-extra-netfilter-6.12.0-0.20.20.el9uek.x86_64
  kernel-uek-modules-usb-6.12.0-0.20.20.el9uek.x86_64
  kernel-uek-modules-wireless-6.12.0-0.20.20.el9uek.x86_64

6 kernel module RPMs may be removed.

Conclusion

In summary, the new packaging model for UEK 8 provides a more modular approach to manage linux kernel modules on a system, giving users greater control and flexibility over their system configuration, while helping users to optimize their systems for specific use cases.

Resources

  1. UEK 8 Release Notes
  2. UEK 8 Announcement Blog