Skip to content

rpm: build kernel modules via DKMS on the target - #1788

Merged
robertbaldyga merged 4 commits into
Open-CAS:masterfrom
Arondight:master
Sep 23, 2026
Merged

robertbaldyga merged 4 commits into
Open-CAS:masterfrom
Arondight:master

Conversation

@Arondight

Copy link
Copy Markdown
Contributor

Switches RPM packaging from prebuilt kmod modules (one per-kernel subpackage, built on the host) to DKMS source built on the target at install time. The build host no longer needs kernel-devel. opencas_exporter is split into an optional subpackage (--with-exporter, off by default) so the default build doesn't pull golang.

Tested on multi kernels: fresh install, clean uninstall, dkms→dkms upgrade, multi-kernel build, kmod→dkms upgrade, kmod→dkms + uninstall, reinstall. All Pass.

@robertbaldyga
robertbaldyga force-pushed the master branch 2 times, most recently from 0d47545 to 997fa5b Compare September 23, 2026 20:44
@robertbaldyga

Copy link
Copy Markdown
Member

@Arondight Hi 秦凡东! Thank you for this contribution. It took a while for me to find a moment to look at it. I let myself to make a few modifications, as many users currently rely on the existing RPM building method and they don't want to switch to DKMS. Therefore I made DKMS RPM a second option, so that the users have a choice of which one they want to build. I also made sure that transitions in both direction (prebuilt->DKMS and DKMS->prebuilt) work well. I'll publish my tests once I get them polished.

Signed-off-by: 秦凡东 <qinfandong@kylinos.cn>
Mirror the DEB packaging: ship DKMS source to /usr/src/ and build the
kernel modules on the target at install time instead of compiling them
for a specific kernel at package build time. For building DKMS packages
the build host no longer needs kernel-devel/kernel-headers.

spec:
- DKMS source tree + dkms.conf (heredoc); %post/%preun modules do
  dkms add/install/remove with --rpm_safe_upgrade on add+remove (per
  dkms(8))
- drop the kernel-version-specific subpackage and weak-modules/depmod
  logic (DKMS builds per-kernel natively)
- build only userspace in %build; scrub OCF-synced headers and utils
  manpages so the DKMS tree ships source-only

pckgen.sh:
- --with-dkms/--without-dkms, plumbed to rpmbuild and mock as the matching
  bcond; --kernel-version is skipped in DKMS mode, where no kernel is
  selected at build time
- in DKMS mode build only casadm (<MAKE_BUILD> -> make -C casadm, matching DEB)

Makefile:
- 'make rpm-dkms' alongside 'make rpm'

The opencas_exporter remains experimental for the current release, so do
not include it into the package.

Co-authored-by: GLM-5.2
Signed-off-by: 秦凡东 <qinfandong@kylinos.cn>
Signed-off-by: Robert Baldyga <robert.baldyga@unvertical.com>
Both module packages ship modules for the same kernel, so having them
installed together means two sets of modules on disk and whichever of them
the module index happens to resolve first being the one in use.

Declare them in conflict, to refuse installing both simultaneously, and leave
switching to be asked for ('dnf --allowerasing', 'dnf swap'). rpm applies it
whichever of the two is being installed, so it only has to be declared on the
side whose counterpart can be named: the prebuilt package's own name carries
the kernel version and cannot be written down.

Switching is still meant to work, so two things have to survive the erasure it
implies:

- the tools require the modules by a name-and-version that both module
  packages provide, rather than by package, so the requirement stays satisfied
  within the transaction and erasing the outgoing package does not cascade into
  the tools
- DKMS registers and builds from %posttrans rather than %post. The outgoing
  package is erased between the two, and dkms refuses to overwrite a module
  already installed at the same version, so from %post the modules being
  replaced are still in the way - and the erase that follows would then take
  away the ones dkms had declined to replace, leaving the kernel with none

Co-authored-by: GLM-5.2
Signed-off-by: 秦凡东 <qinfandong@kylinos.cn>
Signed-off-by: Robert Baldyga <robert.baldyga@unvertical.com>
Installing the DKMS package over an existing prebuilt one leaves the old
modules package behind. It is named after the kernel it was built for
(open-cas-linux-modules_k<kernelver>), so the DKMS package cannot Obsoletes
it by name, and it is not replaced by the transaction either: it simply
stays installed, still owning modules in /lib/modules.

It cannot be removed from inside that transaction either, since rpm holds
the database lock. Remove it from a detached worker started in %posttrans,
which waits for the package manager to exit and then takes the orphan out
with --nodeps (nothing depends on it) and --noscripts (its %preun operates
on .ko files dkms has since archived, and fails). Its weak-updates symlinks
are left dangling by --noscripts, so clear those too. The whole thing is
guarded on such a package actually being installed, so a fresh install and
a dkms-to-dkms upgrade do nothing.

DKMS archives the modules it finds in place as original_module and restores
them when the package is removed, which would put the old kernel's modules
back as orphans after the package that owned them is gone. Drop the archive
in %preun before 'dkms remove'.

Two things the worker has to be careful about. It must not give up the prebuilt
modules unless DKMS has modules of its own installed - a build that produced
nothing would otherwise take away the ones the system is running on - so it
checks that for itself, on top of the build's own failure exiting the scriptlet
before the worker is started. And --noscripts means the old %postun never runs,
so nothing rebuilds the module index once its files are gone: it still lists
them, which breaks modprobe and makes dracut fail in kernel-modules-extra. Run
depmod for the installed kernels afterwards.

Only needed for packages that predate this change; from here on the two
module packages conflict, so they cannot be installed over each other by
accident.

Co-authored-by: GLM-5.2
Signed-off-by: 秦凡东 <qinfandong@kylinos.cn>
Signed-off-by: Robert Baldyga <robert.baldyga@unvertical.com>
@robertbaldyga
robertbaldyga merged commit 89a15b8 into Open-CAS:master Sep 23, 2026
4 of 5 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants