亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频

? 歡迎來到蟲蟲下載站! | ?? 資源下載 ?? 資源專輯 ?? 關(guān)于我們
? 蟲蟲下載站

?? rtl8139 驅(qū)動程序解析.txt

?? 詳細(xì)介紹以太網(wǎng)芯片RTL8139的驅(qū)動程序源代碼的結(jié)構(gòu)。
?? TXT
字號:
RTL8139 驅(qū)動程序解析

前言 
RTL8139 可能是目前最受歡迎的網(wǎng)絡(luò)卡,它的價(jià)格便宜,功能上也還能接受。雖然在效能上有時(shí)會略不及Intel 的 eepro100,但因?yàn)閮r(jià)格實(shí)在太便宜了,所以芯片上的一點(diǎn)小問題通常也接忽略不計(jì)。

廢話少話,馬上來說明 8139too 這個(gè)驅(qū)動程序。8139 雖然價(jià)格不高,但該有的功能一點(diǎn)也不缺。它內(nèi)建了符合 MII 規(guī)格的 tranceiver,可以自動判斷連接的網(wǎng)絡(luò)是那一種型態(tài)。它也可以使用 DMA 直接使用位于主記憶體的緩區(qū)來存網(wǎng)絡(luò)上接收的封包,同樣的,待傳送的封包也可利用 DMA 傳送到網(wǎng)絡(luò)卡上。所以雖然在 8139 芯片上只有 2K 的接收緩沖區(qū)和 2K 的傳送緩沖區(qū),其效能仍十分不錯。

除了 realtek 本身外,有不少的廠商也使用相同的內(nèi)核生產(chǎn)了和 8139 相容的網(wǎng)絡(luò)芯片,包括了

SMC 1211
MPX 5030
DELTA 8139
ADDTRON 8139
DFE 538
可能還有更多。
驅(qū)動程序初始化 
就像其它的驅(qū)動程序一樣,驅(qū)動程序在使用 insmod 載入時(shí),第一個(gè)初呼叫的函數(shù)是 init_module,在使用 rmmod 移除時(shí),cleanuo_module 會被呼叫。在 init_module 中,我們注冊了一個(gè) PCI 驅(qū)動程序
static struct pci_driver rtl8139_pci_driver = {
name: MODNAME,
id_table: rtl8139_pci_tbl,
probe: rtl8139_init_one,
remove: rtl8139_remove_one,
suspend: rtl8139_suspend,
resume: rtl8139_resume,
};


static int __init rtl8139_init_module (void)
{
return pci_module_init (&rtl8139_pci_driver);
} 

這個(gè)結(jié)構(gòu)和上次介紹的 sis900 其實(shí)差別不大。rtl8139_init_one 用來初始化一個(gè) 8139 芯片。PCI 驅(qū)動程序最大的好處是 PCI BUS 提供了組態(tài)空間 (configuration space) 來存放驅(qū)動程序所需的 IO 位址及中斷號碼等資料,我們不必再像 ISA 驅(qū)動程序一樣需要指定這些資源。

rtl8139_init_one 會呼叫 rtl8139_init_board 來初始化芯片,基本上 8139 這個(gè)芯片算是一個(gè)很容易使用的芯片,基本的 PCI 初始化后就可以直接使用了。所以 rtl8139_init_one 和 rtl8139_init_board 其實(shí)多半是在做一些錯誤檢查的動作,并由 PCI 表格中所得稍后會用的到的資源。

我從 rtl8139_init_board 中取出一些比較重要的片斷加以說明,其它的部份請自行參考源代碼。
......
// 由 PCI 子系統(tǒng)中讀出所需的資源
mmio_start = pci_resource_start (pdev, 1);
mmio_end = pci_resource_end (pdev, 1);
mmio_flags = pci_resource_flags (pdev, 1);
mmio_len = pci_resource_len (pdev, 1);
......
......
// 將這些資源保留下來
rc = pci_request_regions (pdev, "8139too");
pci_set_master (pdev);
......
// 將 IO 位址對映到記憶體
ioaddr = ioremap (mmio_start, mmio_len);
dev->base_addr = (long) ioaddr;
tp->mmio_addr = ioaddr;
......
// 重設(shè)芯片
RTL_W8 (ChipCmd, (RTL_R8 (ChipCmd) & ChipCmdClear) | CmdReset);

/* Check that the chip has finished the reset. */
for (i = 1000; i > 0; i--) {
barrier();
udelay (10);
if ((RTL_R8 (ChipCmd) & CmdReset) == 0)
break;
}
// 判斷芯片確的版本
...... 

在 rtl8139_init_one 中最重要的是下面這一段 
dev->open = rtl8139_open;
dev->hard_start_xmit = rtl8139_start_xmit;
dev->stop = rtl8139_close;
dev->get_stats = rtl8139_get_stats;
dev->set_multicast_list = rtl8139_set_rx_mode;
dev->do_ioctl = mii_ioctl;
dev->tx_timeout = rtl8139_tx_timeout;
dev->watchdog_timeo = TX_TIMEOUT;

dev->irq = pdev->irq; 

基本上和上次介紹的函數(shù)基本上相同,在此不再重復(fù)。上面比較特別的可能只有 ioremap 這個(gè)函數(shù),它的用途是將 mmio_start 開始 mmio_len 長度的 IO 映射到記憶體中,之后我們就可以直接使用函數(shù)的傳回值來做 IO 的動作了。

一般而言,mmio_start 的值是一個(gè)位于 CPU 定址空間中的實(shí)體位址,在一般的架構(gòu)下,硬件的設(shè)計(jì)者會保留一塊記憶體位置給記憶體映射裝置 (memory-mapped device) 使用。這些裝置允許 CPU 用記憶體調(diào)用的方式取用其上的暫存器,在有些不支援 IO 調(diào)用的架構(gòu)中,這些唯一取得裝置暫存器的方法。

舉個(gè)例說,如果你要調(diào)用第 100 號暫存器,你可以使用
unsigned int *ap = (unsigned int *) mmio_start + 0x100;
printf("register 0x100 = %x\n", *ap); 

接下來我們一一解釋這些函數(shù)。



開始裝置-- rtl8139_open 
這個(gè)函數(shù)會在你使用 ifconfig 時(shí)初呼叫,在這個(gè)函數(shù)中,你必須做下列的事

注冊中斷函數(shù) rtl8139_interrupt
分配并初始化 8139 所需的接收與傳送緩沖區(qū)。
產(chǎn)生一個(gè) kernel thread 負(fù)責(zé)查看網(wǎng)絡(luò)連線的狀態(tài)
比較特別的是第三個(gè)動作,


rtl8139_start_xmit 
這個(gè)函數(shù)會在傳送一個(gè)封包時(shí)初呼叫, 
static int rtl8139_start_xmit (struct sk_buff *skb, struct net_device *dev)
{
entry = tp->cur_tx % NUM_TX_DESC;


8139 支援四個(gè)傳送緩沖區(qū),你必須挑出下一個(gè)要用的緩沖區(qū)。接下來,你必須把緩沖區(qū)記憶體的實(shí)體表址 (physical address) 設(shè)定到 8139 的暫存器中。
tp->tx_info[entry].skb = skb;
if ((long) skb->data & 3) { /* Must use alignment buffer. */
/* tp->tx_info[entry].mapping = 0; */
memcpy (tp->tx_buf[entry], skb->data, skb->len);
RTL_W32 (TxAddr0 + (entry * 4),
tp->tx_bufs_dma + (tp->tx_buf[entry] - tp->tx_bufs));
} else {
tp->tx_info[entry].mapping =
pci_map_single (tp->pci_dev, skb->data, skb->len,
PCI_DMA_TODEVICE);
RTL_W32 (TxAddr0 + (entry * 4), tp->tx_info[entry].mapping);
} 

上面的程序碼小心的處理的 alignment 的問題, 8139 要求緩沖區(qū)的表址必須對齊 32 位元。也就是說位址必須能被 4 除盡。如果不行的話,我們必須另外安排一個(gè)表址對齊 32 位元的緩沖區(qū),把資料拷貝到那里去,然后將這個(gè)新緩沖區(qū)的實(shí)體表址存放到暫存器中去。


RTL_W32 (TxStatus0 + (entry * sizeof (u32)),
tp->tx_flag | (skb->len >= ETH_ZLEN ? skb->len : ETH_ZLEN)); 

這一段程序用來設(shè)定封包的長度,一個(gè)正確的 ethernet 封包必須至少有 64 位元組長。不幸的,8139 不管這件事,你設(shè)定多長它就送多少。上面這一行程序就在確定封包的長度至少有 ETH_ZLEN。


dev->trans_start = jiffies;
spin_lock_irq (&tp->lock);

tp->cur_tx++;
if ((tp->cur_tx - NUM_TX_DESC) == tp->dirty_tx)
netif_stop_queue (dev);

spin_unlock_irq (&tp->lock);
return 0;
} 

這以前解釋過到,當(dāng)緩沖區(qū)用完時(shí)必須通知上層不要再送封包下來了。



rtl8139_set_rx_mode 
這個(gè)函數(shù)用來設(shè)定接收的模式,8139 提供了 64 組 MAC 位址 filter。只有符合這些 filter 的位址芯片才會用中斷通知 CPU 前來處理,一般狀態(tài)下,我們只接收和 8139 本身 MAC 相符的封包。只有在像 tcpdump 之類的程序中才會想要接收其它的封包。

rtl8139_interrupt 
在中斷函數(shù)中,我們必須將狀態(tài)碼讀入,然后根據(jù)狀態(tài)碼的指示做不同的事。我們要處理的狀況有

發(fā)生錯誤,可能是接收緩沖區(qū)滿了,傳送發(fā)生錯誤,bus 發(fā)生錯誤,接收發(fā)生錯誤。根據(jù)不同的狀況,必須做不同的處理。如果傳送錯誤,則再送一次。如果接收錯誤,那可能只好等待上層協(xié)定發(fā)現(xiàn)并重送封包。如果是 PVCI BUS 錯誤,則可能要重置 BUS。
接收到封包,呼叫 rtl8139_rx_interrupt
傳送完一個(gè)封包,呼叫 rtl8139_tx_interrupt
當(dāng)接收到一個(gè)封包時(shí),我們必須通知上層協(xié)定前檢處理
skb = dev_alloc_skb (pkt_size + 2);
if (skb) {
skb->dev = dev;
skb_reserve (skb, 2); /* 16 byte align the IP fields. */

eth_copy_and_sum (skb, &rx_ring[ring_offset + 4], pkt_size, 0);
skb_put (skb, pkt_size);

skb->protocol = eth_type_trans (skb, dev);
netif_rx (skb);
dev->last_rx = jiffies;
tp->stats.rx_bytes += pkt_size;
tp->stats.rx_packets++;
} else { 

這段程序是非常典型的接收封包程序,先使用 dev_alloc_skb 分配一段足夠大小的緩沖區(qū)。skb_put會調(diào)整緩沖區(qū)的大小,關(guān)鑒在使用 netif_rx 通知上層協(xié)定有新的封包傳入。在稍后會由 BH_NET 這個(gè) bottom half 處理這個(gè)封包。
當(dāng)一個(gè)封包傳送完成后,我們必須將緩沖區(qū)釋放。這件工作在 rtl8139_tx_interrupt 中被完成,此時(shí)我們必須呼叫上層協(xié)定表示可以傳送新的封包了。這件事由下列在 rtl8139_tx_interrupt 最后面的程序完成
if (tp->dirty_tx != dirty_tx) {
tp->dirty_tx = dirty_tx;
if (netif_queue_stopped (dev))
netif_wake_queue (dev);
} 

我們小心的避免呼叫太多次 netif_wake_queue,只有在裝置己經(jīng)因?yàn)榫彌_區(qū)滿了且有新的封包要傳送時(shí)才去呼叫 netif_wake_queue。

?? 快捷鍵說明

復(fù)制代碼 Ctrl + C
搜索代碼 Ctrl + F
全屏模式 F11
切換主題 Ctrl + Shift + D
顯示快捷鍵 ?
增大字號 Ctrl + =
減小字號 Ctrl + -
亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频
国产麻豆一精品一av一免费| 高清国产午夜精品久久久久久| 国产精品视频观看| 日本一区二区免费在线| 欧美精品一区视频| 国产情人综合久久777777| 26uuu国产电影一区二区| 久久久久久久综合日本| 99精品久久99久久久久| 韩日欧美一区二区三区| 成人中文字幕电影| 91美女福利视频| 日韩限制级电影在线观看| 久久免费偷拍视频| 亚洲一区av在线| 久久成人羞羞网站| 色婷婷av一区二区三区软件 | 96av麻豆蜜桃一区二区| 91蜜桃网址入口| 欧美成人video| 亚洲欧洲日韩综合一区二区| 亚洲福利一二三区| 久久国产精品一区二区| 国产成a人无v码亚洲福利| 在线观看日韩国产| 欧美国产一区二区在线观看| 日韩福利电影在线观看| 成人污视频在线观看| 日韩欧美一二区| 亚洲无线码一区二区三区| 懂色av一区二区在线播放| 日韩一区国产二区欧美三区| 18欧美乱大交hd1984| 日韩av中文字幕一区二区三区| 99精品黄色片免费大全| 国产日韩欧美在线一区| 免费精品视频在线| 欧美精品亚洲一区二区在线播放| 国产精品进线69影院| 亚洲高清在线视频| 丁香婷婷综合网| 国产日韩欧美精品在线| 国产另类ts人妖一区二区| 欧美一级视频精品观看| 狂野欧美性猛交blacked| 日韩一区二区中文字幕| 国产资源在线一区| 国产精品三级视频| 国产69精品久久99不卡| 国产精品久久夜| 91丨porny丨户外露出| 亚洲美女屁股眼交3| 欧美色综合网站| 久久激情综合网| 国产精品视频观看| 欧美在线免费播放| 视频一区二区欧美| 国产欧美日韩精品a在线观看| 国产高清精品网站| 亚洲精品国产高清久久伦理二区| 欧美亚州韩日在线看免费版国语版| 亚洲综合色视频| 日韩欧美国产系列| 色欧美88888久久久久久影院| 天堂成人免费av电影一区| 欧美成人欧美edvon| 成人激情动漫在线观看| 五月婷婷另类国产| 亚洲欧洲另类国产综合| 日韩视频一区二区在线观看| 国产成人在线电影| 首页国产欧美久久| 亚洲视频精选在线| 色av综合在线| 麻豆成人av在线| 日本欧美大码aⅴ在线播放| 国产精品久久三区| 国产亚洲欧美色| 国产日产欧美一区二区视频| 欧美日本一区二区在线观看| 91在线观看污| 99re热视频精品| 91久久精品一区二区三| 成人99免费视频| 99精品国产一区二区三区不卡| 国产麻豆精品95视频| 久久精品免费观看| 久久精品国产久精国产爱| 蜜臀av一区二区| 狠狠狠色丁香婷婷综合激情| 精品一区二区日韩| 国产综合久久久久影院| 国产精品99久久久久久似苏梦涵| 经典三级在线一区| 成人激情视频网站| 欧美性一级生活| 精品久久久久一区| 日本一区二区高清| 一级做a爱片久久| 蜜桃久久精品一区二区| 国产精品99久久久| 91国产免费看| 精品国产乱码久久| 亚洲视频免费看| 成人激情动漫在线观看| 日本福利一区二区| 欧美α欧美αv大片| 日韩久久一区二区| 老司机精品视频导航| 日本道免费精品一区二区三区| 日本不卡的三区四区五区| 日本欧美韩国一区三区| 播五月开心婷婷综合| 欧美v国产在线一区二区三区| 欧美激情一区二区三区在线| 蜜桃免费网站一区二区三区| 99国产精品久久久久| 精品福利视频一区二区三区| 日韩一区在线播放| 美国毛片一区二区三区| 欧美午夜电影网| 亚洲精品少妇30p| 成人精品电影在线观看| 精品国产不卡一区二区三区| 亚洲国产精品一区二区尤物区| 国产精品18久久久久久vr| 日韩精品专区在线影院观看| 亚洲第四色夜色| 日韩一区二区不卡| 欧美aaa在线| 精品剧情在线观看| 国产精品资源站在线| 欧美一级片在线| 蜜臀精品一区二区三区在线观看| 欧美午夜精品一区二区三区| 亚洲久草在线视频| 欧美综合在线视频| 图片区小说区区亚洲影院| 欧美视频在线观看一区| 日本最新不卡在线| 日韩你懂的在线播放| 国产一区二区不卡老阿姨| 久久免费午夜影院| 99久久精品免费看国产免费软件| 中文字幕免费观看一区| 91视频国产观看| 麻豆国产欧美一区二区三区| 久久久久久久久久久久电影| 91原创在线视频| zzijzzij亚洲日本少妇熟睡| 久久人人爽爽爽人久久久| 久久er99热精品一区二区| 久久久久久综合| 欧美一区二区性放荡片| 国产最新精品免费| 中文字幕一区二区视频| 欧美一级在线观看| 91黄色小视频| fc2成人免费人成在线观看播放 | 亚洲国产成人高清精品| 久久精品夜色噜噜亚洲aⅴ| 欧美主播一区二区三区| 国产成人av一区| 麻豆免费看一区二区三区| 一区二区在线电影| 欧美国产日本视频| 久久久综合九色合综国产精品| 欧美私人免费视频| 91国在线观看| 精品视频色一区| 欧美日韩免费电影| 欧美色倩网站大全免费| 97超碰欧美中文字幕| 国产91丝袜在线18| 成人av网站在线观看| 偷拍日韩校园综合在线| 亚洲综合999| 亚洲香肠在线观看| 首页欧美精品中文字幕| 日韩高清在线一区| 日韩av高清在线观看| 免费久久精品视频| 国产美女视频一区| 99久久婷婷国产综合精品电影| 国产成人av电影在线观看| 国产一二精品视频| www.成人在线| 91免费视频观看| 色94色欧美sute亚洲线路一ni| 色婷婷综合久久| 日韩欧美国产一区二区在线播放| 精品日韩99亚洲| 中文字幕一区二区三区四区| 视频一区二区不卡| 久久影院视频免费| 夜夜爽夜夜爽精品视频| 日本怡春院一区二区| fc2成人免费人成在线观看播放| 色哟哟一区二区| 精品国精品自拍自在线|