ip - 如何在不破坏 header 的情况下更改 ip header 中的 tos 位

标签 ip kernel-module

如何改变ip头中tos位的值? 我尝试使用iphdr结构直接修改它。 它是使用 netfilter 在内核级别完成的。 我写的代码如下:

// Including the required header files

#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/netfilter.h>
#include <linux/netfilter_ipv4.h>
#include <linux/init.h>
#include <linux/kthread.h>
#include <linux/signal.h>
#include <linux/errno.h>
#include <linux/sched.h>
#include <linux/wait.h>
#include <linux/types.h>
#include <linux/netdevice.h>
#include <linux/ip.h>
#include <linux/tcp.h>
#include <linux/in.h>
#include <linux/inet.h>
#include <linux/delay.h>
#include <linux/string.h>
#include <linux/socket.h>
#include <linux/net.h>
#include <net/sock.h>
#include <asm/processor.h>
#include <asm/uaccess.h>
#include <linux/file.h>
#include <linux/fs.h>
#include <linux/stat.h>
#include <linux/proc_fs.h>

// Defining the name of the module
#define MODULE_NAME "TOS_setter"

// Structure definition for processing outgoing packets
static struct nf_hook_ops nf_ops_out;

//===========================================================
// Function that modifies the TOS bits
unsigned int tos_setter(unsigned int hooknum,struct sk_buff *skb, const struct net_device *in,
                        const struct net_device *out,int (*okfn)(struct sk_buff*))
{
struct iphdr *iph;
unsigned char tosbits;

if (!skb)return NF_ACCEPT;

iph = ip_hdr(skb);

if (!iph)return NF_ACCEPT;
//if(iph->protocol==IPPROTO_TCP)return NF_ACCEPT;

if (iph->protocol==IPPROTO_TCP)
    { 
printk(KERN_ALERT " The total length is : %d\n" , (int)iph->tot_len);
iph->tos = tosbits | (unsigned char)2;
tosbits = iph->tos;
printk(KERN_ALERT " The tos bits are : %d\n" , (int)tosbits);
printk(KERN_ALERT " The total length is : %d\n" , (int)iph->tot_len);
}
return NF_ACCEPT;
}


//===========================================================
//Initialisation function
static int __init init(void){

   printk(KERN_ALERT " Initialization Started \n");

// Initialize Hook Functions
   nf_ops_out.hook = tos_setter;
   nf_ops_out.pf = PF_INET;
   nf_ops_out.hooknum =4;
   nf_ops_out.priority = NF_IP_PRI_FIRST; 
// Register the Hook functions   
   nf_register_hook(&nf_ops_out);
   printk(KERN_ALERT "hook functions registered\n");

   printk(KERN_ALERT " KSTAT Initialization Completed \n");
   return 0;
}

static void __exit cleanup(void){

  printk(KERN_ALERT "KSTAT Exit Started\n");

// Unregister the hook functions
  nf_unregister_hook(&nf_ops_out);
  printk("Unregistered the hooks\n");


  printk(KERN_ALERT "KSTAT Exit Completed\n");
}  

/* init and cleanup functions */
module_init(init);
module_exit(cleanup);

MODULE_LICENSE("GPL");

问题是,当我尝试更改 tos 位的值时,我的互联网停止工作。 有没有其他方法,或者如果有人能指出我做错了什么,那将非常有帮助。

最佳答案

更改 header 中的任何内容后,您必须重新计算 IP header 校验和。

见 WP:http://en.wikipedia.org/wiki/IPv4_header_checksum 代码在这里:How do I compute an RFC 791 IP header checksum?

关于ip - 如何在不破坏 header 的情况下更改 ip header 中的 tos 位,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13410212/

相关文章:

sockets - 在 Windows 中如何检测哪个程序正在监听 TCP/IP 端口?

java - 我如何检查IP是否在java中存在?

android - Android Q中访问/proc/net/tcp

c - 由于没有这样的设备或地址,打开设备文件失败

c - 内核到用户空间的低延迟通信

linux - lm75 内核模块在用户空间可用

sockets - 如何从 Phoenix 框架中的套接字获取remote_ip?

amazon-web-services - 如何控制AWS Elasticsearch Service和Kibana的访问权限?

c - 内核模块中的错误处理

c - 将已弃用的 "dev_attrs"属性替换为 "dev_groups"