返回列表 发帖

[讨论]针对syn flood,怎么办?

假设有一个恶意的家伙,一直给你的web服务器发送源ip已经被修改的,基本上不存在的源ip的syn包,我们如何在自己的程序里识别,并进行阻拦呢?????
假设带宽足够,,,
syn flood:
客户端通过发送在TCP报头中SYN标志置位的数据分段到服务端来请求建立连接。通常情况下,服务端会按照IP报头中的来源地址来返回SYN/ACK置位的数据包给客户端,客户端再返回ACK到服务端来完成一个完整的连接(Figure-1)。
  在攻击发生时,客户端的来源IP地址是经过伪造的(spoofed),现行的IP路由机制仅检查目的IP地址并进行转发,该IP包到达目的主机后返回路径无法通过路由达到的,于是目的主机无法通过TCP三次握手建立连接。在此期间因为TCP缓存队列已经填满,而拒绝新的连接请求。目的主机一直尝试直至超时(大约75秒)。这就是该攻击类型的基本机制。
  发动攻击的主机只要发送较少的,来源地址经过伪装而且无法通过路由达到的SYN连接请求至目标主机提供TCP服务的端口,将目的主机的TCP缓存队列填满,就可以实施一次成功的攻击。实际情况下,发动攻击时往往是持续且高速的.
   这里需要使用经过伪装且无法通过路由达到的来源IP地址,因为攻击者不希望有任何第三方主机可以收到来自目的系统返回的SYN/ACK,第三方主机会返回一个RST(主机无法判断该如何处理连接情况时,会通过RST重置连接),从而妨碍攻击进行。如下图所示:
    由此可以看到,这种攻击方式利用了现有TCP/IP协议本身的薄弱环节,而且攻击者可以通过IP伪装有效的隐蔽自己。但对于目的主机来说,由于无法判断攻击的真正来源。而不能采取有效的防御措施。

如何识别?如何拦截?大家说说自己的想法吧.

[讨论]针对syn flood,怎么办?

这是在网上找到的2种方法:
几种防御技术
  SYN Flood攻击给互联网造成重大影响后,针对如何防御SYN Flood攻击出现了几种比较有效的技术。
2.1   SYN-cookie技术
  一般情况下,当服务器收到一个TCP SYN报文后,马上为该连接请求分配缓冲区,然后返回一个SYN+ACK报文,这时形成一个半连接。SYN Flood正是利用了这一点,发送大量的伪造源地址的SYN连接请求,而不完成连接。这样就大量的消耗的服务器的资源。
  SYN-cookie技术针对标准TCP连接建立过程资源分配上的这一缺陷,改变了资源分配的策略。当服务器收到一个SYN报文后,不立即分配缓冲区,而是利用连接的信息生成一个cookie,并将这个cookie作为将要返回的SYN+ACK报文的初始序列号。当客户端返回一个ACK报文时,根据包头信息计算cookie,与返回的确认序列号(初始的序列号+1)的前24位进行对比,如果相同,则是一个正常连接,然后,分配资源,建立连接。
该技术的巧妙之点在于避免了在连接信息未完全到达前进行资源分配,使SYN Flood攻击的资源消耗失效。实现的关键之处在于cookie的计算。cookie的计算应该做到包含本次连接的状态信息,使攻击者不能伪造cookie。cookie的计算过程如下:
  1)服务器收到一个SYN包后,计算一个消息摘要mac:
mac = MAC(A,k);
MAC是密码学中的一个消息认证码函数,也就是满足某种安全性质的带密钥的hash函数,它能够提供cookie计算中需要的安全性。
A为客户和服务器双方的IP地址和端口号以及参数t的串联组合:
A = SOURCE_IP || SOURCE_PORT || DST_IP || DST_PORT || t
K为服务器独有的密钥;
时间参数t为32比特长的时间计数器,每64秒加1;
  2)生成cookie:
cookie = mac(0:24):表示取mac值的第0到24比特位;
  3)设置将要返回的SYN+ACK报文的初始序列号,设置过程如下:
    i.              高24位用cookie代替;
   ii.              接下来的3比特位用客户要求的最大报文长度MMS代替;
   iii.              最后5比特位为t mod 32。
  客户端收到来自服务器SYN+ACK报文后,返回一个ACK报文,这个ACK报文将带一个cookie(确认号为服务器发送过来的SYN ACK报文的初始序列号加1,所以不影响高24位),在服务器端重新计算cookie,与确认号的前24位比较,如果相同,则说明未被修改,连接合法,然后,服务器完成连接的建立过程。
  SYN-cookie技术由于在连接建立过程中不需要在服务器端保存任何信息,实现了无状态的三次握手,从而有效的防御了SYN Flood攻击。但是该方法也存在一些弱点。由于cookie的计算只涉及了包头的部分信心,在连接建立过程中不在服务器端保存任何信息,所以失去了协议的许多功能,比如,超时重传。此外,由于计算cookie有一定的运算量,增加了连接建立的延迟时间,因此,SYN-cookie技术不能作为高性能服务器的防御手段。通常采用动态资源分配机制,当分配了一定的资源后再采用cookie技术,Linux就是这样实现的。还有一个问题是,当我们避免了SYN Flood攻击的同时,同时也提供了另一种拒绝服务攻击方式,攻击者发送大量的ACK报文,使服务器忙于计算验证。尽管如此,在预防SYN Flood攻击方面,SYN-cookie技术仍然是一种有效的技术。
2.2  地址状态监控的解决方法
  地址状态监控的解决方法是利用监控工具对网络中的有关TCP连接的数据包进行监控,并对监听到的数据包进行处理。处理的主要依据是连接请求的源地址。
每个源地址都有一个状态与之对应,总共有四种状态:
初态:任何源地址刚开始的状态;
NEW状态:第一次出现或出现多次也不能断定存在的源地址的状态;
GOOD状态:断定存在的源地址所处的状态;
BAD状态:源地址不存在或不可达时所处的状态。
具体的动作和状态转换根据TCP头中的位码值决定:
1)监听到SYN包,如果源地址是第一次出现,则置该源地址的状态为NEW状态;如果是NEW状态或BAD状态;则将该包的RST位置1然后重新发出去,如果是GOOD状态不作任何处理。
  2)监听到ACK或RST包,如果源地址的状态为NEW状态,则转为GOOD状态;如果是GOOD状态则不变;如果是BAD状态则转为NEW状态;如果是BAD状态则转为NEW状态。
  3)监听到从服务器来的SYN ACK报文(目的地址为addr),表明服务器已经为从addr发来的连接请求建立了一个半连接,为防止建立的半连接过多,向服务器发送一个ACK包,建立连接,同时,开始计时,如果超时,还未收到ACK报文,证明addr不可达,如果此时addr的状态为GOOD则转为NEW状态;如果addr的状态为NEW状态则转为BAD状态;如果为addr的状态为BAD状态则不变。
状态的转换图如图3所示:



初态
GOOD
NEW
BAD
ACK/RST
SYN
ACK/RST
  
ACK包确认超时
ACK/RST
  
ACK包确认超时
下面分析一下基于地址状态监控的方法如何能够防御SYN Flood攻击。

  1)对于一个伪造源地址的SYN报文,若源地址第一次出现,则源地址的状态为NEW状态,当监听到服务器的SYN+ACK报文,表明服务器已经为该源地址的连接请求建立了半连接。此时,监控程序代源地址发送一个ACK报文完成连接。这样,半连接队列中的半连接数不是很多。计时器开始计时,由于源地址是伪造的,所以不会收到ACK报文,超时后,监控程序发送RST数据包,服务器释放该连接,该源地址的状态转为BAD状态。之后,对于每一个来自该源地址的SYN报文,监控程序都会主动发送一个RST报文。
  2)对于一个合法的SYN报文,若源地址第一次出现,则源地址的状态为NEW状态,服务器响应请求,发送SYN+ACK报文,监控程序发送ACK报文,连接建立完毕。之后,来自客户端的ACK很快会到达,该源地址的状态转为GOOD状态。服务器可以很好的处理重复到达的ACK包。
从以上分析可以看出,基于监控的方法可以很好的防御SYN Flood攻击,而不影响正常用户的连接。
想说下的是第2种方法,,,发送RST数据包,""监控程序发送RST数据包,服务器释放该连接""先不说ip地址随机的状况,,由于目标地址不可以路由到达,主机岂不是要继续等待,还是发送rst包的时候,主机会释放这个半连接???
请熟悉tcp/ip的来讲讲咯!

TOP

[讨论]针对syn flood,怎么办?

SYN网关 防火墙收到客户端的SYN包时,直接转发给服务器;防火墙收到服务器的SYN/ACK包后,一方面将SYN/ACK包转发给客户端,另一方面以客户端的名义给服务器回送一个ACK包,完成TCP的三次握手,让服务器端由半连接状态进入连接状态。当客户端真正的ACK包到达时,有数据则转发给服务器,否则丢弃该包。由于服务器能承受连接状态要比半连接状态高得多,所以这种方法能有效地减轻对服务器的攻击。
被动式SYN网关 设置防火墙的SYN请求超时参数,让它远小于服务器的超时期限。防火墙负责转发客户端发往服务器的SYN包,服务器发往客户端的SYN/ACK包、以及客户端发往服务器的ACK包。这样,如果客户端在防火墙计时器到期时还没发送ACK包,防火墙则往服务器发送RST包,以使服务器从队列中删去该半连接。由于防火墙的超时参数远小于服务器的超时期限,因此这样能有效防止SYN Flood攻击。
SYN中继 防火墙在收到客户端的SYN包后,并不向服务器转发而是记录该状态信息然后主动给客户端回送SYN/ACK包,如果收到客户端的ACK包,表明是正常访问,由防火墙向服务器发送SYN包并完成三次握手。这样由防火墙做为代理来实现客户端和服务器端的连接,可以完全过滤不可用连接发往服务器。

TOP

[讨论]针对syn flood,怎么办?

上面所说的注册表选项在xp中并没有哦,
我所指的dos只是这个代码上所描述的攻击,,,大量伪造的ip的syn请求,,,且ip地址还有可能是随机的,,,问题是我们如何在自己的代码中加入这些功能,比如在xp下就没有这些选项,,
我想到一个简单的方案:
用一个原始套接字不断监听本地的网络连接,对对指定端口的syn请求进行记录,这时主机上的服务程序应该已经发送了ack/syn包了.那么设置一定的时间间隔(小于系统等待重发的时间),在设置的时间内,如果没有受到客户端的ack,,则发送一个rst给自己,源地址修改为那个请求的ip,从而使系统将半连接从队列中删除....
只是一个构想,,,还没有实现相关的代码,,大家说说可行性!!!!

TOP

[讨论]针对syn flood,怎么办?

前几天在网上看到一段代码,只是还要什么platform sdk..我不知道是怎么实现拦截数据包的,如果能在数据链路层拦下来的话,会好很多,这个代码我不能实现,所以不能研究他的拦截机制,至少会比上面所说的自己给自己发送rst包要好很多,创建一个ip列表,拦截所有源ip的包.我想将这两种方法结合到一起.先用rst包来处理,对于频率较大的ip地址和段,创建一个ip列表进行过滤... /* 利用操作系统提供的API编写防火墙. 该程序涉及到的API说明请访问微软的MSDN Library 代码在C++ Builder 5编译通过 如果您想和我交流请email:zzwinner@163.com */ #pragma hdrstop #pragma comment(lib,"Iphlpapi.lib") #include #include // 需要加载"iphlpapi.lib" //--------------------------------------------------------------------------- //#pragma argsused int main(int argc, char* argv[]) { // 一个创建网络包过滤接口 INTERFACE_HANDLE hInterface; PfCreateInterface(0, PF_ACTION_DROP,//PF_ACTION_FORWARD, PF_ACTION_DROP,//PF_ACTION_FORWARD, FALSE, TRUE, &hInterface); // 绑定需要网络包过滤的IP地址 BYTE localIp[] = {192,168,0,2}; PfBindInterfaceToIPAddress(hInterface, PF_IPV4, localIp); // 现在我们开始过滤HTTP协议的的接口 FILTER_HANDLE fHandle; // 填充过滤包的规则结构 PF_FILTER_DESCRIPTOR inFilter; inFilter.dwFilterFlags = FD_FLAGS_NOSYN; //一直添这个值 inFilter.dwRule = 0; //一直添这个值 inFilter.pfatType = PF_IPV4; //用 ipV4 地址 inFilter.SrcAddr = localIp; //设置本地IP地址 inFilter.SrcMask = "\xff\xff\xff\xff"; //设置本地子网掩码 inFilter.wSrcPort = FILTER_TCPUDP_PORT_ANY; //任意来源端口 inFilter.wSrcPortHighRange = FILTER_TCPUDP_PORT_ANY; inFilter.DstAddr = 0; //任意目标地址 inFilter.DstMask = 0; inFilter.wDstPort = 80; //目标端口 80(http 服务) inFilter.wDstPortHighRange = 80; inFilter.dwProtocol = FILTER_PROTO_TCP; // 过滤的协议 // 加入一个过滤接口 PfAddFiltersToInterface(hInterface, 1, &inFilter, 0, NULL, &fHandle); // 请在这设置一个调试断点,然后看看你的IE是否不能访问WEB页. :) // 移除过滤接口 PfRemoveFilterHandles(hInterface, 1, &fHandle); PfUnBindInterface(hInterface); PfDeleteInterface(hInterface); return 0; }

TOP

返回列表 回复 发帖