驅(qū)動注冊

1.結(jié)構(gòu)體platform_driver(vim include/linux/platform_device.h)

struct platform_driver {

? ? ? ? int (*probe)(struct platform_device *);

? ? ? ? int (*remove)(struct platform_device *);

? ? ? ? void (*shutdown)(struct platform_device *);

? ? ? ? int (*suspend)(struct platform_device *, pm_message_t state);

? ? ? ? int (*resume)(struct platform_device *);

? ? ? ? struct device_driver driver;

? ? ? ? const struct platform_device_id *id_table;

};

struct device_driver {

? ? ? ? const char? ? ? ? ? ? ? *name;

? ? ? ? struct bus_type? ? ? ? *bus;

? ? ? ? struct module? ? ? ? ? *owner;

? ? ? ? const char? ? ? ? ? ? ? *mod_name;? ? ? /* used for built-in modules */

? ? ? ? bool suppress_bind_attrs;? ? ? /* disables bind/unbind via sysfs */

? ? ? ? const struct of_device_id? ? ? *of_match_table;

? ? ? ? int (*probe) (struct device *dev);

? ? ? ? int (*remove) (struct device *dev);

? ? ? ? void (*shutdown) (struct device *dev);

? ? ? ? int (*suspend) (struct device *dev, pm_message_t state);

? ? ? ? int (*resume) (struct device *dev);

? ? ? ? const struct attribute_group **groups;

? ? ? ? const struct dev_pm_ops *pm;

? ? ? ? struct driver_private *p;

};

? ? ——注冊結(jié)構(gòu)體

? ? ?驅(qū)動常見的幾種狀態(tài),初始化,移除,休眠,復位

? ? ? ?–就像PC一樣,有的驅(qū)動休眠之后無法使用,有的可以使用;有的系統(tǒng)喚醒之后,驅(qū)動需要重新啟動才能正常工作,也有直接就可以使用等等

? ? ?probe函數(shù)

? ? ? ?–platform_match函數(shù)匹配之后,驅(qū)動調(diào)用的初始化函數(shù)

? ? ??remove函數(shù)

? ? ? ? –移除驅(qū)動函數(shù)

? ? ?suspend函數(shù)

? ? ? ?–懸掛(休眠)驅(qū)動函數(shù)

? ? ??resume函數(shù)

? ? ? ?–休眠后恢復驅(qū)動

? ? ?device_driver數(shù)據(jù)結(jié)構(gòu)的兩個參數(shù)

? ? ? ? ? ? ?–name和注冊的設(shè)備name要一致

? ? ? ? ? ? ?–owner一般賦值THIS_MODULE

2.驅(qū)動注冊函數(shù)

? ? ? ? extern int platform_driver_register(struct platform_driver *);

? ? ? ? extern void platform_driver_unregister(struct platform_driver *);

3.驅(qū)動例子(hello_module.c)

? ? ? ? #include <linux/init.h>

? ? ? ? #include <linux/module.h>

? ? ? ?/*驅(qū)動注冊的頭文件,包含驅(qū)動的結(jié)構(gòu)體和注冊和卸載的函數(shù)*/

? ? ? ?#include <linux/platform_device.h>

? ? ? ?#define DRIVER_NAME "hello_ctl"

? ? ? ? MODULE_LICENSE("Dual BSD/GPL");

? ? ? ? MODULE_AUTHOR("WENDONG");

? ? ? ? static int hello_probe(struct platform_device *pdv){

? ? ? ? ? ? ? ? printk(KERN_EMERG "\tprobe initialized\n");?

? ? ? ? ? ? ? ? return 0;

? ? ? ? }

? ? ? ?/*Drive Remove*/

? ? ? ? static int hello_remove(struct platform_device *pdv){

? ? ? ? ? ? ? ??return 0;

? ? ? ? }

? ? ? ?static void hello_shutdown(struct platform_device *pdv){

? ? ? ? ? ? ? ?;

? ? ? ? }

? ? ? /*Driver 睡眠*/

? ? ? static int hello_suspend(struct platform_device *pdv,?pm_message_tstate){

? ? ? ? ? ? ? return 0;

? ? ? ?}


? ? ? ?/*Driver喚醒*/

? ? ? static int hello_resume(struct platform_device *pdv){

? ? ? ? ? ? ? return 0;

? ? ? ? }


? ? ? ? struct platform_driver hello_driver = {

? ? ? ? ? ? ? ? .probe = hello_probe,

? ? ? ? ? ? ? ? .remove = hello_remove,

? ? ? ? ? ? ? ? .shutdown = hello_shutdown,

? ? ? ? ? ? ? ? .suspend = hello_suspend,

? ? ? ? ? ? ? ? .resume = hello_resume,

? ? ? ? ? ? ? ?.driver = {

? ? ? ? ? ? ? ? ? ? ? ?.name = DRIVER_NAME,

? ? ? ? ? ? ? ? ? ? ? ?.owner = THIS_MODULE,

? ? ? ? ? ? ? }

? ? ? };

? ? ? static int hello_init(void)

? ? ? {

? ? ? ? ? ? ? printk(KERN_EMERG "HELLO WORLD enter!\n");

? ? ? ? ? ? ??int DriverState = platform_driver_register(&hello_driver);

? ? ? ? ? ? ??printk(KERN_EMERG "\tDriverState is %d\n",DriverState);

? ? ? ? ? ? ? return 0;

? ? ? }


? ? ? ? static void hello_exit(void)

? ? ? ? {

? ? ? ? ? ? ? ? printk(KERN_EMERG "HELLO WORLD exit!\n");

? ? ? ? ? ? ? ? platform_driver_unregister(&hello_driver);

? ? ? ? }

? ? ? ? ?/*模塊進入*/

? ? ? ? module_init(hello_init);

? ? ? ? ?/*模塊退出 */

? ? ? ? module_exit(hello_exit);

4. Makefile文件

#!/bin/bash

#通知編譯器我們要編譯模塊的哪些源碼

#這里是編譯hello_module.c這個文件編譯成中間文件hello_module.o

obj-m += hello_module.o

#源碼目錄變量,這里用戶需要根據(jù)實際情況選擇路徑

#作者是將Linux的源碼拷貝到目錄/home/topeet/kernal/4.4/下并解壓的

KDIR := /home/topeet/kernal/4.4/iTop4412_Kernel_3.0

#當前目錄變量

PWD ?= $(shell pwd)

#make命名默認尋找第一個目標

#make -C就是指調(diào)用執(zhí)行的路徑

#$(KDIR)Linux源碼目錄,作者這里指的是/home/topeet/kernal/4.4/iTop4412_Kernel_3.0

#$(PWD)當前目錄變量

#modules要執(zhí)行的操作

all:

make -C $(KDIR) M=$(PWD) modules

#make clean執(zhí)行的操作是刪除后綴為o的文件

clean:

rm -rf *.o

5.make,編譯生成驅(qū)動ko文件

6.

? ? insmod hello.ko 注冊模塊

? ? lsmod , cat /proc/modules | grep hello* 查看模塊?

? ? rmmod 移除模塊

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

推薦閱讀更多精彩內(nèi)容

  • USB設(shè)備驅(qū)動程序用來驅(qū)動相應(yīng)的USB設(shè)備,USB設(shè)備驅(qū)動用usb_driver表示,它主要用來將USB設(shè)備掛接到...
    Joe_HUST閱讀 6,341評論 1 5
  • linux設(shè)備模型bus,device,driver作者 codercjg 在 10 十一月 2015, 2:43...
    codercjg閱讀 421評論 0 1
  • linux設(shè)備模型bus,device,driver作者 codercjg 在 10 十一月 2015, 2:43...
    codercjg閱讀 578評論 0 1
  • 雜項設(shè)備可以說是對一部分字符設(shè)備的封裝,還有一部分不好歸類驅(qū)動也歸到雜項設(shè)備。 ?1為什么會引入雜項設(shè)備? ...
    文東之名閱讀 697評論 0 0
  • make menuconfig過程解析作者 codercjg 在 28 九月 2015, 5:27 下午 make...
    codercjg閱讀 992評論 0 1