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

? 歡迎來到蟲蟲下載站! | ?? 資源下載 ?? 資源專輯 ?? 關于我們
? 蟲蟲下載站

?? snull.c

?? 驅動實例
?? C
?? 第 1 頁 / 共 2 頁
字號:
/* * snull.c --  the Simple Network Utility * * Copyright (C) 2001 Alessandro Rubini and Jonathan Corbet * Copyright (C) 2001 O'Reilly & Associates * * The source code in this file can be freely used, adapted, * and redistributed in source or binary form, so long as an * acknowledgment appears in derived source files.  The citation * should list that the code comes from the book "Linux Device * Drivers" by Alessandro Rubini and Jonathan Corbet, published * by O'Reilly & Associates.   No warranty is attached; * we cannot take responsibility for errors or fitness for use. * * $Id: snull.c,v 1.21 2004/11/05 02:36:03 rubini Exp $ */#include <linux/config.h>#include <linux/module.h>#include <linux/init.h>#include <linux/moduleparam.h>#include <linux/sched.h>#include <linux/kernel.h> /* printk() */#include <linux/slab.h> /* kmalloc() */#include <linux/errno.h>  /* error codes */#include <linux/types.h>  /* size_t */#include <linux/interrupt.h> /* mark_bh */#include <linux/in.h>#include <linux/netdevice.h>   /* struct device, and other headers */#include <linux/etherdevice.h> /* eth_type_trans */#include <linux/ip.h>          /* struct iphdr */#include <linux/tcp.h>         /* struct tcphdr */#include <linux/skbuff.h>#include "snull.h"#include <linux/in6.h>#include <asm/checksum.h>MODULE_AUTHOR("Alessandro Rubini, Jonathan Corbet");MODULE_LICENSE("Dual BSD/GPL");/* * Transmitter lockup simulation, normally disabled. */static int lockup = 0;module_param(lockup, int, 0);static int timeout = SNULL_TIMEOUT;module_param(timeout, int, 0);/* * Do we run in NAPI mode? */static int use_napi = 0;module_param(use_napi, int, 0);/* * A structure representing an in-flight packet. */struct snull_packet {	struct snull_packet *next;	struct net_device *dev;	int	datalen;	u8 data[ETH_DATA_LEN];};int pool_size = 8;module_param(pool_size, int, 0);/* * This structure is private to each device. It is used to pass * packets in and out, so there is place for a packet */struct snull_priv {	struct net_device_stats stats;	int status;	struct snull_packet *ppool;	struct snull_packet *rx_queue;  /* List of incoming packets */	int rx_int_enabled;	int tx_packetlen;	u8 *tx_packetdata;	struct sk_buff *skb;	spinlock_t lock;};static void snull_tx_timeout(struct net_device *dev);static void (*snull_interrupt)(int, void *, struct pt_regs *);/* * Set up a device's packet pool. */void snull_setup_pool(struct net_device *dev){	struct snull_priv *priv = netdev_priv(dev);	int i;	struct snull_packet *pkt;	priv->ppool = NULL;	for (i = 0; i < pool_size; i++) {		pkt = kmalloc (sizeof (struct snull_packet), GFP_KERNEL);		if (pkt == NULL) {			printk (KERN_NOTICE "Ran out of memory allocating packet pool\n");			return;		}		pkt->dev = dev;		pkt->next = priv->ppool;		priv->ppool = pkt;	}}void snull_teardown_pool(struct net_device *dev){	struct snull_priv *priv = netdev_priv(dev);	struct snull_packet *pkt;    	while ((pkt = priv->ppool)) {		priv->ppool = pkt->next;		kfree (pkt);		/* FIXME - in-flight packets ? */	}}    /* * Buffer/pool management. */struct snull_packet *snull_get_tx_buffer(struct net_device *dev){	struct snull_priv *priv = netdev_priv(dev);	unsigned long flags;	struct snull_packet *pkt;    	spin_lock_irqsave(&priv->lock, flags);	pkt = priv->ppool;	priv->ppool = pkt->next;	if (priv->ppool == NULL) {		printk (KERN_INFO "Pool empty\n");		netif_stop_queue(dev);	}	spin_unlock_irqrestore(&priv->lock, flags);	return pkt;}void snull_release_buffer(struct snull_packet *pkt){	unsigned long flags;	struct snull_priv *priv = netdev_priv(pkt->dev);		spin_lock_irqsave(&priv->lock, flags);	pkt->next = priv->ppool;	priv->ppool = pkt;	spin_unlock_irqrestore(&priv->lock, flags);	if (netif_queue_stopped(pkt->dev) && pkt->next == NULL)		netif_wake_queue(pkt->dev);}void snull_enqueue_buf(struct net_device *dev, struct snull_packet *pkt){	unsigned long flags;	struct snull_priv *priv = netdev_priv(dev);	spin_lock_irqsave(&priv->lock, flags);	pkt->next = priv->rx_queue;  /* FIXME - misorders packets */	priv->rx_queue = pkt;	spin_unlock_irqrestore(&priv->lock, flags);}struct snull_packet *snull_dequeue_buf(struct net_device *dev){	struct snull_priv *priv = netdev_priv(dev);	struct snull_packet *pkt;	unsigned long flags;	spin_lock_irqsave(&priv->lock, flags);	pkt = priv->rx_queue;	if (pkt != NULL)		priv->rx_queue = pkt->next;	spin_unlock_irqrestore(&priv->lock, flags);	return pkt;}/* * Enable and disable receive interrupts. */static void snull_rx_ints(struct net_device *dev, int enable){	struct snull_priv *priv = netdev_priv(dev);	priv->rx_int_enabled = enable;}    /* * Open and close */int snull_open(struct net_device *dev){	/* request_region(), request_irq(), ....  (like fops->open) */	/* 	 * Assign the hardware address of the board: use "\0SNULx", where	 * x is 0 or 1. The first byte is '\0' to avoid being a multicast	 * address (the first byte of multicast addrs is odd).	 */	memcpy(dev->dev_addr, "\0SNUL0", ETH_ALEN);	if (dev == snull_devs[1])		dev->dev_addr[ETH_ALEN-1]++; /* \0SNUL1 */	netif_start_queue(dev);	return 0;}int snull_release(struct net_device *dev){    /* release ports, irq and such -- like fops->close */	netif_stop_queue(dev); /* can't transmit any more */	return 0;}/* * Configuration changes (passed on by ifconfig) */int snull_config(struct net_device *dev, struct ifmap *map){	if (dev->flags & IFF_UP) /* can't act on a running interface */		return -EBUSY;	/* Don't allow changing the I/O address */	if (map->base_addr != dev->base_addr) {		printk(KERN_WARNING "snull: Can't change I/O address\n");		return -EOPNOTSUPP;	}	/* Allow changing the IRQ */	if (map->irq != dev->irq) {		dev->irq = map->irq;        	/* request_irq() is delayed to open-time */	}	/* ignore other fields */	return 0;}/* * Receive a packet: retrieve, encapsulate and pass over to upper levels */void snull_rx(struct net_device *dev, struct snull_packet *pkt){	struct sk_buff *skb;	struct snull_priv *priv = netdev_priv(dev);	/*	 * The packet has been retrieved from the transmission	 * medium. Build an skb around it, so upper layers can handle it	 */	skb = dev_alloc_skb(pkt->datalen + 2);	if (!skb) {		if (printk_ratelimit())			printk(KERN_NOTICE "snull rx: low on mem - packet dropped\n");		priv->stats.rx_dropped++;		goto out;	}	skb_reserve(skb, 2); /* align IP on 16B boundary */  	memcpy(skb_put(skb, pkt->datalen), pkt->data, pkt->datalen);	/* Write metadata, and then pass to the receive level */	skb->dev = dev;	skb->protocol = eth_type_trans(skb, dev);	skb->ip_summed = CHECKSUM_UNNECESSARY; /* don't check it */	priv->stats.rx_packets++;	priv->stats.rx_bytes += pkt->datalen;	netif_rx(skb);  out:	return;}    /* * The poll implementation. */static int snull_poll(struct net_device *dev, int *budget){	int npackets = 0, quota = min(dev->quota, *budget);	struct sk_buff *skb;	struct snull_priv *priv = netdev_priv(dev);	struct snull_packet *pkt;    	while (npackets < quota && priv->rx_queue) {		pkt = snull_dequeue_buf(dev);		skb = dev_alloc_skb(pkt->datalen + 2);		if (! skb) {			if (printk_ratelimit())				printk(KERN_NOTICE "snull: packet dropped\n");			priv->stats.rx_dropped++;			snull_release_buffer(pkt);			continue;		}		skb_reserve(skb, 2); /* align IP on 16B boundary */  		memcpy(skb_put(skb, pkt->datalen), pkt->data, pkt->datalen);		skb->dev = dev;		skb->protocol = eth_type_trans(skb, dev);		skb->ip_summed = CHECKSUM_UNNECESSARY; /* don't check it */		netif_receive_skb(skb);		        	/* Maintain stats */		npackets++;		priv->stats.rx_packets++;		priv->stats.rx_bytes += pkt->datalen;		snull_release_buffer(pkt);	}	/* If we processed all packets, we're done; tell the kernel and reenable ints */	*budget -= npackets;	dev->quota -= npackets;	if (! priv->rx_queue) {		netif_rx_complete(dev);		snull_rx_ints(dev, 1);		return 0;	}	/* We couldn't process everything. */	return 1;}	            /* * The typical interrupt entry point */static void snull_regular_interrupt(int irq, void *dev_id, struct pt_regs *regs){	int statusword;	struct snull_priv *priv;	struct snull_packet *pkt = NULL;	/*	 * As usual, check the "device" pointer to be sure it is	 * really interrupting.	 * Then assign "struct device *dev"	 */	struct net_device *dev = (struct net_device *)dev_id;	/* ... and check with hw if it's really ours */	/* paranoid */	if (!dev)		return;	/* Lock the device */	priv = netdev_priv(dev);	spin_lock(&priv->lock);	/* retrieve statusword: real netdevices use I/O instructions */	statusword = priv->status;	priv->status = 0;	if (statusword & SNULL_RX_INTR) {		/* send it to snull_rx for handling */		pkt = priv->rx_queue;		if (pkt) {			priv->rx_queue = pkt->next;			snull_rx(dev, pkt);		}	}	if (statusword & SNULL_TX_INTR) {		/* a transmission is over: free the skb */		priv->stats.tx_packets++;		priv->stats.tx_bytes += priv->tx_packetlen;		dev_kfree_skb(priv->skb);

?? 快捷鍵說明

復制代碼 Ctrl + C
搜索代碼 Ctrl + F
全屏模式 F11
切換主題 Ctrl + Shift + D
顯示快捷鍵 ?
增大字號 Ctrl + =
減小字號 Ctrl + -
亚洲欧美第一页_禁久久精品乱码_粉嫩av一区二区三区免费野_久草精品视频
夜色激情一区二区| 国产亚洲欧美一级| 成人免费av在线| 亚洲午夜精品久久久久久久久| 中文字幕免费一区| 国产精品美女久久久久久久久久久 | 777xxx欧美| 欧美精品v国产精品v日韩精品| 在线观看不卡视频| 69久久夜色精品国产69蝌蚪网| 欧美性videosxxxxx| 欧美日韩一区二区电影| 91精品国产综合久久久蜜臀粉嫩| 欧美日韩精品一二三区| 日韩精品一区二区三区视频播放| 欧美电影免费观看高清完整版| 精品国产123| 国产精品丝袜91| 亚洲精品菠萝久久久久久久| 亚洲综合丁香婷婷六月香| 日本中文字幕一区二区视频| 激情综合网天天干| 成人精品在线视频观看| 不卡在线视频中文字幕| 91丝袜美女网| 欧美一区二区三区小说| 国产婷婷色一区二区三区四区 | 亚洲综合图片区| 亚洲国产精品久久一线不卡| 老汉av免费一区二区三区| 国产精品影视天天线| 91麻豆精品一区二区三区| 欧美日韩不卡一区二区| 2021国产精品久久精品| 亚洲视频小说图片| 日本欧美韩国一区三区| 国产成人综合自拍| 欧美日韩亚洲国产综合| 久久久不卡网国产精品二区| 一区二区三区av电影| 激情久久久久久久久久久久久久久久| 成年人国产精品| 精品久久久久久久久久久久久久久| 国产精品欧美经典| 日韩avvvv在线播放| 色综合久久中文综合久久97| 日韩视频免费直播| 亚洲精品免费在线| 国产精品99久久久久久久女警| 欧美视频在线一区| 国产精品久久久久久户外露出| 日日夜夜精品视频天天综合网| 高清不卡一区二区在线| 91精品国产一区二区三区蜜臀| 国产精品女主播av| 国产精品18久久久久久久久| 7777精品伊人久久久大香线蕉的 | 亚洲国产成人私人影院tom| 日本vs亚洲vs韩国一区三区| 99久久精品免费看| 欧美v国产在线一区二区三区| 亚洲bt欧美bt精品| 99久精品国产| 中文字幕第一区综合| 久久精品国产色蜜蜜麻豆| 在线免费亚洲电影| ...中文天堂在线一区| 国产一区二区三区精品欧美日韩一区二区三区 | 蜜臀av性久久久久蜜臀aⅴ四虎| 在线观看av一区| 1024精品合集| 成人av在线影院| 亚洲国产精华液网站w | 一本久道中文字幕精品亚洲嫩| 久久精品欧美日韩精品| 国产一区二区在线视频| 精品国产乱码久久久久久浪潮| 日韩av午夜在线观看| 欧美猛男男办公室激情| 香蕉久久夜色精品国产使用方法| 97se亚洲国产综合自在线| 中文子幕无线码一区tr| 99re6这里只有精品视频在线观看 99re8在线精品视频免费播放 | 成人网在线播放| 国产精品女同一区二区三区| av在线一区二区| 一区二区三区视频在线看| 91精品福利视频| 亚洲成av人影院在线观看网| 在线播放日韩导航| 久久99这里只有精品| 久久久青草青青国产亚洲免观| 国产盗摄视频一区二区三区| 亚洲欧美激情插| 欧美日韩激情在线| 国产久卡久卡久卡久卡视频精品| 欧美韩国一区二区| 色94色欧美sute亚洲线路一久| 亚洲成人福利片| 久久免费国产精品| 91在线免费看| 全部av―极品视觉盛宴亚洲| 精品黑人一区二区三区久久| 国产69精品久久99不卡| 一区二区三区久久| 精品久久99ma| 色吧成人激情小说| 精品一区二区在线免费观看| 国产精品卡一卡二| 欧美日本国产视频| 国产老妇另类xxxxx| 一区二区三区小说| 久久精品视频一区二区三区| 色8久久人人97超碰香蕉987| 久久99久久精品| 伊人一区二区三区| 久久久久久亚洲综合影院红桃| 色呦呦国产精品| 国产一区二区三区四| 亚洲风情在线资源站| 中文字幕在线一区| 精品福利一二区| 欧美亚洲国产一区二区三区| 国产不卡视频在线播放| 日韩精品福利网| 亚洲精品乱码久久久久久| 国产日韩欧美一区二区三区综合| 欧美日韩在线播放三区四区| 国产福利一区二区三区| 日韩—二三区免费观看av| 亚洲丝袜自拍清纯另类| 久久久国产一区二区三区四区小说 | 欧美人与性动xxxx| 99精品欧美一区二区三区小说| 日本不卡1234视频| 亚洲国产精品久久一线不卡| 亚洲色图欧洲色图| 欧美激情综合网| 精品sm捆绑视频| 欧美一区二区福利在线| 欧美色涩在线第一页| 99久久婷婷国产综合精品电影| 国产一区二区在线观看免费| 日韩不卡一二三区| 亚洲1区2区3区视频| 亚洲欧美日韩久久精品| 国产精品美女久久久久久久| 久久人人97超碰com| 日韩精品一区二区三区老鸭窝| 欧美日韩在线播放三区| 欧美怡红院视频| 在线亚洲一区二区| 91久久精品网| 在线观看网站黄不卡| 色系网站成人免费| 99久久精品久久久久久清纯| av在线播放成人| 91麻豆.com| 在线观看免费视频综合| 欧美日韩中文一区| 8v天堂国产在线一区二区| 91精品国产色综合久久| 91精品国产欧美一区二区成人| 欧美日韩aaaaaa| 精品久久人人做人人爰| 精品国产网站在线观看| 国产色一区二区| 国产精品对白交换视频| 亚洲精品免费一二三区| 日韩极品在线观看| 精品一区二区综合| 不卡的电影网站| 欧美亚洲动漫精品| 日韩欧美电影一二三| 久久精品网站免费观看| 亚洲精品一二三| 日韩电影在线观看网站| 国产盗摄女厕一区二区三区| 色综合久久九月婷婷色综合| 欧美精品1区2区| 久久久久久免费| 一区二区三区在线高清| 久久国产欧美日韩精品| 成人精品视频一区二区三区| 在线中文字幕一区二区| 2023国产精华国产精品| 一区二区成人在线观看| 精品一区二区在线看| 日本高清无吗v一区| 日韩欧美综合在线| 亚洲久草在线视频| 韩国在线一区二区| 欧美性大战xxxxx久久久| 久久综合国产精品| 五月婷婷欧美视频| 成人激情开心网| 日韩免费性生活视频播放| 亚洲精品欧美专区| 粉嫩av一区二区三区粉嫩| 91麻豆精品国产91久久久久|