zoukankan      html  css  js  c++  java
  • 实践2.2 内核模块编译

    实践2.2 内核模块编译

    1.模块代码的编写

    模块构造函数:

    module_init()
    

    即执行insmod或modprobe指令加载内核模块时会调用的初始化函数。

    模块析构函数:

    module_exit()
    

    即执行rmmod指令卸载模块时调用的函数。

    模块许可声明:

    MODULE_LICENSE()
    

    告诉内核该程序使用的许可证,不然在加载时它会提示该模块污染内核。一般会写GPL。

    头文件:

    <linux/module.h>,必须包含此文件;
    <linux/kernel.h>,包含常用的内核函数;
    <linux/init.h>,包含宏_init和_exit,允许释放内核占用的内存。
    

    编写代码:

    //test_sche.c
    #include <linux/init.h>
    #include <linux/module.h>
    
    MODULE_LICENSE("Dual BSD/GPL");
    static char *name="YJX";
    
    static int __init name_init(void)
    {
        printk("***Hello World!***
    ");
        printk("***Hello %s!***
    ",name);
        return 0;
    }
    
    static void __exit name_exit(void)
    {
        printk(KERN_INFO"Name module exit
    ");
    }
    
    module_init(name_init);
    module_exit(name_exit);
    
    module_param(name,charp,S_IRUGO);
    
    MODULE_AUTHOR("YJX");
    MODULE_VERSION("v1.0);
    MODULE_DESCRIPTION(“A simple module for testing pirntk and module params:");
    

    编译模块-Makefile

    //Makefile
    obj-m := test_sche.o
    PWD := $(shell pwd)
    KDIR := /lib/modules/3.2.0-29-generic-pae/build
    
    all:
        make -C $(KDIR) M=$(PWD) modules
    clean:
        make -C $(KDIR) M=$(PWD) clean
    

    第一行:自己写的.c的文件名+”.o”。
    第三行的KDIR后面要写自己的内核版本对应的内核源码包地址.

    如何查看?
    uname -r
    enter description here

    解释一下make命令:
    make -C $(KDIR) 指明跳转到内核源码目录下读取那里的Makefile
    M=$(PWD) 表明返回到当前目录继续执行当前的Makefile。

    make结果:
    enter description here

    make执行之后会出现很多文件:
    enter description here

    加载模块

    sudo insmod test_sche.ko
    

    测试模块

    dmesg
    

    卸载模块

    sudo rmmod test_sche.ko
    

    测试结果:

    1.加载后:
    enter description here
    2.卸载后:
    enter description here


    读取进程链表:

    代码:
    #include <linux/kernel.h>
    #include <linux/module.h>
    #include <linux/init.h>
    #include <linux/sched.h>
    
    static struct task_struct *pcurrent;
    
    static int __init print_init(void)
    {
        pirntk(KERN_INFO"print current task info
    ");
        printk("pid	tgid	prio	state
    ");
        for_each_process(pcurrent){
            printk("%d	",purrent->pid);
            printk("%d	",purrent->tgid);
            printk("%d	",purrent->prio);
            printk("%ld
    ",purrent->state);
            }
        return 0;
    }
    
    static void __exit print_exit(void)
    {
        printk(KERN_INFO "Finished
    ");
    }
    
    module_init(print_init);
    module_exit(print_exit);
    

    编译运行加载后,测试结果为:
    enter description here

  • 相关阅读:
    通过 WakaTime 统计你写代码的时长
    CCF 202012-3 带配额的文件系统
    1
    prometheus 获取cpu利用率
    springboot使用@data注解,减少不必要代码-lombok插件
    django官方教程部署simpleui时候发现加载不到静态文件解决办法
    echarts关系图研究01
    SpringBoot代码方式禁用Druid Monitor
    virtualbox给已有磁盘扩展容量
    centos7 ssh免密登录配置
  • 原文地址:https://www.cnblogs.com/20135202yjx/p/5534064.html
Copyright © 2011-2022 走看看