I am confused by how built-in kernel modules work. As per my understanding, one can embed a kernel module when compiling the Linux kernel by setting kconfig option to MODULE_NAME=y. Then, it doesn't have to be loaded with e.g. modprobe. Built-in kernel modules can be shown with cat /lib/modules/$(uname -r)/modules.builtin.

When I execute this command, the list shows .ko files. But if they are embedded inside the kernel, why is it showing this? For example:

~$ cat /lib/modules/$(uname -r)/modules.builtin | grep -i bsg    #just picking something random

~$ cat /boot/config-6.5.0-14-generic | grep -i bsg
CONFIG_BLK_DEV_BSG_COMMON=y    #implying this is a builtin module

~$ modinfo bsg
name:           bsg
filename:       (builtin)
license:        GPL
file:           block/bsg    #why "file"? Isn't it compiled inside the kernel?

~$ cat /lib/modules/6.5.0-14-generic/kernel/block/bsg.ko
cat: /lib/modules/6.5.0-14-generic/kernel/block/bsg.ko: No such file or directory

So my questions are:

  • What really happens to builtin kernel modules and where do they reside inside the system?
  • Are they inside vmlinuz and extracted somehow?
  • Why do they appear as .ko file but are not present in the directory where I would expect them?

Considering they are indeed embedded in vmlinu(x/z), how do they end up being "registered" such that we can find them using modinfo? And why does it still have a file (block/bsg) as shown by modinfo if it's in the kernel binary?

1 Answer 1


Builtin kernel “modules” (they aren’t really modules) are part of the main kernel binary, vmlinux before it’s compressed. They are never extracted as separate entities, they are loaded along with the rest of the kernel.

They appear as .ko files in modules.builtin to make things easier for other tools, e.g. for module dependency analysis. By listing them as .ko files, they can be handled in the same way as modules.

When components of the kernel are built-in, but their source files contain module declarations, the information provided there is stored in modules.builtin and modules.builtin.modinfo (see the Kbuild documentation). modules.builtin allows modprobe to handle load requests for built-in modules, and modules.builtin.modinfo allows modinfo to provide information about them. Built-in components don’t have a filename (which points to the real .ko on disk, for loadable modules), but they do have a file — this is an entry specific to builtin modules, storing the name of the source file containing the module declarations (block/bsg.c in your example).


You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .