科技行者

行者学院 转型私董会 科技行者专题报道 网红大战科技行者

知识库

知识库 安全导航

至顶网软件频道SYN Cookie原理及在Linux内核中的实现 (2)

SYN Cookie原理及在Linux内核中的实现 (2)

  • 扫一扫
    分享文章到微信

  • 扫一扫
    关注官方公众号
    至顶头条

Linux内核中对SYN Flood有很好的防护。以下的讨论都是针对Linux2.4.20内核进行的。在每一个sock都有一个tcp_opt即这个sock的TCP选项。

作者:赛迪网 来源:赛迪网 2007年10月29日

关键字: 内核 原理 SYN Linux

  • 评论
  • 分享微博
  • 分享邮件

三 Linux内核中的SYN Cookie实现

Linux内核中对SYN Flood有很好的防护。以下的讨论都是针对Linux2.4.20内核进行的。在每一个sock都有一个tcp_opt即这个sock的TCP选项。在tcp_opt其中有一个tcp_listen_opt,这里存储的是这个sock在LISTEN状态下时保存的一些选项,其中有一个open_request结构的数组,数组长度为TCP_SYNQ_HSIZE(512)。所有这些表示在一个sock,最多可以同时开启512个半开连接(这是在不考虑其他约束条件时的最大值,实际情况中不会达到这个值)。当这个数组满了时,新来的open_request会顶替掉一个老的open_request。这样,即使没有启动SYN Cookie,也能够在SYN Flood发生时保护系统免于瘫痪。问题是这种处理方法会在面对SYN Flood攻击时丢掉正常的TCP连接请求。SYN Cookie的作用恰恰是保证在面对SYN Flood攻击时,一方面能够拒绝非法的TCP连接请求,一方面正常连接可以被建立。

Linux内核对TCP流程的处理主要在tcp_ipv4.c文件中的函数实现。具体的,当处理TCP SYN包时,系统进入tcp_v4_conn_request函数。其中调用cookie_v4_init_sequence生成一个ISN(Initial Sequence Number)。Linux内核把它作为SYN Cookie流程中的cookie。

cookie_v4_init_sequence函数在syncookies.c文件中定义,它又调用random.c文件中的secure_tcp_syn_cookie函数。cookie的实质计算是在这个函数中进行的。

在random.c文件里给出secure_tcp_syn_cookie函数的定义之前给出两个宏,它们的定义分别为:

#define COOKIEBITS 24
  #define COOKIEMASK (((__u32)1 << COOKIEBITS) - 1)
  

COOKIEBITS表示cookie的比特长度;COOKIEMASK是一个COOKIEBITS长的比特串,所有比特都是1。

还有两个比特串,被定义成一个__u32的二维数组:

 static __u32 syncookie_secret[2][16-3+HASH_BUFFER_SIZE];

其中所有的比特值在secure_tcp_syn_cookie中被随机的赋予,用get_random_bytes函数。它们成为制作cookie的密钥。这两个被随机产生的比特串是整个SYN Cookie实现方案的关键。另外还有一个开关syncookie_init控制对这两个密钥的改动。

还需要指出,在文件syncookies.c中定义有一个__u16组成的表static __u16 const msstab[],这个表中保存的是一些可能的MSS(Maximum Segment Size)值。

secure_tcp_syn_cookie函数的返回值就是计算得到的ISN值,即cookie。为了描述方便,我们给出如下定义:

tmp1 := saddr + daddr + ((sport<<16)+dport) + syncookie_secret[0]
   tmp2 := saddr + daddr + ((sport<<16)+dport) + syncookie_secret[1]
   tmp11 := HASH_TRANSFORM(tmp1[16], tmp1)
   tmp22 := HASH_TRANSFORM(tmp2[16], tmp2)
  A := tmp11[0][17]
   B := tmp22[1][17]

sseq := ntohl(skb->h.th->seq) 这里的skb是携带TCP SYN的那个skb,count1 := jiffies/(HZ*60) 当前时间的分钟值,data1 := msstab, 从前往后最后一个小于skb中携带的MSS值的值的索引(值得注意的是两个密钥在第一次被初始化后,就不会再有改动,直到系统重新启动。因此可以认为它是一个常值。)

有了上面的定义我们可以得到cookie等于:

    isn := A+sseq + (count1<<COOKIEBITS) + (B+data1)&COOKIEMASK
   
    • 评论
    • 分享微博
    • 分享邮件
    邮件订阅

    如果您非常迫切的想了解IT领域最新产品与技术信息,那么订阅至顶网技术邮件将是您的最佳途径之一。

    重磅专题
    往期文章
    最新文章