aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/module.c
diff options
context:
space:
mode:
Diffstat (limited to 'kernel/module.c')
-rw-r--r--kernel/module.c43
1 files changed, 29 insertions, 14 deletions
diff --git a/kernel/module.c b/kernel/module.c
index 8a94e054230c..9da5af668a20 100644
--- a/kernel/module.c
+++ b/kernel/module.c
@@ -1068,7 +1068,8 @@ static inline void remove_sect_attrs(struct module *mod)
1068} 1068}
1069#endif /* CONFIG_KALLSYMS */ 1069#endif /* CONFIG_KALLSYMS */
1070 1070
1071static int module_add_modinfo_attrs(struct module *mod) 1071#ifdef CONFIG_SYSFS
1072int module_add_modinfo_attrs(struct module *mod)
1072{ 1073{
1073 struct module_attribute *attr; 1074 struct module_attribute *attr;
1074 struct module_attribute *temp_attr; 1075 struct module_attribute *temp_attr;
@@ -1094,7 +1095,7 @@ static int module_add_modinfo_attrs(struct module *mod)
1094 return error; 1095 return error;
1095} 1096}
1096 1097
1097static void module_remove_modinfo_attrs(struct module *mod) 1098void module_remove_modinfo_attrs(struct module *mod)
1098{ 1099{
1099 struct module_attribute *attr; 1100 struct module_attribute *attr;
1100 int i; 1101 int i;
@@ -1109,8 +1110,10 @@ static void module_remove_modinfo_attrs(struct module *mod)
1109 } 1110 }
1110 kfree(mod->modinfo_attrs); 1111 kfree(mod->modinfo_attrs);
1111} 1112}
1113#endif
1112 1114
1113static int mod_sysfs_init(struct module *mod) 1115#ifdef CONFIG_SYSFS
1116int mod_sysfs_init(struct module *mod)
1114{ 1117{
1115 int err; 1118 int err;
1116 1119
@@ -1133,7 +1136,7 @@ out:
1133 return err; 1136 return err;
1134} 1137}
1135 1138
1136static int mod_sysfs_setup(struct module *mod, 1139int mod_sysfs_setup(struct module *mod,
1137 struct kernel_param *kparam, 1140 struct kernel_param *kparam,
1138 unsigned int num_params) 1141 unsigned int num_params)
1139{ 1142{
@@ -1145,8 +1148,10 @@ static int mod_sysfs_setup(struct module *mod,
1145 goto out; 1148 goto out;
1146 1149
1147 mod->holders_dir = kobject_add_dir(&mod->mkobj.kobj, "holders"); 1150 mod->holders_dir = kobject_add_dir(&mod->mkobj.kobj, "holders");
1148 if (!mod->holders_dir) 1151 if (!mod->holders_dir) {
1152 err = -ENOMEM;
1149 goto out_unreg; 1153 goto out_unreg;
1154 }
1150 1155
1151 err = module_param_sysfs_setup(mod, kparam, num_params); 1156 err = module_param_sysfs_setup(mod, kparam, num_params);
1152 if (err) 1157 if (err)
@@ -1169,16 +1174,14 @@ out_unreg:
1169out: 1174out:
1170 return err; 1175 return err;
1171} 1176}
1177#endif
1172 1178
1173static void mod_kobject_remove(struct module *mod) 1179static void mod_kobject_remove(struct module *mod)
1174{ 1180{
1175 module_remove_modinfo_attrs(mod); 1181 module_remove_modinfo_attrs(mod);
1176 module_param_sysfs_remove(mod); 1182 module_param_sysfs_remove(mod);
1177 if (mod->mkobj.drivers_dir) 1183 kobject_unregister(mod->mkobj.drivers_dir);
1178 kobject_unregister(mod->mkobj.drivers_dir); 1184 kobject_unregister(mod->holders_dir);
1179 if (mod->holders_dir)
1180 kobject_unregister(mod->holders_dir);
1181
1182 kobject_unregister(&mod->mkobj.kobj); 1185 kobject_unregister(&mod->mkobj.kobj);
1183} 1186}
1184 1187
@@ -2345,6 +2348,7 @@ void print_modules(void)
2345 printk("\n"); 2348 printk("\n");
2346} 2349}
2347 2350
2351#ifdef CONFIG_SYSFS
2348static char *make_driver_name(struct device_driver *drv) 2352static char *make_driver_name(struct device_driver *drv)
2349{ 2353{
2350 char *driver_name; 2354 char *driver_name;
@@ -2382,8 +2386,13 @@ void module_add_driver(struct module *mod, struct device_driver *drv)
2382 2386
2383 /* Lookup built-in module entry in /sys/modules */ 2387 /* Lookup built-in module entry in /sys/modules */
2384 mkobj = kset_find_obj(&module_subsys.kset, drv->mod_name); 2388 mkobj = kset_find_obj(&module_subsys.kset, drv->mod_name);
2385 if (mkobj) 2389 if (mkobj) {
2386 mk = container_of(mkobj, struct module_kobject, kobj); 2390 mk = container_of(mkobj, struct module_kobject, kobj);
2391 /* remember our module structure */
2392 drv->mkobj = mk;
2393 /* kset_find_obj took a reference */
2394 kobject_put(mkobj);
2395 }
2387 } 2396 }
2388 2397
2389 if (!mk) 2398 if (!mk)
@@ -2403,22 +2412,28 @@ EXPORT_SYMBOL(module_add_driver);
2403 2412
2404void module_remove_driver(struct device_driver *drv) 2413void module_remove_driver(struct device_driver *drv)
2405{ 2414{
2415 struct module_kobject *mk = NULL;
2406 char *driver_name; 2416 char *driver_name;
2407 2417
2408 if (!drv) 2418 if (!drv)
2409 return; 2419 return;
2410 2420
2411 sysfs_remove_link(&drv->kobj, "module"); 2421 sysfs_remove_link(&drv->kobj, "module");
2412 if (drv->owner && drv->owner->mkobj.drivers_dir) { 2422
2423 if (drv->owner)
2424 mk = &drv->owner->mkobj;
2425 else if (drv->mkobj)
2426 mk = drv->mkobj;
2427 if (mk && mk->drivers_dir) {
2413 driver_name = make_driver_name(drv); 2428 driver_name = make_driver_name(drv);
2414 if (driver_name) { 2429 if (driver_name) {
2415 sysfs_remove_link(drv->owner->mkobj.drivers_dir, 2430 sysfs_remove_link(mk->drivers_dir, driver_name);
2416 driver_name);
2417 kfree(driver_name); 2431 kfree(driver_name);
2418 } 2432 }
2419 } 2433 }
2420} 2434}
2421EXPORT_SYMBOL(module_remove_driver); 2435EXPORT_SYMBOL(module_remove_driver);
2436#endif
2422 2437
2423#ifdef CONFIG_MODVERSIONS 2438#ifdef CONFIG_MODVERSIONS
2424/* Generate the signature for struct module here, too, for modversions. */ 2439/* Generate the signature for struct module here, too, for modversions. */