阅读:1406回复:3
为了解决问题,我可以贡献200分!
以前从没接触过driver的编程,刚看了几天NDIS,一头雾水:(,
现在需要在wince下做一个packet filter,有点类似于NAT, 但需要增加一些传输层(TCP/UDP)的分析和改动。 简单的功能需求: 1 截获每一个发到本机MAC地址的IP包 2 分析IP包头和传输层包头,如果符合某种规则( 比如源/目标IP地址在某个范围内,源/目标端口在某个特定范围内),那么向上发给应用层来处理,不是转发! 从NDIS的模型上看,好象并不难,我目前主要的疑问: 是如何让IP地址不是本机的包上传给应用层,我想 是否可以修改应用层包数据,把原始的IP地址/端口信息写进去, 然后由上层某个固定端口的socket来接收。 大侠们,救救我吧。 :P |
|
沙发#
发布于:2003-01-02 11:01
以前从没接触过driver的编程,刚看了几天NDIS,一头雾水:(, 这个方法原理上完全可行。 大致操作过程如下: 1、核心的到一个数据包。 2、判断需要交给app层。既然你的设备属于nat类型的设备, 那么想必其它主机的网关都设置为你的ip,所以也不需要 设置混杂模式。 3、构造一个udp数据包,封装原ip包,交给上层socket端口。 但是细节部分需要做如下考虑: 1、封装之后数据可能拉长。此情况下会得到一个超长的udp 包,上层协议,例如ip,可能没有分配足够大的空间容纳你 的数据包。这种情况下的对策是封装了udp头之后,碎成两个 ip包indicate。 2、你的机器上也许安装了firewall,而firewall的实现也许 在你的driver的上层。这样你indicate一个udp数据包到上层, 也许会被firewall丢弃。因此你必须打开firewall的这个udp 端口。 3、你构造udp包的时候,udp头前面还必须有一个ip头。这个 ip头不能直接复制原来的ip头。你最好是自己定义一个ip头, 用固定源地址,而且不分片。这样也有利于你设置firewall 规则。直接复制原ip头并不会产生太大的问题,因为通常后面 发过来的ip头并不分片。但是ping -l 2000的情况下,会分片。 4、最好用异步socket,否则也许会丢失数据包。 这本身就是核心层和应用层通讯的一个通用方法,freeswan 的pfkey就用类似的思路实现。 不过这个方法在win平台下未必最好。较好的方法还是使用irp 封装数据包上交。但是也许这个driver已经没有deviceobject, 或者已经有了一个irp路线,而你又不打算实现全双工的异步 io,那么这种方法也是完全可以接受的。 用irp的情况下,当判断该数据包需要通过irp交给应用层时, 在receivehandler中总是返回status_success,在 receiveppackethandler中,总是返回0,告诉ndis不需要对 此数据包进行继续处理,也不需要调用complete函数。 Good Luck! |
|
|
板凳#
发布于:2003-01-02 14:29
谢谢版主!
第一步看来是迈出去了,至少方案可行,呵呵。 关于长度和分片的问题暂时可以不考虑,根据我的应用的需求, 我想要做的就是把真实的UDP/TCP头和真实IP地址写到应用层中,然后加上一个UDP头,再加上一个IP头(目的地址为本机),就OK了,总共增加的字节数就是4+8=12,没错吧。 具体的实现上还有很多细节,对于有这方面经验的人想来也不难了, 对我这种driver新手而言可能要走一些弯路,所以需要指导。:) 我的新问题: 1 一般的NAT应该是在IP层就解决问题了吧,不需要让应用层处理吧。 2 Wince跟win2000,XP还是有一些区别的,它提供了一些网卡的 NDIS driver源码,但是没有我用的RTL8139的。另外还提供了 一个passthru的例子,我不太明白passthru是否独立于还是替代 网卡driver来运行? IMD跟NDIS hook相比各有些什么优劣? |
|
地板#
发布于:2003-01-02 15:24
胡版主好久不见,别来无恙乎?
|
|
|