summaryrefslogtreecommitdiffstats
path: root/sys/kern/kern_module.c
diff options
context:
space:
mode:
authorjhb <jhb@FreeBSD.org>2008-12-05 13:40:25 +0000
committerjhb <jhb@FreeBSD.org>2008-12-05 13:40:25 +0000
commit0ac14961cc48c1ab4910a0dfb21d6d4a3137f5a6 (patch)
treea8522c6b0e4d16f7f55489f7822e5cbf7405ddf4 /sys/kern/kern_module.c
parentd57e5b9d8b3abb250cd15d2e7d49be4668ad956a (diff)
downloadFreeBSD-src-0ac14961cc48c1ab4910a0dfb21d6d4a3137f5a6.zip
FreeBSD-src-0ac14961cc48c1ab4910a0dfb21d6d4a3137f5a6.tar.gz
- Invoke MOD_QUIESCE on all modules in a linker file (kld) before
unloading any modules. As a result, if any module veto's an unload request via MOD_QUIESCE, the entire set of modules for that linker file will remain loaded and active now rather than leaving the kld in a weird state where some modules are loaded and some are unloaded. - This also moves the logic for handling the "forced" unload flag out of kern_module.c and into kern_linker.c which is a bit cleaner. - Add a module_name() routine that returns the name of a module and use that instead of printing pointer values in debug messages when a module fails MOD_QUIESCE or MOD_UNLOAD. MFC after: 1 month
Diffstat (limited to 'sys/kern/kern_module.c')
-rw-r--r--sys/kern/kern_module.c25
1 files changed, 20 insertions, 5 deletions
diff --git a/sys/kern/kern_module.c b/sys/kern/kern_module.c
index e2c02b8..fef7f87 100644
--- a/sys/kern/kern_module.c
+++ b/sys/kern/kern_module.c
@@ -196,9 +196,7 @@ module_release(module_t mod)
TAILQ_REMOVE(&modules, mod, link);
if (mod->file)
TAILQ_REMOVE(&mod->file->modules, mod, flink);
- MOD_XUNLOCK;
free(mod, M_MODULE);
- MOD_XLOCK;
}
}
@@ -232,16 +230,25 @@ module_lookupbyid(int modid)
}
int
-module_unload(module_t mod, int flags)
+module_quiesce(module_t mod)
{
int error;
mtx_lock(&Giant);
error = MOD_EVENT(mod, MOD_QUIESCE);
+ mtx_unlock(&Giant);
if (error == EOPNOTSUPP || error == EINVAL)
error = 0;
- if (error == 0 || flags == LINKER_UNLOAD_FORCE)
- error = MOD_EVENT(mod, MOD_UNLOAD);
+ return (error);
+}
+
+int
+module_unload(module_t mod)
+{
+ int error;
+
+ mtx_lock(&Giant);
+ error = MOD_EVENT(mod, MOD_UNLOAD);
mtx_unlock(&Giant);
return (error);
}
@@ -262,6 +269,14 @@ module_getfnext(module_t mod)
return (TAILQ_NEXT(mod, flink));
}
+const char *
+module_getname(module_t mod)
+{
+
+ MOD_LOCK_ASSERT;
+ return (mod->name);
+}
+
void
module_setspecific(module_t mod, modspecific_t *datap)
{
OpenPOWER on IntegriCloud