我正在開發一個netfilter的內核模塊中,我需要重新計算IP校驗和。我用這個功能來計算IP校驗(發現它的地方,互聯網上):如何重新計算netfilter中的IP校驗和?
unsigned short ComputeIPChecksum(unsigned char *data, int len)
{
long sum = 0; /* assume 32 bit long, 16 bit short */
unsigned short *temp = (unsigned short *)data;
while(len > 1){
sum += *temp++;
if(sum & 0x80000000) /* if high order bit set, fold */
sum = (sum & 0xFFFF) + (sum >> 16);
len -= 2;
}
if(len) /* take care of left over byte */
sum += (unsigned short) *((unsigned char *)temp);
while(sum>>16)
sum = (sum & 0xFFFF) + (sum >> 16);
return ~sum;
}
通過查看Wireshark的我可以看到,接收的數據包成功,但傳出的數據包Wireshark的顯示不正確的IP校驗和接收。 這是我的鉤子函數:
static unsigned int hook_func(unsigned int hooknum,
struct sk_buff *skb,
const struct net_device *in,
const struct net_device *out,
int (*okfn)(struct sk_buff *))
{
sock_buff = skb;
if (sock_buff)
{
ip_header = (struct iphdr *)skb_network_header(sock_buff);
if (ip_header && ip_header->protocol == TCP)
{
ip_header->check = ComputeIPChecksum((unsigned char *)ip_header, ip_header->ihl*4);
}
}
return NF_ACCEPT;
}
這裏是主要的,我特地綁定同一鉤子函數PRE_ROUTING和POST_ROUTING
static int __init init_main(void)
{
nfho.hook = hook_func;
nfho.hooknum = 0;
nfho.pf = PF_INET;
nfho.priority = NF_IP_PRI_FIRST;
nfho1.hook = hook_func;
nfho1.hooknum = 4;
nfho1.pf = PF_INET;
nfho1.priority = NF_IP_PRI_FIRST;
nf_register_hook(&nfho);
nf_register_hook(&nfho1);
return 0;
}
爲什麼IP校驗遭到損壞時,傳出的數據包? ?
在Wireshark中所示的錯誤:
Header checksum: 0x0000 [incorrect, should be 0x85de (maybe caused by "IP checksum offload"?)]
你實現C++中的Linux內核模塊? – 2012-04-28 20:18:50
您在Linux內核模塊中使用的代碼是「您在互聯網上找到的」?你明白什麼是版權意味着什麼?你是否理解「簽名」意味着你發誓你寫了所有的代碼,或者擁有代碼版權的人已經在GPLv2下授權了它? – 2012-04-28 20:21:11
定義「損壞的IP標頭」。這是否意味着「不正確的校驗和」或實際上「損壞的IP頭」?如果是後者,那麼你可能搞亂了別的東西。 – mfontanini 2012-04-28 20:48:16