Add support for load-time parameters for modules, which are passed through
a dictionary. As discussed in tech-kern@.
This commit is contained in:
parent
9edaf4a46f
commit
3fd8e29a11
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: kern_module.c,v 1.8 2008/01/19 18:20:39 rumble Exp $ */
|
||||
/* $NetBSD: kern_module.c,v 1.9 2008/03/02 11:18:43 jmmv Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2008 The NetBSD Foundation, Inc.
|
||||
@ -42,7 +42,7 @@
|
||||
*/
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
__KERNEL_RCSID(0, "$NetBSD: kern_module.c,v 1.8 2008/01/19 18:20:39 rumble Exp $");
|
||||
__KERNEL_RCSID(0, "$NetBSD: kern_module.c,v 1.9 2008/03/02 11:18:43 jmmv Exp $");
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
@ -73,7 +73,8 @@ static modinfo_t module_dummy;
|
||||
__link_set_add_rodata(modules, module_dummy);
|
||||
|
||||
static module_t *module_lookup(const char *);
|
||||
static int module_do_load(const char *, bool, bool, module_t **);
|
||||
static int module_do_load(const char *, bool, int, prop_dictionary_t,
|
||||
module_t **);
|
||||
static int module_do_unload(const char *);
|
||||
static void module_error(const char *, ...);
|
||||
static int module_do_builtin(const char *, module_t **);
|
||||
@ -142,7 +143,8 @@ module_init_class(modclass_t class)
|
||||
* list as we call module_do_load();
|
||||
*/
|
||||
while ((mod = TAILQ_FIRST(&module_bootlist)) != NULL) {
|
||||
module_do_load(mod->mod_info->mi_name, false, false, NULL);
|
||||
module_do_load(mod->mod_info->mi_name, false, 0,
|
||||
NULL, NULL);
|
||||
}
|
||||
mutex_exit(&module_lock);
|
||||
}
|
||||
@ -162,16 +164,15 @@ module_jettison(void)
|
||||
/*
|
||||
* module_load:
|
||||
*
|
||||
* Load a single module from the file system. If force is set,
|
||||
* bypass the version check.
|
||||
* Load a single module from the file system.
|
||||
*/
|
||||
int
|
||||
module_load(const char *filename, bool force)
|
||||
module_load(const char *filename, int flags, prop_dictionary_t props)
|
||||
{
|
||||
int error;
|
||||
|
||||
mutex_enter(&module_lock);
|
||||
error = module_do_load(filename, false, force, NULL);
|
||||
error = module_do_load(filename, false, flags, props, NULL);
|
||||
mutex_exit(&module_lock);
|
||||
|
||||
return error;
|
||||
@ -374,7 +375,8 @@ module_do_builtin(const char *name, module_t **modp)
|
||||
* pushed by the boot loader.
|
||||
*/
|
||||
static int
|
||||
module_do_load(const char *filename, bool isdep, bool force, module_t **modp)
|
||||
module_do_load(const char *filename, bool isdep, int flags,
|
||||
prop_dictionary_t props, module_t **modp)
|
||||
{
|
||||
static TAILQ_HEAD(,module) pending = TAILQ_HEAD_INITIALIZER(pending);
|
||||
static int depth;
|
||||
@ -545,7 +547,7 @@ module_do_load(const char *filename, bool isdep, bool force, module_t **modp)
|
||||
module_error("self-dependency detected");
|
||||
goto fail;
|
||||
}
|
||||
error = module_do_load(buf, true, force,
|
||||
error = module_do_load(buf, true, flags, NULL,
|
||||
&mod->mod_required[mod->mod_nrequired++]);
|
||||
if (error != 0 && error != EEXIST)
|
||||
goto fail;
|
||||
@ -555,7 +557,7 @@ module_do_load(const char *filename, bool isdep, bool force, module_t **modp)
|
||||
/*
|
||||
* We loaded all needed modules successfully: initialize.
|
||||
*/
|
||||
error = (*mi->mi_modcmd)(MODULE_CMD_INIT, NULL);
|
||||
error = (*mi->mi_modcmd)(MODULE_CMD_INIT, props);
|
||||
if (error != 0) {
|
||||
module_error("modctl function returned error %d", error);
|
||||
goto fail;
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: sys_module.c,v 1.3 2008/01/17 22:30:54 rumble Exp $ */
|
||||
/* $NetBSD: sys_module.c,v 1.4 2008/03/02 11:18:43 jmmv Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2008 The NetBSD Foundation, Inc.
|
||||
@ -38,7 +38,7 @@
|
||||
*/
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
__KERNEL_RCSID(0, "$NetBSD: sys_module.c,v 1.3 2008/01/17 22:30:54 rumble Exp $");
|
||||
__KERNEL_RCSID(0, "$NetBSD: sys_module.c,v 1.4 2008/03/02 11:18:43 jmmv Exp $");
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
@ -47,11 +47,65 @@ __KERNEL_RCSID(0, "$NetBSD: sys_module.c,v 1.3 2008/01/17 22:30:54 rumble Exp $"
|
||||
#include <sys/kauth.h>
|
||||
#include <sys/kobj.h>
|
||||
#include <sys/kmem.h>
|
||||
#include <sys/malloc.h>
|
||||
#include <sys/module.h>
|
||||
#include <sys/kauth.h>
|
||||
#include <sys/syscall.h>
|
||||
#include <sys/syscallargs.h>
|
||||
|
||||
static
|
||||
int
|
||||
handle_modctl_load(void *arg)
|
||||
{
|
||||
modctl_load_t *ml = (modctl_load_t *)arg;
|
||||
|
||||
char *path;
|
||||
char *props;
|
||||
int error;
|
||||
prop_dictionary_t dict;
|
||||
size_t propslen;
|
||||
|
||||
if ((ml->ml_props != NULL && ml->ml_propslen == 0) ||
|
||||
(ml->ml_props == NULL && ml->ml_propslen > 0)) {
|
||||
error = EINVAL;
|
||||
goto out1;
|
||||
}
|
||||
|
||||
path = PNBUF_GET();
|
||||
error = copyinstr(ml->ml_filename, path, MAXPATHLEN, NULL);
|
||||
if (error != 0)
|
||||
goto out2;
|
||||
|
||||
propslen = ml->ml_propslen + 1;
|
||||
props = (char *)malloc(propslen, M_TEMP, M_WAITOK|M_CANFAIL);
|
||||
if (props == NULL) {
|
||||
error = ENOMEM;
|
||||
goto out2;
|
||||
}
|
||||
|
||||
error = copyinstr(ml->ml_props, props, propslen, NULL);
|
||||
if (error != 0)
|
||||
goto out3;
|
||||
|
||||
dict = prop_dictionary_internalize(props);
|
||||
if (dict == NULL) {
|
||||
error = EINVAL;
|
||||
goto out3;
|
||||
}
|
||||
|
||||
error = module_load(path, ml->ml_flags, dict);
|
||||
|
||||
prop_object_release(dict);
|
||||
|
||||
out3:
|
||||
free(props, M_TEMP);
|
||||
out2:
|
||||
PNBUF_PUT(path);
|
||||
out1:
|
||||
|
||||
return error;
|
||||
}
|
||||
|
||||
int
|
||||
sys_modctl(struct lwp *l, const struct sys_modctl_args *uap,
|
||||
register_t *retval)
|
||||
@ -70,13 +124,11 @@ sys_modctl(struct lwp *l, const struct sys_modctl_args *uap,
|
||||
struct iovec iov;
|
||||
int error;
|
||||
void *arg;
|
||||
char *path;
|
||||
|
||||
arg = SCARG(uap, arg);
|
||||
|
||||
switch (SCARG(uap, cmd)) {
|
||||
case MODCTL_LOAD:
|
||||
case MODCTL_FORCELOAD:
|
||||
case MODCTL_UNLOAD:
|
||||
/* Authorize. */
|
||||
error = kauth_authorize_system(l->l_cred, KAUTH_SYSTEM_MODULE,
|
||||
@ -90,15 +142,8 @@ sys_modctl(struct lwp *l, const struct sys_modctl_args *uap,
|
||||
}
|
||||
|
||||
switch (SCARG(uap, cmd)) {
|
||||
case MODCTL_FORCELOAD:
|
||||
case MODCTL_LOAD:
|
||||
path = PNBUF_GET();
|
||||
error = copyinstr(arg, path, MAXPATHLEN, NULL);
|
||||
if (error == 0) {
|
||||
error = module_load(path,
|
||||
SCARG(uap, cmd) == MODCTL_FORCELOAD);
|
||||
}
|
||||
PNBUF_PUT(path);
|
||||
error = handle_modctl_load(arg);
|
||||
break;
|
||||
|
||||
case MODCTL_UNLOAD:
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: module.h,v 1.1 2008/01/16 12:34:54 ad Exp $ */
|
||||
/* $NetBSD: module.h,v 1.2 2008/03/02 11:18:43 jmmv Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2008 The NetBSD Foundation, Inc.
|
||||
@ -92,6 +92,8 @@ typedef struct module {
|
||||
|
||||
#include <sys/mutex.h>
|
||||
|
||||
#include <prop/proplib.h>
|
||||
|
||||
/*
|
||||
* Per-module linkage. Loadable modules have a `link_set_modules' section
|
||||
* containing only one entry, pointing to the module's modinfo_t record.
|
||||
@ -121,7 +123,7 @@ void module_init_class(modclass_t);
|
||||
int module_prime(void *, size_t);
|
||||
void module_jettison(void);
|
||||
|
||||
int module_load(const char *, bool);
|
||||
int module_load(const char *, int, prop_dictionary_t);
|
||||
int module_unload(const char *);
|
||||
int module_hold(const char *);
|
||||
void module_rele(const char *);
|
||||
@ -132,9 +134,18 @@ void module_rele(const char *);
|
||||
|
||||
#endif /* _KERNEL */
|
||||
|
||||
typedef struct modctl_load {
|
||||
const char *ml_filename;
|
||||
|
||||
#define MODCTL_LOAD_FORCE 1
|
||||
int ml_flags;
|
||||
|
||||
const char *ml_props;
|
||||
size_t ml_propslen;
|
||||
} modctl_load_t;
|
||||
|
||||
typedef enum modctl {
|
||||
MODCTL_LOAD, /* char *filename */
|
||||
MODCTL_FORCELOAD, /* char *filename */
|
||||
MODCTL_LOAD, /* modctl_load_t *ml */
|
||||
MODCTL_UNLOAD, /* char *name */
|
||||
MODCTL_STAT /* struct iovec *buffer */
|
||||
} modctl_t;
|
||||
|
Loading…
Reference in New Issue
Block a user