| 1 | [[PageOutline]] |
| 2 | |
| 3 | = Linux Kernel modules |
| 4 | If your kernel is built with loadable module support (CONFIG_MODULES=y) you can load and unload pre-built kernel modules to add, remove, and alter functionality of a running kernel. |
| 5 | |
| 6 | The userspace support for doing this comes from a set of commands typically packaged in a 'kmod' package name consisting of: |
| 7 | - {{{lsmod}}} - show the status of modules currently loaded in the kernel (uses info from /proc/modules) |
| 8 | - {{{insmod}}} - manually insert a module into the kernel |
| 9 | - {{{rmmod}}} - manually remove a module from the kernel |
| 10 | - {{{modinfo}}} - show info about a module |
| 11 | - {{{depmod}}} - create a modules.dep and map file describing module dependencies |
| 12 | - {{{modprobe}}} - add or remove a module from the kernel (handling dependencies and finding modules in the /lib/modules/$(uname -r) directory) taking into account module parameters from optional configuration files in /etc/modprobe.d |
| 13 | |
| 14 | Examples: |
| 15 | * load a module: |
| 16 | {{{#!bash |
| 17 | insmod ./mymod.ko # by path |
| 18 | modprobe mymod # from /lib/modules using dependencies |
| 19 | }}} |
| 20 | * remove a module: |
| 21 | {{{#!bash |
| 22 | rmmod mymod |
| 23 | }}} |
| 24 | * show loaded modules: |
| 25 | {{{#!bash |
| 26 | lsmod |
| 27 | }}} |
| 28 | * show kernel params for a given module: |
| 29 | {{{#!bash |
| 30 | $ modinfo g_ether | grep parm |
| 31 | parm: idVendor:USB Vendor ID (ushort) |
| 32 | parm: idProduct:USB Product ID (ushort) |
| 33 | parm: bcdDevice:USB Device version (BCD) (ushort) |
| 34 | parm: iSerialNumber:SerialNumber string (charp) |
| 35 | parm: iManufacturer:USB Manufacturer string (charp) |
| 36 | parm: iProduct:USB Product string (charp) |
| 37 | parm: qmult:queue length multiplier at high/super speed (uint) |
| 38 | parm: dev_addr:Device Ethernet Address (charp) |
| 39 | parm: host_addr:Host Ethernet Address (charp) |
| 40 | parm: use_eem:use CDC EEM mode (bool) |
| 41 | }}} |
| 42 | * show vermagic for a given module: |
| 43 | {{{#!bash |
| 44 | $ modinfo g_ether | grep vermagic |
| 45 | vermagic: 6.12.0-g530fc2d305a3 SMP mod_unload aarch64 |
| 46 | }}} |
| 47 | |
| 48 | == Building |
| 49 | |
| 50 | == Linux Kernel vermagic |
| 51 | Vermagic is a magic string present in the Linux Kernel and added into the .modinfo section of the Linux Kernel Modules. |
| 52 | |
| 53 | This is used to verify whether the kernel module was compiled for the particular kernel version or not. |
| 54 | |
| 55 | This string is generated by the kernel configuration via the following in include/linux/vermagic.h: |
| 56 | {{{#!bash |
| 57 | #define VERMAGIC_STRING \ |
| 58 | UTS_RELEASE " " \ |
| 59 | MODULE_VERMAGIC_SMP MODULE_VERMAGIC_PREEMPT \ |
| 60 | MODULE_VERMAGIC_MODULE_UNLOAD MODULE_VERMAGIC_MODVERSIONS \ |
| 61 | MODULE_ARCH_VERMAGIC \ |
| 62 | MODULE_RANDSTRUCT |
| 63 | }}} |
| 64 | |
| 65 | A typical VERMAGIC_STRING for an aarch64 kernel would look something like:{{{6.12.0-g530fc2d305a3 SMP mod_unload aarch64}}} |
| 66 | |
| 67 | While you can easily find the kernel version and arch of a running kenrel, perhaps the best way to see this exact string would be to use modinfo command on an existing module: |
| 68 | {{{#!bash |
| 69 | # modinfo $(find /lib/modules/$(uname -r)/ -name "*.ko" | head -n1) | grep vermagic |
| 70 | vermagic: 6.12.0-g530fc2d305a3 SMP mod_unload aarch64 |
| 71 | }}} |
| 72 | |
| 73 | The vermagic string is checked upon module loading and if the string in the module does not match the string in the kernel the module loading will fail by design: |
| 74 | {{{#!bash |
| 75 | # insmod mymod.ko |
| 76 | mymod: version magic '6.12.0-00017-g530fc2d305a3 SMP mod_unload aarch64' should be '6.12.0-g530fc2d305a3 SMP mod_unload aarch64' |
| 77 | insmod: ERROR: could not insert module ./mymod.ko: Invalid module format |
| 78 | }}} |
| 79 | |
| 80 | There is no easy way to disable the kernel module loading vermagic string unless you disable a lot of security measures and the vermagic check is there for a very important reason: to disallow loading of modules that are not compatible with the specific version of kernel running. |
| 81 | |
| 82 | There are times however as a developer building an out-of-tree kernel module that you may wish to avoid this check. For example, if your running kernel version varies only slightly in ways you know are compatible. In such a case where you assume full responsibility for breaking something you could use the [https://dev.gateworks.com/sources/setvermagic.sh setvermagic.sh] script to modify the vermagic string: |
| 83 | {{{#!bash |
| 84 | $ wget https://dev.gateworks.com/sources/setvermagic.sh |
| 85 | $ chmod +x setvermagic.sh |
| 86 | $ modinfo mymod.ko | grep vermagic |
| 87 | vermagic: 6.6.8-00035-gc6ef8b5e47a0 SMP mod_unload aarch64 |
| 88 | Show quoted text |
| 89 | $ ./setvermagic.sh mymod.ko "6.6.8-gc6ef8b5e47a0 SMP mod_unload aarch64" |
| 90 | Current vermagic: 6.6.8-00035-gc6ef8b5e47a0 SMP mod_unload aarch64 |
| 91 | New vermagic : 6.6.8-gc6ef8b5e47a0 SMP mod_unload aarch64 |
| 92 | Modified module saved as: mymod-modified.ko |
| 93 | You can load it with: insmod mymod-modified.ko |
| 94 | }}} |