驅(qū)動入門知識_第1頁
驅(qū)動入門知識_第2頁
驅(qū)動入門知識_第3頁
驅(qū)動入門知識_第4頁
驅(qū)動入門知識_第5頁
已閱讀5頁,還剩5頁未讀 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡介

驅(qū)動入門知識設(shè)備驅(qū)動簡介:內(nèi)核功能劃分:1、 進(jìn)程管理進(jìn)程管理功能負(fù)責(zé)創(chuàng)建銷毀進(jìn)程,并處理他們與外界之間的連接(輸入輸出)。不同進(jìn)程之間的通信是整個(gè)系統(tǒng)的基本功能。2、 內(nèi)存管理內(nèi)核在有限的可用資源之上為每個(gè)進(jìn)程都創(chuàng)建了一個(gè)虛擬的得知空間,內(nèi)核的不同部分在和內(nèi)存管理子系統(tǒng)法交互的時(shí)候使用一組函數(shù)調(diào)用,包括簡單的malloc/free函數(shù)3、 文件系統(tǒng)Unix中的每個(gè)對象幾乎都可以當(dāng)作文件來看待。內(nèi)核在沒有結(jié)構(gòu)的硬件上構(gòu)造結(jié)構(gòu)化的文件系統(tǒng)4、 設(shè)備控制幾乎每一個(gè)系統(tǒng)操作最終都會映射到物理設(shè)備上。除了處理器、內(nèi)存以及其他很有限的幾個(gè)對象外,所有設(shè)備操作都由相關(guān)的代碼來完成,這段代碼就叫做驅(qū)動程序內(nèi)核必須為系統(tǒng)中的每件外設(shè)嵌入相應(yīng)的驅(qū)動程序5、 網(wǎng)絡(luò)功能大部分網(wǎng)絡(luò)操作和具體的進(jìn)程無關(guān),數(shù)據(jù)包的傳入是異步事件。在某個(gè)進(jìn)程處理這些數(shù)據(jù)包之前,必須收集標(biāo)識和分發(fā)這些數(shù)據(jù)包系統(tǒng)負(fù)責(zé)在應(yīng)用程序和網(wǎng)絡(luò)接口之間傳遞數(shù)據(jù)包。設(shè)備和模塊的分類:字符設(shè)備:塊設(shè)備:網(wǎng)絡(luò)接口:模塊:首先是模塊,內(nèi)核的驅(qū)動分為兩種形式,一種是直接編譯進(jìn)內(nèi)核,另一種是寫成模塊,這樣在需要的時(shí)候可以裝載,不需要的時(shí)候就可以接卸,所以要了解驅(qū)動首先從模塊入手。在我們學(xué)習(xí)編程的時(shí)候,第一個(gè)寫的程序基本上都是hello_word。所以,我們現(xiàn)在也寫一個(gè)hello_word模塊。//Hello_word.c#include<linux/init.h>#include<linux/kernel.h>#include<linux/module.h>staticinthello_init(void){printk(KERN_ALERT"Moduleinit:Helloword!\n");return0;}staticvoidhello_exit(void){printk(KERN_ALERT"Moduleexit:bye-bye\n");return;}module_init(hello_init);module_exit(hello_exit);對應(yīng)的用來編譯hello_word的makefile文件//Makefileobj-m:=hw_module.ohw_modulemodule-objs:=moduleKDIR:=/lib/modules/3.5.0-57-generic/buildMAKE:=makedefault:$(MAKE)-C$(KDIR)SUBDIRS=$(PWD)modulesclean:$(MAKE)-C$(KDIR)SUBDIRS=$(PWD)clean這樣一個(gè)簡單的模塊就完成了,這里的程序?qū)懛?、調(diào)用與用戶空間的程序有很多不同。比如,模塊函數(shù)沒有main函數(shù),在裝載模塊的時(shí)候會調(diào)用module_init(hello_init);注冊函數(shù),這里注冊的是hello_init。在模塊卸載時(shí)候同樣會調(diào)用module_exit(hello_exit);注冊函數(shù),這里注冊的是hello_exit。module_init注冊函數(shù)主要是初始化,分配內(nèi)存,注冊設(shè)備等等,而module_exit中注冊函數(shù)恰恰相反,主要是釋放內(nèi)存,注銷設(shè)備等等。還有在內(nèi)河中用printk打印信息,不過printk不支持浮點(diǎn)型數(shù)據(jù),printk中可以加入7種信息級別#defineKERN_EMERG"<0>"/*systemisunusable*/#defineKERN_ALERT"<1>"/*actionmustbetakenimmediately*/#defineKERN_CRIT"<2>"/*criticalconditions*/#defineKERN_ERR"<3>"/*errorconditions*/#defineKERN_WARNING"<4>"/*warningconditions*/#defineKERN_NOTICE"<5>"/*normalbutsignificant*/#defineKERN_INFO"<6>"/*informational*/#defineKERN_DEBUG"<7>"/*debug-levelmessages*/對應(yīng)與不同用戶的錯(cuò)誤等級選擇不同的option,并做不同的處理,小于一定等級的信息答應(yīng)到終端可以使用dmesg來查看全部的打印信息。編譯內(nèi)核的頭文件是在/lib/modules/$(shelluname-r)/build/include/目錄下的,而不是用戶目錄下/usr/include/,所以編譯后不會產(chǎn)生可執(zhí)行文件,而是一個(gè).ko的文件。下來就是加載/卸載模塊。加載模塊命令:insmodxxx.ko卸載模塊命令:rmmodxxx.ko查看模塊命令:lsmod簡單的字符設(shè)備驅(qū)動:1、 主次設(shè)備號2、 字符設(shè)備中重要的數(shù)據(jù)結(jié)構(gòu)文件操作File結(jié)構(gòu)3.Inode結(jié)構(gòu)4.Cdev結(jié)構(gòu)3、 字符設(shè)備的注冊Platform總線架構(gòu):從Linux2.6內(nèi)核起,引入一套新的驅(qū)動管理注冊機(jī)制:platform_device和platform_driver。Linux中大部分的設(shè)備驅(qū)動都可以使用這套機(jī)制,設(shè)備用platform_device表示,設(shè)備用platform_driver進(jìn)行注冊。Linuxplatformdriver機(jī)制和傳統(tǒng)的device機(jī)制(通過driver_register函數(shù)進(jìn)行注冊)相比有一個(gè)十分明顯的優(yōu)勢,那就是platform機(jī)制將設(shè)備本身的資源注冊進(jìn)內(nèi)核,由內(nèi)核統(tǒng)一管理,在驅(qū)動程序中使用這些資源時(shí),通過platformdevice提供的標(biāo)準(zhǔn)接口進(jìn)行申請并使用。Platform是一個(gè)虛擬的地址總線,相比PCI、USB,他主要用于描述SOC上的資源。Platform所描述的資源有一個(gè)共同點(diǎn):在CPU的總線上直接取址。Platform總線下驅(qū)動開發(fā)步驟:1、 設(shè)備設(shè)備注冊中,需要實(shí)現(xiàn)的機(jī)構(gòu)體是:platform_device初始化resource結(jié)構(gòu)變量初始化platform_device結(jié)構(gòu)變量向系統(tǒng)注冊設(shè)備:platform_device_registero以上三步必須在設(shè)備驅(qū)動加載前完成。2、 驅(qū)動驅(qū)動注冊中,需要實(shí)現(xiàn)的結(jié)構(gòu)體是:platform_driver。在驅(qū)動程序的初始化函數(shù)中,調(diào)用了platform_driver_register()注冊platform_driver。這里需要注意的是platform_driver和platform_device中的name變量的值必須是相同的。因?yàn)?,在platform_driver_register()注冊時(shí)會將當(dāng)前注冊的platform_driver中的name變量的值和已注冊的所有platform_device中的name變量的值進(jìn)行比較,只有找到具有相同名稱的platform_device才能注冊成功。當(dāng)注冊成功時(shí),會調(diào)用platform_driver結(jié)構(gòu)元素probe函數(shù)指針進(jìn)入CF卡驅(qū)動的入口函數(shù)是phoenix_ide_init()函數(shù),進(jìn)去之后發(fā)現(xiàn)里面就一句話voidphoenix_ide_init(void){platform_driver_register(&nlm_common_ide_driver);}再進(jìn)入platform_driver_register()函數(shù)看看intplatform_driver_register(structplatform_driver*drv){drv->driver.bus=&platform_bus_type;if(drv->probe)drv->be=platform_drv_probe;if(drv->remove)drv->driver.remove=platform_drv_remove;if(drv->shutdown)drv->driver.shutdown=platform_drv_shutdown;if(drv->suspend)drv->driver.suspend=platform_drv_suspend;if(drv->resume)drv->driver.resume=platform_drv_resume;if(drv->pm)drv->driver.pm=&drv->pm->base;returndriver_register(&drv->driver);}在這個(gè)函數(shù)中對drv結(jié)構(gòu)體進(jìn)行了賦值,最后調(diào)用dirver_register注冊dirver成員,在賦值的過程中調(diào)用了probe函數(shù)指針,下面看看probe函數(shù)staticstructplatform_drivernlm_common_ide_driver={.driver={.name = "xlp-ide-commpact",.owner = THIS_MODULE,.of_match_table=nlm_common_ide_dt_ids,},.probe =nlm_drv_ide_probe,.remove =nlm_common_ide_remove,};staticint__devinitnlm_drv_ide_probe(structplatform_device*dev){unsignedinti=0;intret=0;structide_host*host;unsignedlongaddr;structide_hwhw,*hws[]={&hw};

ide_hwif_t*nlm_common_ide_hwif;u32l2_irq;printk("InitializingxlrPCMCIAIDE...\n");memset(&hw,0,sizeof(hw));addr=(unsignedlong)get_localbus_add(CS_CF);printk(KERN_ALERT"DEBUG__ADDR=%x...\n”,addr);if(addr==INVALID_U32){printk("localbushavenotassignmemoryforcf\r\n");return-1;}hw.io_ports.data_addrhw.io_ports.error_addrhw.io_ports.nsect_addrhw.io_ports.lbal_addrhw.io_ports.lbam_addrhw.io_ports.lbah_addrhw.io_ports.device_addrhw.io_ports.status_addrhw.io_ports.ctl_addrhw.io_ports.irq_addrhw.io_ports.data_addrhw.io_ports.error_addrhw.io_ports.nsect_addrhw.io_ports.lbal_addrhw.io_ports.lbam_addrhw.io_ports.lbah_addrhw.io_ports.device_addrhw.io_ports.status_addrhw.io_ports.ctl_addrhw.io_ports.irq_addr=NETLOGIC_IDE_REG(addr,0x82);=NETLOGIC_IDE_REG(addr,0x84);=NETLOGIC_IDE_REG(addr,0x86);=NETLOGIC_IDE_REG(addr,0x88);=NETLOGIC_IDE_REG(addr,0x8a);=NETLOGIC_IDE_REG(addr,0x8c);=NETLOGIC_IDE_REG(addr,0x8e);=NETLOGIC_IDE_REG(addr,0x4c);=NETLOGIC_IDE_REG(addr,0x4e);hw.dev=&dev->dev;〃中斷初始化l2_irq=bsp_get_irq_num(DRV_IRQ_CF0);hw.irq=l2_irq;request_l2_irq_register(l2_int_connect);/*注冊cfreset函數(shù)*/l2_int_connect(hw.irq,cf_default_int_proc,(void*)0);int_enable(hw.irq);ret=ide_host_add(&nlm_common_port_info,hws,1,&host);if(ret)gotoout;platform_set_drvdata(dev,host);nlm_common_ide_hwif=host->ports[0];printk("NetlogicXLRPCMCIAconfiguredasIDEinterface=%d\n",i);u32test=1;u8*pstr=(u8*)&test;if(*pstr==1)printk("DEBUG__Little_endian.....\n"); //Little_endianelseprintk("DEBUG__Big_endian \n");//Big_endianout:returnret;}在這里先看藍(lán)色標(biāo)記的代碼(之前的是一些初始化賦值)ret=ide_host_add(&nlm_common_port_info,hws,1,&host);Ide_host_add函數(shù)在內(nèi)核t_all/tos/drivers/ide/ide_probe.c文件中,源代碼如下:intide_host_add(conststructide_port_info*d,structide_hw**hws,unsignedintn_ports,structide_host**hostp){structide_host*host;intrc;1516host=ide_host_alloc(d,hws,n_ports);if(host==NULL)return-ENOMEM;1520rc=ide_host_register(host,d,hws);if(rc){ide_host_free(host);returnrc;}1526if(hostp)*hostp=host;1529return0;}EXPORT_SYMBOL_GPL(ide_host_add);在該函數(shù)中先是用ide_host_alloc函數(shù)給**hws分配內(nèi)存并初始化,再用函數(shù)ide_host_register注冊到內(nèi)核中。intide_host_register(structide_host*host,conststructide_port_info*d,structide_hw**hws){ide_hwif_t*hwif,*mate=NULL;inti,j=0;

14201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463ide_host_for_each_port(i,hwif,host){if(hwif==NULL){mate=NULL;continue;}ide_init_port_hw(hwif,hws[i]);ide_port_apply_params(hwif);if((i&1)&&mate){hwif->mate=mate;mate->mate=hwif;}mate=(i&1)?NULL:hwif;ide_init_port(hwif,i&1,d);ide_port_cable_detect(hwif);hwif->port_flags|=IDE_PFLAG_PROBING;ide_port_init_devices(hwif);}ide_host_for_each_port(i,hwif,host){if(hwif==NULL)continue;if(ide_probe_port(hwif)==0)hwif->present=1;hwif->port_flags&=~IDE_PFLAG_PROBING;if((hwif->host_flags&IDE_HFLAG_4DRIVES)==0||hwif->mate==NULL||hwif->mate->present==0){if(ide_register_port(hwif)){ide_disable_port(hwif);continue;}}if(hwif->present)ide_port_tune_devices(hwif);

146414651466146714681469147014711472147314741475147614771478147

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

最新文檔

評論

0/150

提交評論