请问处理帧要占用CPU时间吗?

cwanter 2003-06-10 06:39:07
一位前辈在他的文章中说:
在一个实际的系统中,数据的收发是由网卡来完成的,网卡接收到传输来的数据,网卡内的单片程序接收数据帧的目的MAC地址,根据计算机上的网卡驱动程序设置的接收模式判断该不该接收,认为该接收就接收后产生中断信号通知CPU,认为不该接收就丢掉不管,所以不该接收的数据网卡就截断了,计算机根本就不知道。CPU得到中断信号产生中断,操作系统就根据网卡的驱动程序设置的网卡中断程序地址调用驱动程序接收数据,驱动程序接收数据后放入信号堆栈让操作系统处理。

我的理解为:如果目的mac地址不为本网卡的MAC的话,就由网卡把帧过滤掉,跟本不会由CPU处理。但我修改mac地址后,仍能正常通信。mac地址是放在注册表中。这就产生一个问题:到底是收到帧后取注册表中的mac地址与收到的帧比较还是由网卡处理?用ipconfig看到的mac地址确实已经修改成功,而且其他机器arp表的本机mac地址也是修改后的地址。是每收到一帧就读注册表比较,还是网卡中就有一个缓存在系统启动时就把注册表中的mac读入,以后处理帧就用这个了。前者好象效率很低吧。

敬请各位大侠指点~
...全文
86 13 打赏 收藏 转发到动态 举报
写回复
用AI写文章
13 条回复
切换为时间正序
请发表友善的回复…
发表回复
jigsawpuzzle 2003-06-14
  • 打赏
  • 举报
回复
现在有专门的NP(网络处理器)这样就不用耗费CPU的时间了!
alamb 2003-06-13
  • 打赏
  • 举报
回复
除了把物理信号还原成数据信号以外,网卡都要耗费cpu的时间的,也就是说物理层以上都要经过cpu处理(有些是在驱动程序上处理,但无论如何都耗费cpu时间)
cwanter 2003-06-12
  • 打赏
  • 举报
回复
谢谢,关于数据包的分类我明白了,现在就是网卡的工作模式问题了,这也是我一直困惑的问题:“网卡处于混杂模式的条件永远为真”是什么意思?就是说除了广播和组播就是混杂了?没有直接方式了?那为什么sniff的时候还要设混杂模式?
jigsawpuzzle 2003-06-12
  • 打赏
  • 举报
回复
OK!再贴一小段源代码大家就明白了,在linux\net\ipv4\ip_input.c中有关于IP数据包处理如下函数ip_rcv():
/*
* Main IP Receive routine.
*/
int ip_rcv(struct sk_buff *skb, struct net_device *dev, struct packet_type *pt)
{
struct iphdr *iph;

/* When the interface is in promisc. mode, drop all the crap
* that it receives, do not try to analyse it.
*/
if (skb->pkt_type == PACKET_OTHERHOST)嘿嘿……不是我们的包就都丢掉了~
goto drop;

IP_INC_STATS_BH(IpInReceives);对于接收到数据包的CPU更新SNMP统计变量
……
……
……
drop:
kfree_skb(skb);
out:
return NET_RX_DROP;
}

对于直接单播嘛很好处理的,这是sk_buff结构初始化的默认值,所以在上贴对skb->pkt_type的判断中就不再出现了,因为处了多播、广播、非本机类型外,就只有单播了。源码片段:
skb->pkt_type = PACKET_HOST; /* Default type */ 直接单播



cwanter 2003-06-12
  • 打赏
  • 举报
回复
楼上好象没有看明白我的意思:
网卡不是有4种工作模式:
广播、组播、混杂、直接。上面的代码if(*eth->h_dest&1)处理了广播、组播模式,else if(1 /*dev->flags&IFF_PROMISC*/) 网卡处于混杂模式的条件永远为真 这里处理所有其他的情况,好象是只处理了混杂模式,那直接模式呢?
cwanter 2003-06-12
  • 打赏
  • 举报
回复
谢谢楼上,请再到http://expert.csdn.net/Expert/topic/1899/1899893.xml?temp=.4501612领分:)
jigsawpuzzle 2003-06-12
  • 打赏
  • 举报
回复
“网卡处于混杂模式的条件永远为真”这是接口文件判断的条件,它和驱动程序是两回事。网卡里的缓存(具体位置不清楚)记住了当前网卡自身的MAC地址。你说的修改MAC地址后仍然可以正常通讯,我想哪必须是又经历了一次ARP地址解析之后的事!发自你主机以前MAC地址的包必定被你丢弃了。
else if(1 /*dev->flags&IFF_PROMISC*/)
{
if(memcmp(eth->h_dest,dev->dev_addr, ETH_ALEN))
skb->pkt_type=PACKET_OTHERHOST;
}
另外谁也没有说除了广播和组播之外就只剩下混杂了,else if(1)中还有一个if判断呢~而且skb->pkt_type的默认值是PACKET_HOST!
tpProgramer 2003-06-11
  • 打赏
  • 举报
回复
网卡的工作模式设置为混杂模式,这样网卡就不会丢弃不属于自己接收的包了,这跟广播和组播是两回事。
jigsawpuzzle 2003-06-11
  • 打赏
  • 举报
回复
else if(1 /*dev->flags&IFF_PROMISC*/) 网卡处于混杂模式的条件永远为真
Sorry~ 如果你没有读过Linux源代码,可能看起来会比较麻烦,我简单的注释一下:
{
if(memcmp(eth->h_dest,dev->dev_addr, ETH_ALEN))
skb->pkt_type=PACKET_OTHERHOST;
}
memcmp函数: 比较两个字符串是否匹配,当然是在规定的长度内
eth->h_dest: 网卡接收到的以太首部结构中的目的MAC地址
dev->dev_addr:接收网卡的mac地址
ETH_ALEN: mac地址长度,这个宏的值为6个字节。
skb-pkt_type: skb是Linux用于在各层间交互数据的数据结构,成员pkt_type表明收到数据包的类型,(多播包?广播包?给其它人的包?给我们的包?……)
jigsawpuzzle 2003-06-11
  • 打赏
  • 举报
回复
数据帧的过滤不是单纯靠硬件来实现的,系统在初始化硬件的时候都有一个描述此硬件的数据结构被创建,对于网卡来说这个数据结构就是net_device结构,此结构中保存着网卡的mac地址。用户可以很方便的修改这个mac地址。当网卡接收到一个帧后,就会调用一个函数,此函数对mac地址进行比对,如果不相同则做出标记,以下是Linux下3c501网卡驱动程序调用/linux/net/ethernet/eth.c的一部分,你可以看看(else if(1)的哪行源代码!):
if(*eth->h_dest&1)
{
if(memcmp(eth->h_dest,dev->broadcast, ETH_ALEN)==0)
skb->pkt_type=PACKET_BROADCAST;
else
skb->pkt_type=PACKET_MULTICAST;
}

/*
* This ALLMULTI check should be redundant by 1.4
* so don't forget to remove it.
*
* Seems, you forgot to remove it. All silly devices
* seems to set IFF_PROMISC.
*/

else if(1 /*dev->flags&IFF_PROMISC*/)
{
if(memcmp(eth->h_dest,dev->dev_addr, ETH_ALEN))
skb->pkt_type=PACKET_OTHERHOST;
}

if (ntohs(eth->h_proto) >= 1536)
return eth->h_proto;
cwanter 2003-06-11
  • 打赏
  • 举报
回复
关于sniffer,是把网卡设为混杂模式就可以让所有的数据都入协议栈了。
cwanter 2003-06-11
  • 打赏
  • 举报
回复
“网卡处于混杂模式的条件永远为真”是什么意思?
就是说除了广播和组播就是混杂了?没有直接方式了?那为什么sniff的时候还要设混杂模式?
ensoniq 2003-06-10
  • 打赏
  • 举报
回复
从你的帖子来看,你已经解出问题所在了那,不是吗?
我也是菜鸟,有个同样的疑惑一起讨论:
如果按照第一种说法,数据的过滤是由网卡硬件实现的,那么局域网上面很常见的那种sniffer工具是怎么实现的呢?

4,356

社区成员

发帖
与我相关
我的任务
社区描述
通信技术相关讨论
社区管理员
  • 网络通信
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧