提交 80a3d1bb 编写于 作者: R Rusty Russell

module: move sysfs exposure to end of load_module

This means a little extra work, but is more logical: we don't put
anything in sysfs until we're about to put the module into the
global list an parse its parameters.

This also gives us a logical place to put duplicate module detection
in the next patch.
Signed-off-by: NRusty Russell <rusty@rustcorp.com.au>
上级 c8e21ced
...@@ -560,7 +560,6 @@ static int already_uses(struct module *a, struct module *b) ...@@ -560,7 +560,6 @@ static int already_uses(struct module *a, struct module *b)
*/ */
static int add_module_usage(struct module *a, struct module *b) static int add_module_usage(struct module *a, struct module *b)
{ {
int no_warn;
struct module_use *use; struct module_use *use;
DEBUGP("Allocating new usage for %s.\n", a->name); DEBUGP("Allocating new usage for %s.\n", a->name);
...@@ -574,7 +573,6 @@ static int add_module_usage(struct module *a, struct module *b) ...@@ -574,7 +573,6 @@ static int add_module_usage(struct module *a, struct module *b)
use->target = b; use->target = b;
list_add(&use->source_list, &b->source_list); list_add(&use->source_list, &b->source_list);
list_add(&use->target_list, &a->target_list); list_add(&use->target_list, &a->target_list);
no_warn = sysfs_create_link(b->holders_dir, &a->mkobj.kobj, a->name);
return 0; return 0;
} }
...@@ -619,7 +617,6 @@ static void module_unload_free(struct module *mod) ...@@ -619,7 +617,6 @@ static void module_unload_free(struct module *mod)
list_del(&use->source_list); list_del(&use->source_list);
list_del(&use->target_list); list_del(&use->target_list);
kfree(use); kfree(use);
sysfs_remove_link(i->holders_dir, mod->name);
} }
} }
...@@ -1303,6 +1300,29 @@ static inline void remove_notes_attrs(struct module *mod) ...@@ -1303,6 +1300,29 @@ static inline void remove_notes_attrs(struct module *mod)
#endif #endif
#ifdef CONFIG_SYSFS #ifdef CONFIG_SYSFS
static void add_usage_links(struct module *mod)
{
#ifdef CONFIG_MODULE_UNLOAD
struct module_use *use;
int nowarn;
list_for_each_entry(use, &mod->target_list, target_list) {
nowarn = sysfs_create_link(use->target->holders_dir,
&mod->mkobj.kobj, mod->name);
}
#endif
}
static void del_usage_links(struct module *mod)
{
#ifdef CONFIG_MODULE_UNLOAD
struct module_use *use;
list_for_each_entry(use, &mod->target_list, target_list)
sysfs_remove_link(use->target->holders_dir, mod->name);
#endif
}
int module_add_modinfo_attrs(struct module *mod) int module_add_modinfo_attrs(struct module *mod)
{ {
struct module_attribute *attr; struct module_attribute *attr;
...@@ -1385,6 +1405,10 @@ int mod_sysfs_setup(struct module *mod, ...@@ -1385,6 +1405,10 @@ int mod_sysfs_setup(struct module *mod,
{ {
int err; int err;
err = mod_sysfs_init(mod);
if (err)
goto out;
mod->holders_dir = kobject_create_and_add("holders", &mod->mkobj.kobj); mod->holders_dir = kobject_create_and_add("holders", &mod->mkobj.kobj);
if (!mod->holders_dir) { if (!mod->holders_dir) {
err = -ENOMEM; err = -ENOMEM;
...@@ -1399,6 +1423,8 @@ int mod_sysfs_setup(struct module *mod, ...@@ -1399,6 +1423,8 @@ int mod_sysfs_setup(struct module *mod,
if (err) if (err)
goto out_unreg_param; goto out_unreg_param;
add_usage_links(mod);
kobject_uevent(&mod->mkobj.kobj, KOBJ_ADD); kobject_uevent(&mod->mkobj.kobj, KOBJ_ADD);
return 0; return 0;
...@@ -1408,6 +1434,7 @@ int mod_sysfs_setup(struct module *mod, ...@@ -1408,6 +1434,7 @@ int mod_sysfs_setup(struct module *mod,
kobject_put(mod->holders_dir); kobject_put(mod->holders_dir);
out_unreg: out_unreg:
kobject_put(&mod->mkobj.kobj); kobject_put(&mod->mkobj.kobj);
out:
return err; return err;
} }
...@@ -1422,10 +1449,15 @@ static void mod_sysfs_fini(struct module *mod) ...@@ -1422,10 +1449,15 @@ static void mod_sysfs_fini(struct module *mod)
{ {
} }
static void del_usage_links(struct module *mod)
{
}
#endif /* CONFIG_SYSFS */ #endif /* CONFIG_SYSFS */
static void mod_kobject_remove(struct module *mod) static void mod_kobject_remove(struct module *mod)
{ {
del_usage_links(mod);
module_remove_modinfo_attrs(mod); module_remove_modinfo_attrs(mod);
module_param_sysfs_remove(mod); module_param_sysfs_remove(mod);
kobject_put(mod->mkobj.drivers_dir); kobject_put(mod->mkobj.drivers_dir);
...@@ -2242,11 +2274,6 @@ static noinline struct module *load_module(void __user *umod, ...@@ -2242,11 +2274,6 @@ static noinline struct module *load_module(void __user *umod,
/* Now we've moved module, initialize linked lists, etc. */ /* Now we've moved module, initialize linked lists, etc. */
module_unload_init(mod); module_unload_init(mod);
/* add kobject, so we can reference it. */
err = mod_sysfs_init(mod);
if (err)
goto free_unload;
/* Set up license info based on the info section */ /* Set up license info based on the info section */
set_license(mod, get_modinfo(sechdrs, infoindex, "license")); set_license(mod, get_modinfo(sechdrs, infoindex, "license"));
...@@ -2443,6 +2470,7 @@ static noinline struct module *load_module(void __user *umod, ...@@ -2443,6 +2470,7 @@ static noinline struct module *load_module(void __user *umod,
err = mod_sysfs_setup(mod, mod->kp, mod->num_kp); err = mod_sysfs_setup(mod, mod->kp, mod->num_kp);
if (err < 0) if (err < 0)
goto unlink; goto unlink;
add_sect_attrs(mod, hdr->e_shnum, secstrings, sechdrs); add_sect_attrs(mod, hdr->e_shnum, secstrings, sechdrs);
add_notes_attrs(mod, hdr->e_shnum, secstrings, sechdrs); add_notes_attrs(mod, hdr->e_shnum, secstrings, sechdrs);
...@@ -2461,9 +2489,6 @@ static noinline struct module *load_module(void __user *umod, ...@@ -2461,9 +2489,6 @@ static noinline struct module *load_module(void __user *umod,
module_arch_cleanup(mod); module_arch_cleanup(mod);
cleanup: cleanup:
free_modinfo(mod); free_modinfo(mod);
kobject_del(&mod->mkobj.kobj);
kobject_put(&mod->mkobj.kobj);
free_unload:
module_unload_free(mod); module_unload_free(mod);
#if defined(CONFIG_MODULE_UNLOAD) #if defined(CONFIG_MODULE_UNLOAD)
free_percpu(mod->refptr); free_percpu(mod->refptr);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册