文章详情

  • 游戏榜单
  • 软件榜单
关闭导航
热搜榜
热门下载
热门标签
php爱好者> php文档>Linux下的网络HOOK实现以及使用方法【来自2.6.19..

Linux下的网络HOOK实现以及使用方法【来自2.6.19..

时间:2007-03-07  来源:leigaiting

最近疯狂的研究Linux的种种功能,也颇有心得,这里讲述一下Linux下的Net的Hook,使用net的Hook可以实现很多很多非常底层的功能,比如过滤报文,做防火墙,做代理等等。
Now,Let's Go!

使用的是Linux 2.6.19.1的内核代码。
首先是 在./Source/net/netfilter/core.c文件中的函数 nf_register_hook:

static DEFINE_SPINLOCK(nf_hook_lock);

int nf_register_hook(struct nf_hook_ops *reg)
{
  struct list_head *i;

  spin_lock_bh(&nf_hook_lock);
  list_for_each(i, &nf_hooks[reg->pf][reg->hooknum]) {
    if (reg->priority < ((struct nf_hook_ops *)i)->priority)
      break;
  }
  list_add_rcu(&reg->list, i->prev);
  spin_unlock_bh(&nf_hook_lock);

  synchronize_net();
  return 0;
}
EXPORT_SYMBOL(nf_register_hook);

void nf_unregister_hook(struct nf_hook_ops *reg)
{
  spin_lock_bh(&nf_hook_lock);
  list_del_rcu(&reg->list);
  spin_unlock_bh(&nf_hook_lock);

  synchronize_net();
}
EXPORT_SYMBOL(nf_unregister_hook);

int nf_register_hooks(struct nf_hook_ops *reg, unsigned int n)
{
  unsigned int i;
  int err = 0;

  for (i = 0; i < n; i++) {
    err = nf_register_hook(&reg[i]);
    if (err)
      goto err;
  }
  return err;

err:
  if (i > 0)
    nf_unregister_hooks(reg, i);
  return err;
}
EXPORT_SYMBOL(nf_register_hooks);

void nf_unregister_hooks(struct nf_hook_ops *reg, unsigned int n)
{
  unsigned int i;

  for (i = 0; i < n; i++)
    nf_unregister_hook(&reg[i]);
}
EXPORT_SYMBOL(nf_unregister_hooks);


上面分别是四个函数:
nf_register_hook,nf_unregister_hook,nf_register_hooks,nf_unregister_hooks.
功能是注册Hooks函数
输入的参数是struct nf_hook_ops *reg。

下面让我们看一个验证ARP报文的Hook代码,以表示我们如何使用Hook函数实现这种功能。


unsigned int arphook_snd(unsigned int hooknum,struct sk_buff **skb,const struct net_device *in, const struct net_device *out,int (*okfn)(struct sk_buff*))
{
  struct arphdr *arp;
  struct net_device *dev;
  unsigned char * arp_ptr;
  unsigned char *sha, *tha;
  u32 sip,tip;
  unsigned short arpop;
  unsigned int status=NF_DROP;

  dev=(*skb)->dev;
  arp = (*skb)->nh.arph;
  arp_ptr= (unsigned char *)(arp+1);
  sha     = arp_ptr;
  arp_ptr += dev->addr_len;
  memcpy(&sip, arp_ptr, 4);
  arp_ptr += 4;
  tha     = arp_ptr;
  arp_ptr += dev->addr_len;
  memcpy(&tip, arp_ptr, 4);

  arpop=ntohs(arp->ar_op);

  if(!check_ip(&tip,WABLOCK))  /*check block list*/
  {
    if(arpop==1) /*sending ARP request*/
    {
      if(!check_ip(&tip,WAARP)) /*if not in list add it*/
        add_ip(&tip,WAARP);
    }
    status=NF_ACCEPT;
  }
  return(status);
}


下面是初始化一些参数的函数

static int arpstar_init(void)
{
  arphkrcv.hook=arphook_rcv;  /*arp receive hook*/
  arphkrcv.hooknum=NF_ARP_IN;
  arphkrcv.pf=NF_ARP;
  arphkrcv.priority=NF_IP_PRI_FIRST;
  nf_register_hook(&arphkrcv);

  arphksnd.hook=arphook_snd;  /*arp send hook*/
  arphksnd.hooknum=NF_ARP_OUT;
  arphksnd.pf=NF_ARP;
  arphksnd.priority=NF_IP_PRI_FIRST;  
  nf_register_hook(&arphksnd);

  iphkrcv.hook=iphook_rcv;  /*ip rcv hook*/
  iphkrcv.hooknum=NF_IP_LOCAL_IN;
  iphkrcv.pf=PF_INET;
  iphkrcv.priority=NF_IP_PRI_FIRST;
  nf_register_hook(&iphkrcv);
 
  tmac=strtomac(trustedmac);
  trustip=strtou32(trustedip);
  run_timer(0);
  return(0);
}

下面是函数结束时候的清理工作

static void arpstar_exit(void)
{
  nf_unregister_hook(&arphkrcv);  /*clean up time*/
  nf_unregister_hook(&arphksnd);
  nf_unregister_hook(&iphkrcv);
  del_timer(&watimer);    
  free_list();
  kfree(tmac);
}



我们知道Windows下面也有Hook的功能,但是要Hook到Net的底层,一般是使用NDIS来实现,但是Linux就提供了如此强大的功能,让我们不得不佩服Linux的伟大。几天的研究让我越来越对Linux的推崇!而且我想Linux在嵌入式方面的应用会更加广泛!
这几天也在看一些嵌入式的资料,想想,这个世界真的可以因为Linux的改变而改变,相对来说Windows的代码保密性会失去很多嵌入式方面的开发者的!
相关阅读 更多 +
排行榜 更多 +
平衡球球

平衡球球

休闲益智 下载
平衡球球游戏

平衡球球游戏

休闲益智 下载
土耳其方块消除游戏

土耳其方块消除游戏

休闲益智 下载