Module Name:    src
Committed By:   pgoyette
Date:           Mon Jun 25 07:22:54 UTC 2018

Modified Files:
        src/sys/kern [pgoyette-compat]: kern_module.c
        src/sys/sys [pgoyette-compat]: module.h

Log Message:
Resolve conflicts with HEAD


To generate a diff of this commit:
cvs rdiff -u -r1.130.2.8 -r1.130.2.9 src/sys/kern/kern_module.c
cvs rdiff -u -r1.41.14.8 -r1.41.14.9 src/sys/sys/module.h

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/sys/kern/kern_module.c
diff -u src/sys/kern/kern_module.c:1.130.2.8 src/sys/kern/kern_module.c:1.130.2.9
--- src/sys/kern/kern_module.c:1.130.2.8	Mon Apr  2 00:18:43 2018
+++ src/sys/kern/kern_module.c	Mon Jun 25 07:22:54 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: kern_module.c,v 1.130.2.8 2018/04/02 00:18:43 pgoyette Exp $	*/
+/*	$NetBSD: kern_module.c,v 1.130.2.9 2018/06/25 07:22:54 pgoyette Exp $	*/
 
 /*-
  * Copyright (c) 2008 The NetBSD Foundation, Inc.
@@ -34,7 +34,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: kern_module.c,v 1.130.2.8 2018/04/02 00:18:43 pgoyette Exp $");
+__KERNEL_RCSID(0, "$NetBSD: kern_module.c,v 1.130.2.9 2018/06/25 07:22:54 pgoyette Exp $");
 
 #define _MODULE_INTERNAL
 
@@ -65,6 +65,21 @@ struct modlist        module_list = TAIL
 struct modlist        module_builtins = TAILQ_HEAD_INITIALIZER(module_builtins);
 static struct modlist module_bootlist = TAILQ_HEAD_INITIALIZER(module_bootlist);
 
+struct module_callbacks {
+	TAILQ_ENTRY(module_callbacks) modcb_list;
+	void (*modcb_load)(struct module *);
+	void (*modcb_unload)(struct module *);
+};
+TAILQ_HEAD(modcblist, module_callbacks);
+static struct modcblist modcblist;
+
+static module_t *module_netbsd;
+static const modinfo_t module_netbsd_modinfo = {
+	.mi_version = __NetBSD_Version__,
+	.mi_class = MODULE_CLASS_MISC,
+	.mi_name = "netbsd"
+};
+
 static module_t	*module_active;
 bool		module_verbose_on;
 #ifdef MODULAR_DEFAULT_AUTOLOAD
@@ -84,11 +99,14 @@ int (*module_load_vfs_vec)(const char *,
 
 static kauth_listener_t	module_listener;
 
+static specificdata_domain_t module_specificdata_domain;
+
 /* Ensure that the kernel's link set isn't empty. */
 static modinfo_t module_dummy;
 __link_set_add_rodata(modules, module_dummy);
 
 static module_t	*module_newmodule(modsrc_t);
+static void	module_free(module_t *);
 static void	module_require_force(module_t *);
 static int	module_do_load(const char *, bool, int, prop_dictionary_t,
 		    module_t **, modclass_t modclass, bool);
@@ -107,6 +125,9 @@ static bool	module_merge_dicts(prop_dict
 static void	sysctl_module_setup(void);
 static int	sysctl_module_autotime(SYSCTLFN_PROTO);
 
+static void	module_callback_load(struct module *);
+static void	module_callback_unload(struct module *);
+
 #define MODULE_CLASS_MATCH(mi, modclass) \
 	((modclass) == MODULE_CLASS_ANY || (modclass) == (mi)->mi_class)
 
@@ -117,6 +138,13 @@ module_incompat(const modinfo_t *mi, int
 	    mi->mi_name, modclass, mi->mi_class);
 }
 
+struct module *
+module_kernel(void)
+{
+
+	return module_netbsd;
+}
+
 /*
  * module_error:
  *
@@ -153,6 +181,30 @@ module_print(const char *fmt, ...)
 	}
 }
 
+/*
+ * module_name:
+ *
+ *	Utility function: return the module's name.
+ */
+const char *
+module_name(struct module *mod)
+{
+
+	return mod->mod_info->mi_name;
+}
+
+/*
+ * module_source:
+ *
+ *	Utility function: return the module's source.
+ */
+modsrc_t
+module_source(struct module *mod)
+{
+
+	return mod->mod_source;
+}
+
 static int
 module_listener_cb(kauth_cred_t cred, kauth_action_t action, void *cookie,
     void *arg0, void *arg1, void *arg2, void *arg3)
@@ -180,12 +232,25 @@ module_newmodule(modsrc_t source)
 
 	mod = kmem_zalloc(sizeof(*mod), KM_SLEEP);
 	mod->mod_source = source;
-	mod->mod_info = NULL;
-	mod->mod_flags = 0;
+	specificdata_init(module_specificdata_domain, &mod->mod_sdref);
 	return mod;
 }
 
 /*
+ * Free a module_t
+ */
+static void
+module_free(module_t *mod)
+{
+
+	specificdata_fini(module_specificdata_domain, &mod->mod_sdref);
+	if (mod->mod_required)
+		kmem_free(mod->mod_required, mod->mod_arequired *
+		    sizeof(module_t));
+	kmem_free(mod, sizeof(*mod));
+}
+
+/*
  * Require the -f (force) flag to load a module
  */
 static void
@@ -281,7 +346,7 @@ module_builtin_add(modinfo_t *const *mip
 	if (rv != 0) {
 		for (i = 0; i < nmodinfo; i++) {
 			if (modp[i])
-				kmem_free(modp[i], sizeof(*modp[i]));
+				module_free(modp[i]);
 		}
 	}
 	kmem_free(modp, sizeof(*modp) * nmodinfo);
@@ -348,6 +413,7 @@ module_init(void)
 	}
 	cv_init(&module_thread_cv, "mod_unld");
 	mutex_init(&module_thread_lock, MUTEX_DEFAULT, IPL_NONE);
+	TAILQ_INIT(&modcblist);
 
 #ifdef MODULAR	/* XXX */
 	module_init_md();
@@ -374,6 +440,11 @@ module_init(void)
 	}
 
 	sysctl_module_setup();
+	module_specificdata_domain = specificdata_domain_create();
+
+	module_netbsd = module_newmodule(MODULE_SOURCE_KERNEL);
+	module_netbsd->mod_refcnt = 1;
+	module_netbsd->mod_info = &module_netbsd_modinfo;
 }
 
 /*
@@ -707,21 +778,13 @@ module_lookup(const char *name)
  *	responsibility to ensure that the reference is dropped
  *	later.
  */
-int
-module_hold(const char *name)
+void
+module_hold(module_t *mod)
 {
-	module_t *mod;
 
 	kernconfig_lock();
-	mod = module_lookup(name);
-	if (mod == NULL) {
-		kernconfig_unlock();
-		return ENOENT;
-	}
 	mod->mod_refcnt++;
 	kernconfig_unlock();
-
-	return 0;
 }
 
 /*
@@ -730,16 +793,11 @@ module_hold(const char *name)
  *	Release a reference acquired with module_hold().
  */
 void
-module_rele(const char *name)
+module_rele(module_t *mod)
 {
-	module_t *mod;
 
 	kernconfig_lock();
-	mod = module_lookup(name);
-	if (mod == NULL) {
-		kernconfig_unlock();
-		panic("%s: gone", __func__);
-	}
+	KASSERT(mod->mod_refcnt > 0);
 	mod->mod_refcnt--;
 	kernconfig_unlock();
 }
@@ -1045,8 +1103,9 @@ module_do_load(const char *name, bool is
 				module_error("vfs load failed for `%s', "
 				    "error %d", name, error);
 #endif
-			kmem_free(mod, sizeof(*mod));
 			SLIST_REMOVE_HEAD(&pend_stack, pe_entry);
+			module_free(mod);
+			depth--;
 			return error;
 		}
 		TAILQ_INSERT_TAIL(pending, mod, mod_chain);
@@ -1258,6 +1317,7 @@ module_do_load(const char *name, bool is
 	}
 	SLIST_REMOVE_HEAD(&pend_stack, pe_entry);
 	module_print("module `%s' loaded successfully", mi->mi_name);
+	module_callback_load(mod);
 	return 0;
 
  fail1:
@@ -1270,11 +1330,9 @@ module_do_load(const char *name, bool is
 		filedict = NULL;
 	}
 	TAILQ_REMOVE(pending, mod, mod_chain);
-	if (mod->mod_required)
-		kmem_free(mod->mod_required, mod->mod_arequired *
-		    sizeof(module_t));
-	kmem_free(mod, sizeof(*mod));
 	SLIST_REMOVE_HEAD(&pend_stack, pe_entry);
+	module_free(mod);
+	depth--;
 	return error;
 }
 
@@ -1318,6 +1376,7 @@ module_do_unload(const char *name, bool 
 
 	prev_active = module_active;
 	module_active = mod;
+	module_callback_unload(mod);
 	error = (*mod->mod_info->mi_modcmd)(MODULE_CMD_FINI, NULL);
 	module_active = prev_active;
 	if (error != 0) {
@@ -1345,7 +1404,7 @@ module_do_unload(const char *name, bool 
 		TAILQ_INSERT_TAIL(&module_builtins, mod, mod_chain);
 		module_builtinlist++;
 	} else {
-		kmem_free(mod, sizeof(*mod));
+		module_free(mod);
 	}
 	module_gen++;
 
@@ -1395,7 +1454,7 @@ module_prime(const char *name, void *bas
 
 	error = kobj_load_mem(&mod->mod_kobj, name, base, size);
 	if (error != 0) {
-		kmem_free(mod, sizeof(*mod));
+		module_free(mod);
 		module_error("unable to load `%s' pushed by boot loader, "
 		    "error %d", name, error);
 		return error;
@@ -1403,7 +1462,7 @@ module_prime(const char *name, void *bas
 	error = module_fetch_info(mod);
 	if (error != 0) {
 		kobj_unload(mod->mod_kobj);
-		kmem_free(mod, sizeof(*mod));
+		module_free(mod);
 		module_error("unable to fetch_info for `%s' pushed by boot "
 		    "loader, error %d", name, error);
 		return error;
@@ -1649,3 +1708,131 @@ out:
 
 	return !error;
 }
+
+/*
+ * module_specific_key_create:
+ *
+ *	Create a key for subsystem module-specific data.
+ */
+specificdata_key_t
+module_specific_key_create(specificdata_key_t *keyp, specificdata_dtor_t dtor)
+{
+
+	return specificdata_key_create(module_specificdata_domain, keyp, dtor);
+}
+
+/*
+ * module_specific_key_delete:
+ *
+ *	Delete a key for subsystem module-specific data.
+ */
+void
+module_specific_key_delete(specificdata_key_t key)
+{
+
+	return specificdata_key_delete(module_specificdata_domain, key);
+}
+
+/*
+ * module_getspecific:
+ *
+ *	Return module-specific data corresponding to the specified key.
+ */
+void *
+module_getspecific(module_t *mod, specificdata_key_t key)
+{
+
+	return specificdata_getspecific(module_specificdata_domain,
+	    &mod->mod_sdref, key);
+}
+
+/*
+ * module_setspecific:
+ *
+ *	Set module-specific data corresponding to the specified key.
+ */
+void
+module_setspecific(module_t *mod, specificdata_key_t key, void *data)
+{
+
+	specificdata_setspecific(module_specificdata_domain,
+	    &mod->mod_sdref, key, data);
+}
+
+/*
+ * module_register_callbacks:
+ *
+ *	Register a new set of callbacks to be called on module load/unload.
+ *	Call the load callback on each existing module.
+ *	Return an opaque handle for unregistering these later.
+ */
+void *
+module_register_callbacks(void (*load)(struct module *),
+    void (*unload)(struct module *))
+{
+	struct module_callbacks *modcb;
+	struct module *mod;
+
+	modcb = kmem_alloc(sizeof(*modcb), KM_SLEEP);
+	modcb->modcb_load = load;
+	modcb->modcb_unload = unload;
+
+	kernconfig_lock();
+	TAILQ_INSERT_TAIL(&modcblist, modcb, modcb_list);
+	TAILQ_FOREACH(mod, &module_list, mod_chain)
+		load(mod);
+	kernconfig_unlock();
+
+	return modcb;
+}
+
+/*
+ * module_unregister_callbacks:
+ *
+ *	Unregister a previously-registered set of module load/unload callbacks.
+ *	Call the unload callback on each existing module.
+ */
+void
+module_unregister_callbacks(void *opaque)
+{
+	struct module_callbacks *modcb;
+	struct module *mod;
+
+	modcb = opaque;
+	kernconfig_lock();
+	TAILQ_FOREACH(mod, &module_list, mod_chain)
+		modcb->modcb_unload(mod);
+	TAILQ_REMOVE(&modcblist, modcb, modcb_list);
+	kernconfig_unlock();
+	kmem_free(modcb, sizeof(*modcb));
+}
+
+/*
+ * module_callback_load:
+ *
+ *	Helper routine: call all load callbacks on a module being loaded.
+ */
+static void
+module_callback_load(struct module *mod)
+{
+	struct module_callbacks *modcb;
+
+	TAILQ_FOREACH(modcb, &modcblist, modcb_list) {
+		modcb->modcb_load(mod);
+	}
+}
+
+/*
+ * module_callback_unload:
+ *
+ *	Helper routine: call all unload callbacks on a module being unloaded.
+ */
+static void
+module_callback_unload(struct module *mod)
+{
+	struct module_callbacks *modcb;
+
+	TAILQ_FOREACH(modcb, &modcblist, modcb_list) {
+		modcb->modcb_unload(mod);
+	}
+}

Index: src/sys/sys/module.h
diff -u src/sys/sys/module.h:1.41.14.8 src/sys/sys/module.h:1.41.14.9
--- src/sys/sys/module.h:1.41.14.8	Tue Apr  3 08:29:44 2018
+++ src/sys/sys/module.h	Mon Jun 25 07:22:54 2018
@@ -1,4 +1,4 @@
-/*	$NetBSD: module.h,v 1.41.14.8 2018/04/03 08:29:44 pgoyette Exp $	*/
+/*	$NetBSD: module.h,v 1.41.14.9 2018/06/25 07:22:54 pgoyette Exp $	*/
 
 /*-
  * Copyright (c) 2008 The NetBSD Foundation, Inc.
@@ -32,7 +32,6 @@
 #include <sys/types.h>
 #include <sys/param.h>
 #include <sys/cdefs.h>
-#include <sys/queue.h>
 #include <sys/uio.h>
 
 #define	MAXMODNAME	32
@@ -68,6 +67,8 @@ typedef enum modcmd {
 
 #include <sys/kernel.h>
 #include <sys/mutex.h>
+#include <sys/queue.h>
+#include <sys/specificdata.h>
 
 #include <prop/proplib.h>
 
@@ -84,6 +85,10 @@ typedef struct modinfo {
 /* Per module information, maintained by kern_module.c */ 
 typedef struct module {
 	u_int			mod_refcnt;
+	int			mod_flags;
+#define MODFLG_MUST_FORCE	0x01
+#define MODFLG_AUTO_LOADED	0x02
+#define	MODFLG_IS_ALIAS		0x04	/* only for export via modstat_t */
 	const modinfo_t		*mod_info;
 	struct kobj		*mod_kobj;
 	TAILQ_ENTRY(module)	mod_chain;
@@ -92,13 +97,7 @@ typedef struct module {
 	u_int			mod_arequired;
 	modsrc_t		mod_source;
 	time_t			mod_autotime;
-	void 			*mod_ctf;
-	u_int			mod_fbtentries;	/* DTrace FBT entry count */
-	int			mod_flags;
-#define MODFLG_MUST_FORCE	0x01
-#define MODFLG_AUTO_LOADED	0x02
-#define	MODFLG_IS_ALIAS		0x04	/* only for export via modstat_t */
-
+	specificdata_reference	mod_sdref;
 } module_t;
 
 /*
@@ -190,18 +189,29 @@ void	module_init_md(void);
 void	module_init_class(modclass_t);
 int	module_prime(const char *, void *, size_t);
 
+module_t *module_kernel(void);
+const char *module_name(struct module *);
+modsrc_t module_source(struct module *);
 bool	module_compatible(int, int);
 int	module_load(const char *, int, prop_dictionary_t, modclass_t);
 int	module_builtin_add(modinfo_t * const *, size_t, bool);
 int	module_builtin_remove(modinfo_t *, bool);
 int	module_autoload(const char *, modclass_t);
 int	module_unload(const char *);
-int	module_hold(const char *);
-void	module_rele(const char *);
+void	module_hold(module_t *);
+void	module_rele(module_t *);
 int	module_find_section(const char *, void **, size_t *);
 void	module_thread_kick(void);
 void	module_load_vfs_init(void);
 
+specificdata_key_t module_specific_key_create(specificdata_key_t *, specificdata_dtor_t);
+void	module_specific_key_delete(specificdata_key_t);
+void	*module_getspecific(module_t *, specificdata_key_t);
+void	module_setspecific(module_t *, specificdata_key_t, void *);
+void	*module_register_callbacks(void (*)(struct module *),
+				  void (*)(struct module *));
+void	module_unregister_callbacks(void *);
+
 void	module_whatis(uintptr_t, void (*)(const char *, ...)
     __printflike(1, 2));
 void	module_print_list(void (*)(const char *, ...) __printflike(1, 2));
@@ -237,13 +247,12 @@ typedef struct modctl_load {
 	size_t ml_propslen;
 } modctl_load_t;
 
-typedef enum modctl {
+enum modctl {
 	MODCTL_LOAD,		/* modctl_load_t *ml */
 	MODCTL_UNLOAD,		/* char *name */
-	MODCTL_OSTAT,		/* struct iovec *buffer */
-	MODCTL_EXISTS,		/* enum: 0: load, 1: autoload */
-	MODCTL_STAT		/* struct iovec *buffer */
-} modctl_t;
+	MODCTL_STAT,		/* struct iovec *buffer */
+	MODCTL_EXISTS		/* enum: 0: load, 1: autoload */
+};
 
 /*
  * This structure intentionally has the same layout for 32 and 64

Reply via email to