0

When Linux Kernel load new module with insmod, it will invoke

finit_module
  do_init_module
    do_one_initcall

then the init function defined in module will be invoked.

static noinline int do_init_module(struct module *mod)
{
    int ret = 0;
    struct mod_initfree *freeinit;

    freeinit = kmalloc(sizeof(*freeinit), GFP_KERNEL);
    if (!freeinit) {
        ret = -ENOMEM;
        goto fail;
    }
    freeinit->module_init = mod->init_layout.base;

    /*
     * We want to find out whether @mod uses async during init.  Clear
     * PF_USED_ASYNC.  async_schedule*() will set it.
     */
    current->flags &= ~PF_USED_ASYNC;

    do_mod_ctors(mod);
    /* Start the module */
    if (mod->init != NULL)
        ret = do_one_initcall(mod->init);
...
}

But after searching all code of linux kernel, I haven't found the place where does mod->init assigned, could anyone help me?

Thanks in advance.

Felix Du
  • 105
  • 6
  • Why do you need to find that assignment or initialization? What is the actual and underlying problem you're trying to solve? Or is it just plain curiosity (which is okay, but then please tell us)? Otherwise please ask us directly about the real problem. Perhaps take some time to refresh [the help pages](http://stackoverflow.com/help), take the SO [tour], read [ask], as well as [this question checklist](https://codeblog.jonskeet.uk/2012/11/24/stack-overflow-question-checklist/). – Some programmer dude Jun 27 '21 at 15:20
  • Thanks for your comments. Yes, it is just plain curiosity. I am interested with the scenario of how to load the kernel module, so I checked the code, but blocked here. – Felix Du Jun 27 '21 at 15:29
  • I believe the information ends up in the `struct module` compiled into the `.gnu.linkonce.this_module` section of the .ko file. The generated source is in the *modulename*.mod.c file. – Ian Abbott Jun 28 '21 at 12:11
  • You can also use the `objdump -j .gnu.linkonce.this_module -r modulename.ko` command to see the relocation information for the `struct module` embedded in the `.gnu.linkonce.this_module` section of the .ko file. It should show relocation information for `init_module` and `cleanup_module` if they exist in the module. (Those functions may be created by the `module_init(initfn)` and `module_exit(exitfn)` macro calls.) – Ian Abbott Jun 28 '21 at 12:29

1 Answers1

5

The values of mod->init and mod->exit come from the struct module __this_module variable contained in the .gnu.linkonce.this_module section of the module's .ko file. The kernel assumes that this variable is at the start of the section, and in fact it is the only variable in the section.

The __this_module variable is initialized by a C initializer within the modulename.mod.c file that is generated during the MODPOST phase of the kernel build process. A typical definition of the __this_module variable in a modulename.mod.c file looks like this for current kernels:

__visible struct module __this_module
__section(.gnu.linkonce.this_module) = {
    .name = KBUILD_MODNAME,
    .init = init_module,
#ifdef CONFIG_MODULE_UNLOAD
    .exit = cleanup_module,
#endif
    .arch = MODULE_ARCH_INIT,
};

The finit_module and init_module syscall handling functions call load_module to do most of the work. load_module calls setup_load_info, which amongst other things, looks for the .gnu.linkonce.this_module section that contains only the __this_module variable. A temporary pointer to this is placed in info->mod (where info points to the struct load_info used to hold information for loading the module). load_module later calls layout_and_allocate which returns a pointer to the __this_module variable (actually, a pointer to the .gnu.linkonce.this_module section) after it has been copied to its final place in kernel memory by move_module. After load_module calls apply_relocations to perform dynamic linking, mod->init and mod->exit will have their final values (ignoring modifications by CONFIG_CFI_CLANG in kernel 5.13 onwards).

Note that the __this_module.init function pointer is always either a pointer to init_module or is defaulted to null, and the __this_module.exit function pointer is always either a pointer to cleanup_module or is defaulted to null. (Most module source codes use the module_init(initfn) and module_exit(exitfn) macros to create those functions, but they can be defined explicitly.)

Ian Abbott
  • 15,083
  • 19
  • 33