硬件设备:JZ2440开发板
软件环境:Ubuntu15.04
自制编译器
本案例测试内核模块,实现链表的创建、增加节点、遍历和删除操作。
实现步骤:通过vim编写c源程序
- 编写相应的Makefile文件
- 在listdemo,c文件目录下执行make指令,生成ko文件
- 将生成的ko拷贝到开发板内
- 打开开发板,在ko文件目录下执行insmod listdemo.ko
listdemo.c文件
#include <linux/init.h>
#include <linux/module.h>
#include <linux/slab.h>
#include <linux/list.h>
MODULE_LICENSE("Dual BSD/GPL");
#define EMPLOYEE_NUMBEROF 5
static struct list_head employee_list;
struct employee{
char name[20];
int number;
int salary;
struct list_head list;
};
static struct employee *employeep = NULL;
static struct employee *employeep_tmp = NULL;
static struct list_head *pos = NULL;
static struct list_head *pos1 = NULL;
static int __init listdemo_init(void)
{
int i;
printk(
KERN_ALERT "Entry listdemo_init!\n");
INIT_LIST_HEAD(&employee_list);
employeep = kmalloc(sizeof(struct employee) * EMPLOYEE_NUMBEROF,GFP_KERNEL);
if(NULL==employeep){
printk(KERN_ALERT "can't allocate memory for employee array from kernel!\n");
return -ENOMEM;
}
printk(KERN_ALERT "Success to allocate memory for employee array from kernel!\n");
memset(employeep,0,sizeof(struct employee) * EMPLOYEE_NUMBEROF);
for(i=0;i<EMPLOYEE_NUMBEROF;i++){
sprintf(employeep[i].name,"Employee%d",i+1);
employeep[i].number = 1001 + i;
employeep[i].salary = 50000 + 5000 * i;
list_add(&(employeep[i].list),&employee_list);
}
list_for_each(pos,&employee_list){
employeep_tmp = list_entry(pos,struct employee,list);
printk(KERN_ALERT "Employee Name: %s\tNumber:%d\tSalary:%d!\n",employeep_tmp->name,employeep_tmp->number,employeep_tmp->salary);
}
return 0;
}
static void __exit listdemo_exit(void)
{
printk(KERN_ALERT "Entry listdem_exit!\n");
#if 0
for(i=0;i<EMPLOYEE_NUMBEROF;i++){
list_del(&(employeep[i].list));
}
#endif
list_for_each_safe(pos,pos1,&employee_list){
employeep_tmp = list_entry(pos,struct employee,list);
list_del(&employeep_tmp->list);
}
printk(KERN_ALERT "Exit listdemo_exit!\n");
kfree(employeep);
}
module_init(listdemo_init);
module_exit(listdemo_exit);
MODULE_AUTHOR("shenchao");
MODULE_DESCRIPTION("Demo kernel list_head");
MODULE_VERSION("0.0.1");
MODULE_ALIAS("ListSemo");
Makefile文件
KERN_DIR = /work/system/linux-3.14.11
all:
make -C $(KERN_DIR) M=`pwd` modules
clean:
make -C $(KERN_DIR) M=`pwd` modules clean
rm -rf modules.order
obj-m += listdemo.o
最终实现insmod listdemo.ko指令后输出:
/work # insmod listdemo.ko Entry listdemo_init! Success to allocate memory for employee array from kernel! Employee Name: Employee5 Number:1005 Salary:70000! Employee Name: Employee4 Number:1004 Salary:65000! Employee Name: Employee3 Number:1003 Salary:60000! Employee Name: Employee2 Number:1002 Salary:55000! Employee Name: Employee1 Number:1001 Salary:50000!
执行rmmod listdemo指令后输出:
/work # rmmod listdemo Entry listdem_exit! Exit listdemo_exit!
内核list_head链表节点使用