2.6. Passing Command Line Arguments to a Module

Modules can take command line arguments, but not with the argc/argv you might be used to.

To allow arguments to be passed to your module, declare the variables that will take the values of the command line arguments as global and then use the MODULE_PARM() macro, (defined in linux/module.h) to set the mechanism up. At runtime, insmod will fill the variables with any command line arguments that are given. The variable declarations and macros should be placed at the beginning of the module for clarity. The example code should clear up my admittedly lousy explanation.

The MODULE_PARM() macro takes 2 arguments: the name of the variable and its type. The supported variable types are "b": single byte, "h": short int, "i": integer, "l": long int and "s": string. Strings should be declared as "char *" and insmod will allocate memory for them. You should always try to give the variables an initial default value. This is kernel code, and you should program defensively. For example:

    int myint = 3;
char *mystr;

MODULE_PARM (myint, "i");
MODULE_PARM (mystr, "s");

Arrays are supported too. An integer value preceding the type in MODULE_PARM will indicate an array of some maximum length. Two numbers separated by a '-' will give the minimum and maximum number of values. For example, an array of shorts with at least 2 and no more than 4 values could be declared as:

    int myshortArray[4];
MODULE_PARM (myintArray, "2-4i");

A good use for this is to have the module variable's default values set, like which IO port or IO memory to use. If the variables contain the default values, then perform autodetection (explained elsewhere). Otherwise, keep the current value. This will be made clear later on. For now, I just want to demonstrate passing arguments to a module.

Example 2-7. hello-5.c

/*  hello-5.c - Demonstrates command line argument passing to a module.
*/
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
MODULE_LICENSE("GPL");
MODULE_AUTHOR("Peiter Jay Salzman");

static short int myshort = 1;
static int myint = 420;
static long int mylong = 9999;
static char *mystring = "blah";

MODULE_PARM (myshort, "h");
MODULE_PARM (myint, "i");
MODULE_PARM (mylong, "l");
MODULE_PARM (mystring, "s");


static int __init hello_5_init(void)
{
printk(KERN_ALERT "Hello, world 5/n=============/n");
printk(KERN_ALERT "myshort is a short integer: %hd/n", myshort);
printk(KERN_ALERT "myint is an integer: %d/n", myint);
printk(KERN_ALERT "mylong is a long integer: %ld/n", mylong);
printk(KERN_ALERT "mystring is a string: %s/n", mystring);
return 0;
}


static void __exit hello_5_exit(void)
{
printk(KERN_ALERT "Goodbye, world 5/n");
}


module_init(hello_5_init);
module_exit(hello_5_exit);

Supercalifragilisticexpialidocious

 

2.7. Modules Spanning Multiple Files

Sometimes it makes sense to divide a kernel module between several source files. In this case, you need to:

  1. In all the source files but one, add the line #define __NO_VERSION__. This is important because module.h normally includes the definition of kernel_version, a global variable with the kernel version the module is compiled for. If you need version.h, you need to include it yourself, because module.h won't do it for you with __NO_VERSION__.

  2. Compile all the source files as usual.

  3. Combine all the object files into a single one. Under x86, use ld -m elf_i386 -r -o <module name.o> <1st src file.o> <2nd src file.o>.

Here's an example of such a kernel module.

Example 2-8. start.c

/*  start.c - Illustration of multi filed modules
*/

#include <linux/kernel.h> /* We're doing kernel work */
#include <linux/module.h> /* Specifically, a module */

int init_module(void)
{
printk("Hello, world - this is the kernel speaking/n");
return 0;
}

The next file:

Example 2-9. stop.c

/*  stop.c - Illustration of multi filed modules
*/

#if defined(CONFIG_MODVERSIONS) && ! defined(MODVERSIONS)
#include <linux/modversions.h> /* Will be explained later */
#define MODVERSIONS
#endif
#include <linux/kernel.h> /* We're doing kernel work */
#include <linux/module.h> /* Specifically, a module */
#define __NO_VERSION__ /* It's not THE file of the kernel module */
#include <linux/version.h> /* Not included by module.h because of
__NO_VERSION__ */

void cleanup_module()
{
printk("<1>Short is the life of a kernel module/n");
}

And finally, the makefile:

Example 2-10. Makefile for a multi-filed module

CC=gcc
MODCFLAGS := -O -Wall -DMODULE -D__KERNEL__

hello.o: hello2_start.o hello2_stop.o
ld -m elf_i386 -r -o hello2.o hello2_start.o hello2_stop.o

start.o: hello2_start.c
${CC} ${MODCFLAGS} -c hello2_start.c

stop.o: hello2_stop.c
${CC} ${MODCFLAGS} -c hello2_stop.c
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值