六.编写bash脚本进行防范(我的方法是统计同一个IP的状态包并处理)
#!/bin/sh
## 定义变量
MAX_TOTAL_SYN_RECV="1000"
MAX_PER_IP_SYN_RECV="20"
MARK="SYN_RECV"
PORT="80"
LOGFILE="/var/log/netstat_$MARK-$PORT"
LOGFILE_IP="/var/log/netstat_connect_ip.log"
DROP_IP_LOG="/var/log/netstat_syn_drop_ip.log"
## iptables初始化,拒绝非法包和不明状态的包,允许请求包和已经连接的包进入
iptables -F -t filter
iptables -A INPUT -p TCP ! --syn -m state --state NEW -j DROP
iptables -A INPUT -p ALL -m state --state INVALID -j DROP
iptables -A INPUT -p ALL -m state --state ESTABLISHED,RELATED -j ACCEPT
## 初始化变量
if [ -z $MARK ];then
MARK="LISTEN"
fi
if [ -z $PORT ];then
SPORT="tcp"
else
SPORT=":$PORT"
fi
######################## end
## 保存netstat结果到指定记录文件中便于分析
netstat -atun|grep $MARK|grep $SPORT 2>/dev/null >$LOGFILE
REPEAT_CONNECT_IP=`less $LOGFILE|awk '{print $5}'|cut -f1 -d ':'|sort|uniq -d |tee > $LOGFILE_IP`
## 如果IP记录文件不为空,则从原来的记录文件中读取记录并添加规则
if [ -s $DROP_IP_LOG ];then
for i in `less $DROP_IP_LOG|awk '{print $1}'`;do
/sbin/iptables -A INPUT -p ALL -s $i -j DROP
done
fi
for i in `less $LOGFILE_IP`;do
## 统计同一个IP在在的SYN_RECV状态
REPEAT_CONNECT_NUM=`grep $i $LOGFILE|wc -l`
## 如果超过了预设的同一个IP的连接数,就拒绝此IP的连接包进入
if [ $REPEAT_CONNECT_NUM -gt $MAX_PER_IP_SYN_RECV ];then
echo "$i $REPEAT_CONNECT_NUM" >> $DROP_IP_LOG
iptables -A INPUT -p ALL -s $i -j DROP
fi
done
## 统计所有状态为SYN_RECV状态的数据包,如果数量超过预设,就重置状态。
ALL_CONNECT=`uniq -u $LOGFILE|wc -l`
echo $ALL_CONNECT
## count repeat connections ,if the accout is large than default number,then drop packages
if [ $ALL_CONNECT -gt $MAX_TOTAL_SYN_RECV ];then
echo $ALL_CONNECT
exit
fi
课外知识:
这些记录会使得一些 log 统计分析软件在统计的时候出现错误警告,同时我们也不希望经常被这些扫描者所骚扰,于是就试着写了一个脚本,把 apache 的 log 中的这些 IP 地址读取出来,以便以后在做 Iptables 的时候可以使用。脚本代码:
######## Ver 0.2
# ==== NULL.ida扫描者IP排序脚本
#!/bin/sh
### null.ida_stat.sh, Ver. 0.2 2004/05/18 13:41:32 Kreny
LOG_FILE1='/usr/local/apache2/logs/www.domain1.com-access_log'
LOG_FILE2='/usr/local/apache2/logs/www.domain2.com-access_log'
# You can add more log files here.
#LOG_FILE3='/usr/local/apache2/logs/www.domain3.com-access_log'
#LOG_FILE4='/usr/local/apache2/logs/www.domain4.com-access_log'
#LOG_FILE5='/usr/local/apache2/logs/www.domain5.com-access_log'
FINAL_FILE='/home/user/public_html/log/ida.txt'
DATE=`date`
# Rank the IP addresses of NULL.IDA scanner
## Add your LOG_FILEs after the $LOG_FILE2
less $LOG_FILE1 $LOG_FILE2 | grep NULL.IDA | awk '{print $1}'| sort | uniq -c | sort -rn > $FINAL_FILE
echo "" >> $FINAL_FILE
echo "Last update:".$DATE >> $FINAL_FILE
# ========= 仅列出IP地址 (感谢 随风漂 指导)=====
#!/bin/sh
####### null.ida_stat.sh, Ver. 0.2 2004/05/18 13:41:32 Kreny #######
####### Only List the Scanner's IPs #######
LOG_FILE1='/usr/local/apache2/logs/www.domain1.com-access_log'
LOG_FILE2='/usr/local/apache2/logs/www.domain2.com-access_log'
# You can add more log files here.
#LOG_FILE3='/usr/local/apache2/logs/www.domain3.com-access_log'
#LOG_FILE4='/usr/local/apache2/logs/www.domain4.com-access_log'
#LOG_FILE5='/usr/local/apache2/logs/www.domain5.com-access_log'
FINAL_FILE='/home/user/public_html/log/ida_ip.txt'
DATE=`date`
awk '/NULL.IDA/{print $1}' $LOG_FILE1 $LOG_FILE2 | sort -u > $FINAL_FILE
echo "" >> $FINAL_FILE
echo "Last update:".$DATE >> $FINAL_FILE