PCIe裝置驅動demo

2021-08-25 05:54:35 字數 3601 閱讀 6238

pcie(pci express)是intel提出的新一代的匯流排介面,目前普及的pcie 3.0的傳輸速率為8gt/s,下一代pcie 4.0將翻番為16gt/s,因為傳輸速率快廣泛應用於資料中心、雲計算、人工智慧、機器學習、視覺計算、顯示卡、儲存和網路等領域。pcie插槽是可以向下相容的,比如pcie 1x介面可以插4x、8x、16x的插槽上。

實現基本的pcie驅動程式,實現以下模組:初始化裝置、裝置開啟、資料讀寫和控制、中斷處理、裝置釋放、裝置解除安裝。本程式適合pcie驅動開發通用除錯的基本框架,對於具體pcie裝置,需要配置相關暫存器才可以使用!

#include #include #include #include #include #include #include #include #include #include #include #include module_license("dual bsd/gpl");

module_description("pcie device driver");

#define dev_name "hello_pcie"

#define debug

#ifdef debug

#define debug_err(format,args...) \

dowhile(0)

#else

#define debug_print(format,args...)

#endif

//1m

#define dma_buffer_size 1*1024*1024

#define fasync_minor 1

#define fasync_major 244

#define device_number 1

static struct class * hello_class;

static struct device * hello_class_dev;

struct hello_device

my_device;

//barn(n=0,1,2或者0,1,2,3,4,5) 空間的實體地址,長度,虛擬位址

unsigned long bar0_phy;

unsigned long bar0_vir;

unsigned long bar0_length;

unsigned long bar1_phy;

unsigned long bar1_vir;

unsigned long bar1_length;

//進行dma轉換時,dma的源位址和目的位址

dma_addr_t dma_src_phy;

dma_addr_t dma_src_vir;

dma_addr_t dma_dst_phy;

dma_addr_t dma_dst_vir;

//根據裝置的id填寫,這裡假設廠商id和裝置id

#define hello_vendor_id 0x666

#define hello_device_id 0x999

static struct pci_device_id hello_ids = ,

};module_device_table(pci,hello_ids);

static int hello_probe(struct pci_dev *pdev, const struct pci_device_id *id);

static void hello_remove(struct pci_dev *pdev);

static irqreturn_t hello_interrupt(int irq, void * dev);

//往iatu寫資料的函式

void iatu_write_config_dword(struct pci_dev *pdev,int offset,int value)

//假設需要將bar0對映到記憶體

static void iatu_bar0(void)

//往dma配置暫存器中讀寫資料的函式,這是難點一:dma暫存器的定址。

int dma_read_config_dword(struct pci_dev *pdev,int offset)

void dma_write_config_dword(struct pci_dev *pdev,int offset,int value)

void dma_init(void)

else

把資料暫存器的值寫入到dma的控制暫存器組中的 dma write channel 0 imwr data中

//dma_write_config_dword(my_device.pci_dev,dma write channel 0 imwr data,msi_data);

dma channel 0 control register 1 = 0x4000010

//dma_write_config_dword(my_device.pci_dev,dma channel 0 control register 1,0x4000010);

通道0 讀初始化 和上述操作類似,不再敘述。}

static int hello_probe(struct pci_dev *pdev, const struct pci_device_id *id)

pci_set_master(pdev);

my_device.pci_dev=pdev;

if(unlikely(pci_request_regions(pdev,dev_name)))

//獲得bar0的實體地址和虛擬位址

bar0_phy = pci_resource_start(pdev,0);

if(bar0_phy<0)

//假設bar0是作為記憶體,流程是這樣的,但是在本程式中不對bar0進行任何操作。

bar0_length = pci_resource_len(pdev,0);

if(bar0_length!=0)

//申請一塊dma記憶體,作為源位址,在進行dma讀寫的時候會用到。

dma_src_vir=(dma_addr_t)pci_alloc_consistent(pdev,dma_buffer_size,&dma_src_phy);

if(dma_src_vir != 0)

result = request_irq(pdev->irq, hello_interrupt, 0, dev_name, my_device.pci_dev);

if (unlikely(result))

//dma 的讀寫初始化

dma_init();

enable_msi_error:

pci_disable_msi(pdev);

alloc_dma_dst_err:

for(i=0;iirq,my_device.pci_dev);

pci_disable_msi(pdev);

for(i=0;i驅動示例:

驅動詳解:

linux下pcie裝置驅動

pcie裝置驅動與platform裝置驅動的對比學習 1 驅動模組結構 1 pcie裝置註冊 module pci driver x driver 展開之後對應於 module init x driver pci register drive x driver module exit x drive...

linux裝置驅動之PCIE驅動開發

pcie pci express 是intel提出的新一代的匯流排介面,目前普及的pcie 3.0的傳輸速率為8gt s,下一代pcie 4.0將翻番為16gt s,因為傳輸速率快廣泛應用於資料中心 雲計算 人工智慧 機器學習 視覺計算 顯示卡 儲存和網路等領域。pcie插槽是可以向下相容的,比如p...

PCIe總結 裝置資源

上篇文章說到列舉過程中的資源分配,這篇文章具體說下。首先要知道需要分配哪些資源,主要就2個 匯流排 bus 資源和記憶體 memory 資源。匯流排資源 bus資源就是給裝置分配唯一的id,其中bus號為8個bit,所以bus範圍為0 255,device是5個bit,所以範圍是0 31,funct...