亚洲av成人无遮挡网站在线观看,少妇性bbb搡bbb爽爽爽,亚洲av日韩精品久久久久久,兔费看少妇性l交大片免费,无码少妇一区二区三区

  免費注冊 查看新帖 |

Chinaunix

  平臺 論壇 博客 文庫
12下一頁
最近訪問板塊 發(fā)新帖
查看: 7104 | 回復: 12
打印 上一主題 下一主題

[內核模塊] [求助]skb_copy_expand擴展報文頭 [復制鏈接]

論壇徽章:
0
跳轉到指定樓層
1 [收藏(0)] [報告]
發(fā)表于 2012-11-29 19:21 |只看該作者 |倒序瀏覽
本帖最后由 newand 于 2012-11-29 19:34 編輯

現在程序中使用skb_copy_expand步驟是這樣的
1. 調用skb_copy_expand多增加一塊內容,返回new_skb。
2. 使用skb_put將tail指針下移,增加skb的len。
3. 用memcpy將skb中前40個字節(jié)的IP header復制到new_skb中。
4. 用memcpy將skb中40字節(jié)往后的內容復制到new_skb的第40+extend header地址處。
5. 設置extend header的值。

但是運行的結果是,每次抓包,報文的長度不會改變,只是因為第5步改變的內容導致報文出錯。
  1. /*
  2. * this programe is working as plugin of netfilter which will pin a timestamp to
  3. * the destination header of ipv6 packet every x seconds when the packet is
  4. * the object multicast packet.
  5. */


  6. #include <linux/netfilter.h>
  7. #include <linux/netfilter_ipv6.h>
  8. #include <linux/netfilter_ipv6/ip6_tables.h>
  9. #include <linux/module.h>
  10. #include <linux/moduleparam.h>
  11. #include <linux/kernel.h>
  12. #include <linux/inet.h>
  13. #include <linux/ip.h>
  14. #include <linux/udp.h>
  15. #include <net/checksum.h>
  16. #include <net/udp.h>
  17. #include <net/ipv6.h>
  18. #include <linux/time.h>

  19. #include <asm/byteorder.h>

  20. MODULE_LICENSE("GPL");
  21. MODULE_AUTHOR("qj");
  22. MODULE_DESCRIPTION("Change the header of ipv6 packet");

  23. #define PRINT(fmt,args...) printk("INFO: " fmt, ##args)


  24. /* IP6 Hooks */
  25. /* After promisc drops#include <asm/byteorder.h>
  26. , checksum checks. */
  27. #define NF_IP6_PRE_ROUTING  0
  28. /* If the packet is destined for this box. */
  29. #define NF_IP6_LOCAL_IN     1
  30. /* If the packet is destined for another interface. */
  31. #define NF_IP6_FORWARD      2
  32. /* Packets coming from a local process. */
  33. #define NF_IP6_LOCAL_OUT        3
  34. /* Packets about to hit the wire. */
  35. #define NF_IP6_POST_ROUTING 4


  36. /*sequence of measeure#include <asm/byteorder.h>
  37. sample packet*/
  38. static int sample_seq = 0;

  39. /*Next header destination header*/
  40. struct ip6_dst_hdr
  41. {
  42.                 uint8_t ip6d_nxt;
  43.                 uint8_t ip6d_len;
  44.                 uint8_t ip6d_opt_type;
  45.                 uint8_t ip6d_opt_len;
  46.                 uint32_t ip6d_ssn;
  47.                 uint32_t ip6d_sec;
  48.                 uint32_t ip6d_usec;
  49. };


  50. inline
  51. void print_6addr(const struct in6_addr *addr)
  52. {
  53.     PRINT("%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x:%02x%02x\n",
  54.                  (int)addr->s6_addr[0], (int)addr->s6_addr[1],
  55.                  (int)addr->s6_addr[2], (int)addr->s6_addr[3],
  56.                  (int)addr->s6_addr[4], (int)addr->s6_addr[5],
  57.                  (int)addr->s6_addr[6], (int)addr->s6_addr[7],
  58.                  (int)addr->s6_addr[8], (int)addr->s6_addr[9],
  59.                  (int)addr->s6_addr[10], (int)addr->s6_addr[11],
  60.                  (int)addr->s6_addr[12], (int)addr->s6_addr[13],
  61.                  (int)addr->s6_addr[14], (int)addr->s6_addr[15]);
  62. }
  63. char *in_ntoa(__u32 in)
  64.   {
  65.           static char buff[18];
  66.           char *p;
  67.   
  68.           p = (char *) &in;
  69.           sprintf(buff, "%d.%d.%d.%d",
  70.                   (p[0] & 255), (p[1] & 255), (p[2] & 255), (p[3] & 255));
  71.           return(buff);
  72.   }

  73. struct sk_buff *
  74. ip6_reconstruct_pkt(struct sk_buff *skb)
  75. {
  76.         struct sk_buff *new_skb, *temp_skb;
  77.         struct ipv6hdr * ip6_hdr = ipv6_hdr(skb);
  78.         struct ip6_dst_hdr *ip6_dst;
  79.         struct timeval tv;//get time

  80.         ip6_hdr->nexthdr = 0x60;

  81.         //copy from the *skb to new_skb
  82.         new_skb = skb_copy_expand(skb, skb_headroom(skb),
  83.                                 skb_tailroom(skb) + sizeof(struct ip6_dst_hdr),
  84.                                 GFP_ATOMIC);

  85.         if(new_skb == NULL)
  86.         {
  87.                 PRINT("Allocate new sk_buffer error!\n");
  88.                 return NULL;
  89.         }

  90.         //set the new_skb
  91.         if(skb->sk != NULL)
  92.                 skb_set_owner_w(new_skb, skb->sk);

  93.         //move tail to tail + sizeof(ip6_dst_hdr)
  94.         skb_put(new_skb,sizeof(struct ip6_dst_hdr));
  95.   
  96.         //insert a ip6_dst_hdr between the memory
  97.         memcpy (new_skb->data, skb->data, 40);//the ip header has 40 bytes
  98.              memcpy (new_skb->data + 40 + sizeof (struct ip6_dst_hdr),
  99.                                   skb->data + 40, skb->len - 40);

  100.         skb = new_skb;//skb pointer to new_skb

  101.             //turn the space to ip6_dst struct
  102.         ip6_dst = (struct ip6_dst_hdr *)(new_skb->data + 40);
  103.         memset(ip6_dst,0,sizeof(struct ip6_dst_hdr));
  104.         //add ipv6 destination header
  105.         ip6_dst->ip6d_nxt = htonl(0x17);
  106.         ip6_dst->ip6d_len = htonl(0x15);
  107.         ip6_dst->ip6d_opt_type = htonl(0x00);// type of option
  108.         ip6_dst->ip6d_opt_len = htonl(0x0C);
  109.        
  110.         do_gettimeofday(&tv);
  111.              ip6_dst->ip6d_sec = htonl(tv.tv_sec);
  112.         ip6_dst->ip6d_usec = htonl(tv.tv_usec);
  113.         sample_seq++;
  114.         if(sample_seq==0xffffffff)//if overflow ,reset
  115.         {
  116.            sample_seq=0;
  117.         }
  118.         ip6_dst->ip6d_ssn = htonl(sample_seq);

  119.         return skb;
  120. }

  121. /*Hook which will call the encapsulate func when condition satisfied
  122. *condition1: IPv6 Multicast packets
  123. *condition2: every 20ms
  124. */
  125. static unsigned int
  126. ip6_multi_modify(unsigned int hooknum,
  127.                                 struct sk_buff *skb,
  128.                                 const struct net_device *in,
  129.                                 const struct net_device *out,
  130.                                 int (*okfn)(struct sk_buff*))
  131. {
  132.     struct sk_buff *sk = skb;
  133.         struct ipv6hdr *ip6_hdr = ipv6_hdr(skb);//header

  134.         //because nh only supportted in kernels below 2.6
  135.         //after 2.6, it often use network_header to express nh
  136.         //struct ipv6hdr *ip6_hdr = (struct ipv6hdr*)skb->nh.ipv6h;
  137.         if(ip6_hdr->version == 6)
  138.         {
  139.                 struct in6_addr destip = ip6_hdr->daddr;//destination ip
  140.                 //TODO:use module_para or /proc to replace here
  141.                 if(destip.s6_addr[0] == 0xff && destip.s6_addr[1] == 0x15)

  142.                 {
  143.                         if(skb_tailroom(sk) >= 40)
  144.                         {
  145.                                 PRINT("tailroom is enough\n");
  146.                         }
  147.                         else
  148.                         {
  149.                                 PRINT("not enough\n");
  150.                         }
  151.                    skb = ip6_reconstruct_pkt(skb);
  152.                         if(skb == NULL)
  153.                         {
  154.                                 return NF_STOLEN;
  155.                         }
  156.                         ip6_hdr= ipv6_hdr(skb);

  157.                         if(!skb)
  158.                                 return NF_STOLEN;
  159.                 }
  160.         }
  161.         return NF_ACCEPT;
  162. }


  163. /*Initialize the hook*/
  164. static struct nf_hook_ops nf_out_modify =
  165. {
  166.         .hook = ip6_multi_modify,
  167.         .hooknum = NF_IP6_PRE_ROUTING,//Check all the forwarded packets
  168.         .pf = PF_INET6,
  169.         .priority = NF_IP6_PRI_FIRST,
  170. };

  171. /*Initialize the module*/
  172. static int __init ip6_multi_init(void)
  173. {
  174.         int ret;
  175.         ret = nf_register_hook(&nf_out_modify);
  176.         PRINT("IPV6 multicast packet modify module init.\n");
  177.         return 0; //success
  178. }

  179. /*Clear the module*/
  180. static void __exit ip6_multi_exit(void)
  181. {
  182.         nf_unregister_hook(&nf_out_modify);
  183.         PRINT("IPV6 multicast packet modify module exit.\n");
  184. }

  185. module_init(ip6_multi_init);
  186. module_exit(ip6_multi_exit);
復制代碼
實在沒找出問題在哪,請各位大牛幫忙看看。

論壇徽章:
0
2 [報告]
發(fā)表于 2012-11-30 14:07 |只看該作者
沒有拿代碼做實驗,至少有一個潛在的問題。
skb_linear.

論壇徽章:
0
3 [報告]
發(fā)表于 2012-11-30 14:11 |只看該作者
回復 1# newand


    還有個原有的skb沒有釋放的問題。

論壇徽章:
0
4 [報告]
發(fā)表于 2012-11-30 16:11 |只看該作者
本帖最后由 newand 于 2012-11-30 16:30 編輯

回復 2# oscarvei


    你好,剛接觸內核網絡編程,大部分都是看網上的示例或者去github上找代碼。比較少用skb_linear,查了skb_linearize的作用是- convert paged skb to linear one。(我不是特別明白,請問有沒有什么書或者資料推薦嗎?)

另外關于釋放skb的問題
我之前用kfree來在 skb = new_skb;之前釋放skb,不過會導致死機的問題。
是不是還需要其他操作?

還有一個問題就是,抓包時發(fā)現通過skb_copy_expand新產生報文是沒有的,還需要調用什么函數,將它返回的skb加入到隊列嗎?

論壇徽章:
0
5 [報告]
發(fā)表于 2012-12-01 10:38 |只看該作者
kfree不能釋放skb    skb釋放用__kfree_skb

論壇徽章:
0
6 [報告]
發(fā)表于 2012-12-01 13:47 |只看該作者
一些操作的函數 可以參考內核代碼

論壇徽章:
0
7 [報告]
發(fā)表于 2012-12-01 13:53 |只看該作者
回復 6# SCDXMOE


    請問,我擴展了報文報頭的長度,用skb_put將tail指針下移,然后用memcpy將數據拷貝。除了這些操作還應該有其他能夠設置報文長度的操作嗎?
因為我咋client抓到的報文,長度還是沒有更改之前的長度。

論壇徽章:
0
8 [報告]
發(fā)表于 2012-12-01 14:37 |只看該作者
你要確定 你用了skb_put之后 要相應的更改skb->len

論壇徽章:
0
9 [報告]
發(fā)表于 2012-12-01 15:03 |只看該作者
本帖最后由 newand 于 2012-12-01 15:10 編輯

回復 8# SCDXMOE


    skb_put的函數中會對skb->len做增加操作。
  1. unsigned char *skb_put(struct sk_buff *skb, unsigned int len)
  2. {
  3.     unsigned char *tmp = skb_tail_pointer(skb);
  4.     SKB_LINEAR_ASSERT(skb);
  5.     skb->tail += len;
  6.     skb->len  += len;
  7.     if (unlikely(skb->tail > skb->end))
  8.         skb_over_panic(skb, len, __builtin_return_address(0));
  9.     return tmp;
  10. }
復制代碼
skb->len的大小是隨著skb->put的調用而變化的,
不過skb->truesize沒變,但是我手動設置了skb->truesize之后,在client抓到的報文,長度不因為增加了ip首部而變化。

論壇徽章:
0
10 [報告]
發(fā)表于 2012-12-01 16:17 |只看該作者
skb->truesize =len+sizeof(skbuff)是隨著len的長度變化er變化的 怎么可能是沒有變化呢
您需要登錄后才可以回帖 登錄 | 注冊

本版積分規(guī)則 發(fā)表回復

  

北京盛拓優(yōu)訊信息技術有限公司. 版權所有 京ICP備16024965號-6 北京市公安局海淀分局網監(jiān)中心備案編號:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年舉報專區(qū)
中國互聯網協(xié)會會員  聯系我們:huangweiwei@itpub.net
感謝所有關心和支持過ChinaUnix的朋友們 轉載本站內容請注明原作者名及出處

清除 Cookies - ChinaUnix - Archiver - WAP - TOP