从收包和发包来看IP层的csum是如何计算的,是如何进行校验的。csum值为2个字节长度。
发包流程如下所示,在__ip_local_out_sk函数中调用ip_send_check函数进行csum计算。
ip_local_out->ip_local_out_sk->__ip_local_out->__ip_local_out_sk
ip_send_check函数
/* Generate a checksum for an outgoing IP datagram. */
void ip_send_check(struct iphdr *iph)
{
iph->check = 0; //设置check为0
iph->check = ip_fast_csum((unsigned char *)iph, iph->ihl); //把计算csum的值保存到check字段
}
ip_fast_csum函数 (ip_fast_csum的实现版本较多,选择其中一个利于理解的进行分析)
/*
* This is a version of ip_compute_csum() optimized for IP headers,
* which always checksum on 4 octet boundaries.
*/
__sum16 ip_fast_csum(const void *iph, unsigned int ihl)
{
return (__force __sum16)~do_csum(iph, ihl*4);
}
do_csum函数
static unsigned int do_csum(const unsigned char *buff,