Woops...forgot to commit this file. Part of Terry Lambert's loadable kernel
module support, with NetBSD improvements.
This commit is contained in:
parent
6d35ce1570
commit
255b8baf81
363
sys/sys/lkm.h
Normal file
363
sys/sys/lkm.h
Normal file
@ -0,0 +1,363 @@
|
||||
/*
|
||||
* Header file used by loadable kernel modules and loadable kernel module
|
||||
* utilities.
|
||||
*
|
||||
* 23 Jan 93 Terry Lambert Original
|
||||
*
|
||||
* Copyright (c) 1992 Terrence R. Lambert.
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by Terrence R. Lambert.
|
||||
* 4. The name Terrence R. Lambert may not be used to endorse or promote
|
||||
* products derived from this software without specific prior written
|
||||
* permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY TERRENCE R. LAMBERT ``AS IS'' AND ANY
|
||||
* EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE TERRENCE R. LAMBERT BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* $Id$
|
||||
*/
|
||||
|
||||
#ifndef _SYS_LKM_H_
|
||||
#define _SYS_LKM_H_
|
||||
|
||||
/*
|
||||
* Supported module types
|
||||
*/
|
||||
typedef enum loadmod {
|
||||
LM_SYSCALL,
|
||||
LM_VFS,
|
||||
LM_DEV,
|
||||
LM_STRMOD,
|
||||
LM_EXEC,
|
||||
LM_MISC
|
||||
} MODTYPE;
|
||||
|
||||
|
||||
#define LKM_VERSION 1 /* version of module loader */
|
||||
#define MAXLKMNAME 32
|
||||
|
||||
/****************************************************************************/
|
||||
|
||||
#ifdef KERNEL
|
||||
|
||||
/*
|
||||
* Loadable system call
|
||||
*/
|
||||
struct lkm_syscall {
|
||||
MODTYPE lkm_type;
|
||||
int lkm_ver;
|
||||
char *lkm_name;
|
||||
u_long lkm_offset; /* save/assign area */
|
||||
struct sysent *lkm_sysent;
|
||||
struct sysent lkm_oldent; /* save area for unload */
|
||||
};
|
||||
|
||||
/*
|
||||
* Loadable file system
|
||||
*/
|
||||
struct lkm_vfs {
|
||||
MODTYPE lkm_type;
|
||||
int lkm_ver;
|
||||
char *lkm_name;
|
||||
u_long lkm_offset;
|
||||
struct vfsops *lkm_vfsops;
|
||||
};
|
||||
|
||||
/*
|
||||
* Supported device module types
|
||||
*/
|
||||
typedef enum devtype {
|
||||
LM_DT_BLOCK,
|
||||
LM_DT_CHAR
|
||||
} DEVTYPE;
|
||||
|
||||
/*
|
||||
* Loadable device driver
|
||||
*/
|
||||
struct lkm_dev {
|
||||
MODTYPE lkm_type;
|
||||
int lkm_ver;
|
||||
char *lkm_name;
|
||||
u_long lkm_offset;
|
||||
DEVTYPE lkm_devtype;
|
||||
union {
|
||||
void *anon;
|
||||
struct bdevsw *bdev;
|
||||
struct cdevsw *cdev;
|
||||
} lkm_dev;
|
||||
union {
|
||||
struct bdevsw bdev;
|
||||
struct cdevsw cdev;
|
||||
} lkm_olddev;
|
||||
};
|
||||
|
||||
/*
|
||||
* Loadable streams module
|
||||
*/
|
||||
struct lkm_strmod {
|
||||
MODTYPE lkm_type;
|
||||
int lkm_ver;
|
||||
char *lkm_name;
|
||||
u_long lkm_offset;
|
||||
/*
|
||||
* Removed: future release
|
||||
*/
|
||||
};
|
||||
|
||||
/*
|
||||
* Exec loader
|
||||
*/
|
||||
struct lkm_exec {
|
||||
MODTYPE lkm_type;
|
||||
int lkm_ver;
|
||||
char *lkm_name;
|
||||
u_long lkm_offset;
|
||||
struct execsw *lkm_exec;
|
||||
struct execsw lkm_oldexec;
|
||||
};
|
||||
|
||||
/*
|
||||
* Miscellaneous module (complex load/unload, potentially complex stat
|
||||
*/
|
||||
struct lkm_misc {
|
||||
MODTYPE lkm_type;
|
||||
int lkm_ver;
|
||||
char *lkm_name;
|
||||
u_long lkm_offset;
|
||||
};
|
||||
|
||||
/*
|
||||
* Any module (to get type and name info without knowing type)
|
||||
*/
|
||||
struct lkm_any {
|
||||
MODTYPE lkm_type;
|
||||
int lkm_ver;
|
||||
char *lkm_name;
|
||||
u_long lkm_offset;
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* Generic reference ala XEvent to allow single entry point in the xxxinit()
|
||||
* routine.
|
||||
*/
|
||||
union lkm_generic {
|
||||
struct lkm_any *lkm_any;
|
||||
struct lkm_syscall *lkm_syscall;
|
||||
struct lkm_vfs *lkm_vfs;
|
||||
struct lkm_dev *lkm_dev;
|
||||
struct lkm_strmod *lkm_strmod;
|
||||
struct lkm_exec *lkm_exec;
|
||||
struct lkm_misc *lkm_misc;
|
||||
};
|
||||
|
||||
union lkm_all {
|
||||
struct lkm_any lkm_any;
|
||||
struct lkm_syscall lkm_syscall;
|
||||
struct lkm_vfs lkm_vfs;
|
||||
struct lkm_dev lkm_dev;
|
||||
struct lkm_strmod lkm_strmod;
|
||||
struct lkm_exec lkm_exec;
|
||||
struct lkm_misc lkm_misc;
|
||||
};
|
||||
|
||||
/*
|
||||
* Per module information structure
|
||||
*/
|
||||
struct lkm_table {
|
||||
int type;
|
||||
u_long size;
|
||||
u_long offset;
|
||||
u_long area;
|
||||
char used;
|
||||
|
||||
int ver; /* version (INIT) */
|
||||
int refcnt; /* reference count (INIT) */
|
||||
int depcnt; /* dependency count (INIT) */
|
||||
int id; /* identifier (INIT) */
|
||||
|
||||
int (*entry)(); /* entry function */
|
||||
union lkm_generic private; /* module private data */
|
||||
};
|
||||
|
||||
|
||||
#define LKM_E_LOAD 1
|
||||
#define LKM_E_UNLOAD 2
|
||||
#define LKM_E_STAT 3
|
||||
|
||||
|
||||
#define MOD_SYSCALL(name,callslot,sysentp) \
|
||||
static struct lkm_syscall _module = { \
|
||||
LM_SYSCALL, \
|
||||
LKM_VERSION, \
|
||||
name, \
|
||||
callslot, \
|
||||
sysentp \
|
||||
};
|
||||
|
||||
#define MOD_VFS(name,vfsslot,vfsopsp) \
|
||||
static struct lkm_vfs _module = { \
|
||||
LM_VFS, \
|
||||
LKM_VERSION, \
|
||||
name, \
|
||||
vfsslot, \
|
||||
vfsopsp \
|
||||
};
|
||||
|
||||
#define MOD_DEV(name,devtype,devslot,devp) \
|
||||
static struct lkm_dev _module = { \
|
||||
LM_DEV, \
|
||||
LKM_VERSION, \
|
||||
name, \
|
||||
devslot, \
|
||||
devtype, \
|
||||
(void *)devp \
|
||||
};
|
||||
|
||||
#define MOD_EXEC(name,execslot,execsw) \
|
||||
static struct lkm_exec _module = { \
|
||||
LM_EXEC, \
|
||||
LKM_VERSION, \
|
||||
name, \
|
||||
execslot, \
|
||||
execsw \
|
||||
};
|
||||
|
||||
#define MOD_MISC(name) \
|
||||
static struct lkm_misc _module = { \
|
||||
LM_MISC, \
|
||||
LKM_VERSION, \
|
||||
name \
|
||||
};
|
||||
|
||||
|
||||
extern int nosys();
|
||||
|
||||
/*
|
||||
* DISPATCH -- body function for use in module entry point function;
|
||||
* generally, the function body will consist entirely of a single
|
||||
* DISPATCH line.
|
||||
*
|
||||
* If load/unload/stat are not "nosys", then they are called on each
|
||||
* corresponding entry instance. "cmd" is passed to each function so
|
||||
* that a single function can be used if desired.
|
||||
*/
|
||||
#define DISPATCH(lkmtp,cmd,ver,load,unload,stat) \
|
||||
if (ver != LKM_VERSION) \
|
||||
return EINVAL; /* version mismatch */ \
|
||||
switch (cmd) { \
|
||||
int error; \
|
||||
case LKM_E_LOAD: \
|
||||
lkmtp->private.lkm_any = (struct lkm_any *)&_module; \
|
||||
if (load != nosys && (error = load(lkmtp, cmd))) \
|
||||
return error; \
|
||||
break; \
|
||||
case LKM_E_UNLOAD: \
|
||||
if (unload != nosys && (error = unload(lkmtp, cmd))) \
|
||||
return error; \
|
||||
break; \
|
||||
case LKM_E_STAT: \
|
||||
if (stat != nosys && (error = stat(lkmtp, cmd))) \
|
||||
return error; \
|
||||
break; \
|
||||
} \
|
||||
return lkmdispatch(lkmtp, cmd);
|
||||
|
||||
#endif /* KERNEL */
|
||||
|
||||
/****************************************************************************/
|
||||
|
||||
/*
|
||||
* IOCTL's recognized by /dev/lkm
|
||||
*/
|
||||
#define LMRESERV _IOWR('K', 0, struct lmc_resrv)
|
||||
#define LMLOADBUF _IOW('K', 1, struct lmc_loadbuf)
|
||||
#define LMUNRESRV _IO('K', 2)
|
||||
#define LMREADY _IOW('K', 3, int)
|
||||
|
||||
#define LMLOAD _IOW('K', 9, struct lmc_load)
|
||||
#define LMUNLOAD _IOWR('K', 10, struct lmc_unload)
|
||||
#define LMSTAT _IOWR('K', 11, struct lmc_stat)
|
||||
|
||||
#define MODIOBUF 512 /* # of bytes at a time to loadbuf */
|
||||
|
||||
/*
|
||||
* IOCTL arguments
|
||||
*/
|
||||
|
||||
|
||||
/*
|
||||
* Reserve a page-aligned block of kernel memory for the module
|
||||
*/
|
||||
struct lmc_resrv {
|
||||
u_long size; /* IN: size of module to reserve */
|
||||
char *name; /* IN: name (must be provided */
|
||||
int slot; /* OUT: allocated slot (module ID) */
|
||||
u_long addr; /* OUT: Link-to address */
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* Copy a buffer at a time into the allocated area in the kernel; writes
|
||||
* are assumed to occur contiguously.
|
||||
*/
|
||||
struct lmc_loadbuf {
|
||||
int cnt; /* IN: # of chars pointed to by data */
|
||||
char *data; /* IN: pointer to data buffer */
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* Load a module (assumes it's been mmapped to address before call)
|
||||
*/
|
||||
struct lmc_load {
|
||||
caddr_t address; /* IN: user space mmap address */
|
||||
int status; /* OUT: status of operation */
|
||||
int id; /* OUT: module ID if loaded */
|
||||
};
|
||||
|
||||
/*
|
||||
* Unload a module (by name/id)
|
||||
*/
|
||||
struct lmc_unload {
|
||||
int id; /* IN: module ID to unload */
|
||||
char *name; /* IN: module name to unload if id -1 */
|
||||
int status; /* OUT: status of operation */
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* Get module information for a given id (or name if id == -1).
|
||||
*/
|
||||
struct lmc_stat {
|
||||
int id; /* IN: module ID to unload */
|
||||
char name[MAXLKMNAME]; /* IN/OUT: name of module */
|
||||
u_long offset; /* OUT: target table offset */
|
||||
MODTYPE type; /* OUT: type of module */
|
||||
u_long area; /* OUT: kernel load addr */
|
||||
u_long size; /* OUT: module size (pages) */
|
||||
u_long private; /* OUT: module private data */
|
||||
int ver; /* OUT: lkm compile version */
|
||||
};
|
||||
|
||||
#endif /* !_SYS_LKM_H_ */
|
Loading…
x
Reference in New Issue
Block a user