Hi, I am attempting to adjust contents of tcp packets using the nf queue system, the queue part is working as I expected, however I am running into problems recalculating the tcp checksum. At the moment, the packet isnt being changed, and I am simply reading the checksum, then trying to regenerate it, these values arent matching and I am at a loss as to where I am going wrong. Here is the checksum code at the moment: struct tcp_pseudo /*the tcp pseudo header*/ { __u32 src_addr; __u32 dst_addr; __u8 zero; __u8 proto; __u16 length; }pseudohead; long checksum(unsigned short *addr, unsigned int count) { register long sum = 0; while( count > 1 ) { /* This is the inner loop */ sum += * addr++; count -= 2; } /* Add left-over byte, if any */ if( count > 0 ) sum += * (unsigned char *) addr; /* Fold 32-bit sum to 16 bits */ while (sum>>16) sum = (sum & 0xffff) + (sum >> 16); return ~sum; } long get_tcp_checksum(struct iphdr * myip, struct tcphdr * mytcp) { mytcp->check = 0; u16 total_len = ntohs(myip->tot_len); int tcpopt_len = mytcp->doff*4 - 20; int tcpdatalen = total_len - (mytcp->doff*4) - (myip->ihl*4); /*Setup the pseudo header*/ pseudohead.src_addr=myip->saddr; pseudohead.dst_addr=myip->daddr; pseudohead.zero=0; pseudohead.proto=IPPROTO_TCP; pseudohead.length=htons(sizeof(struct tcphdr) + tcpopt_len + tcpdatalen); /*Calc lengths*/ int totaltcp_len = sizeof(struct tcp_pseudo) + sizeof(struct tcphdr) + tcpopt_len + tcpdatalen; unsigned short * tcp = new unsigned short[totaltcp_len]; /*Copy to required mem*/ memcpy((unsigned char *)tcp,&pseudohead,sizeof(struct tcp_pseudo)); memcpy((unsigned char *)tcp+sizeof(struct tcp_pseudo),(unsigned char *)mytcp,sizeof(struct tcphdr)); if(tcpopt_len > 0) memcpy((unsigned char *)tcp+sizeof(struct tcp_pseudo)+sizeof(struct tcphdr), (unsigned char *)myip+(myip->ihl*4)+(sizeof(struct tcphdr)), tcpopt_len); if(tcpdatalen > 0) memcpy((unsigned char *)tcp+sizeof(struct tcp_pseudo)+sizeof(struct tcphdr), (unsigned char *)mytcp+(mytcp->doff*4), tcpdatalen); // memcpy((unsigned char *)tcp+sizeof(struct tcp_pseudo)+sizeof(struct tcphdr)+tcpopt_len, (unsigned char *)mytcp+(mytcp->doff*4), tcpdatalen); return checksum(tcp, totaltcp_len); } and the whole file, although not much bigger is here: http://pastebin.com/m2bc636ed An example of the output values I am getting at the moment is: packet size = 529 ip->checksum = 22679 tcp->checksum = 14964 new ip->checksum = 22679 new tcp->checksum = 8007 packet size = 52 ip->checksum = 13465 tcp->checksum = 8007 new ip->checksum = 13465 new tcp->checksum = 31444 packet size = 52 ip->checksum = 13209 tcp->checksum = 31444 new ip->checksum = 13209 new tcp->checksum = 50105 packet size = 52 ip->checksum = 12953 tcp->checksum = 50105 new ip->checksum = 12953 new tcp->checksum = 12783 Any help or suggestions please? I am at a loss -- Michael Lawson (mshindo) -- To unsubscribe from this list: send the line "unsubscribe netfilter-devel" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html