On Tue, 19 May 2026 12:49:34 +0100, Jonathan Cameron wrote:

> Agreed. I'm curious why it was built that way.  I scraped an email address
> that is hopefully the right Lucas from another thread. +CC
>
> [...]
>
> My suspicion is this is papering over a race condition that occurs in
> a normal module load -  it may not be possible to tell the difference
> between COMMING and BUILTIN reliably.

I went and read through libkmod's code and history carefully on this,
and your suspicion is correct -- the COMING return is deliberate, not
incidental.

The behavior was introduced in libkmod commit fd44a98 ("Fix race while
loading modules", 2015), and Lucas spelled out the rationale in the
commit message:

  The problem is that the creation of /sys/module/<name> and
  /sys/module/<name>/initstate are not atomic. There's a small window
  in which the directory exists but the initstate file was still not
  created.
  [...]
  We enforce mod->builtin to always be up-to-date when
  kmod_module_get_initstate() is called. This way if the directory
  exists but the initstate doesn't, we can be sure this is because the
  module is in the "coming" state, i.e. kernel didn't create the file
  yet, but since builtin modules were already handled by checking our
  index the only reason for that to happen is that we hit the race
  condition.

So COMING on the sysfs fallback path is intentional: libkmod treats
kmod_module_is_builtin() (i.e. the modules.builtin lookup) as the
authoritative answer to "is this builtin", and assumes anything else
hitting the dir-without-initstate window has to be a concurrent load
race. When modules.builtin is missing, that assumption silently flips
and a builtin driver looks exactly like a load-in-progress -- which
is the COMING you saw.

Given that, I don't think the right fix is in libkmod. Returning
BUILTIN unconditionally on the dir-without-initstate fallback would
re-open the very race fd44a98 set out to close: a parallel modprobe
of a real loadable module that wins the directory creation but not
yet the initstate write would be misreported as builtin, and callers
waiting on it (the nls_cp437 / sd-card scenario in fd44a98) would
skip the wait. That's a behavioral regression on a configuration
libkmod has supported for ten years, in exchange for tidying up a
no-modules_install setup that libkmod arguably never promised to
handle. Lucas (CC'd) -- please correct me if I'm misreading the
original intent.

So I'll take Alison's suggestion and handle it on the ndctl side. v2
will keep the BUILTIN/LIVE short-circuit and additionally treat
KMOD_MODULE_COMING as builtin when /sys/module/<name>/ exists but the
initstate file does not -- exactly the fingerprint your VM hits.

I'll post v2 shortly.

Thanks,
Pei

Reply via email to