大概原理就是对最新日志里面的客户端访问IP进行采样统计分析,然后对超出正常访问次数的IP进行屏蔽,如下面统计分析后的结果:
对最新1000条日志的客户端访问IP进行排序统计访问次数。比如第一个IP 219.128.20.68 1000条日志就有295条,访问肯定不正常
root@ubuntu134:# tail access.log -n 1000 |grep vote.php |awk {'print $2'} |sort |uniq -c |sort -nr
295 219.128.20.68
175 113.250.97.209
164 218.87.140.39
153 59.61.215.42
98 222.240.182.234
83 220.181.110.65
73 120.38.1.255
62 221.3.99.106
21 220.249.83.74
12 218.22.10.114
1 123.52.158.16
1 114.81.115.201
然后就是自动处理,如果1000条日志单IP超过50条就屏蔽掉
*/2 * * * * /usr/local/nginx/var/log/drop.sh
#!/bin/sh
cd /usr/local/nginx/var/log
tail access.log -n 1000 |grep vote.php |awk {'print $2'} |sort |uniq -c |sort -nr |awk '{if ($2!=null && $1>50) {print $2}}' > drop_ip.txt
for i in `cat drop_ip.txt`
do
/sbin/iptables -I INPUT -s $i -j DROP;
done
这shell 每几分钟执行一次,就可自动屏蔽那些不正常IP,相信大家都看的懂,下面是针对连接数屏蔽代码
#!/bin/sh
/bin/netstat -ant |grep 80 |awk '{print $5}' |awk -F : '{print $1}' |sort |uniq -c |sort -rn |grep -v -E '192.168|127.0' |awk '{if ($2!=null && $1>50) {print $2}}' > drop_ip.txt
for i in `cat drop_ip.txt`
do
/sbin/iptables -I INPUT -s $i -j DROP;
done
说下,grep -v -E '192.168|127.0' 也就是排除内网IP,免得把自己给屏蔽了,当然还可以加些自己的IP。
nginx限制ip并发数,也是说限制同一个ip同时连接服务器的数量
1.添加limit_zone
这个变量只能在http使用
vi /usr/local/nginx/conf/nginx.conf
limit_zone one $remote_addr 10m;
2.添加limit_conn
这个变量可以在http, server, location使用
我只限制一个站点,所以添加到server里面
vi /usr/local/nginx/conf/host/gaojinbo.com.conf
limit_conn one 10;
3.重启nginx
killall -HUP nginx
nginx 限速模块
参考:
关于limit_zone:http://wiki.nginx.org/NginxHttpLimitZoneModule
关于limit_rate和limit_conn:http://wiki.nginx.org/NginxHttpCoreModule
nginx可以通过HTTPLimitZoneModule和HTTPCoreModule两个组件来对目录进行限速。
http {
limit_zone one $binary_remote_addr 10m;
server {
location /download/ {
limit_conn one 1;
limit_rate 300k;
}
}
}
limit_zone,是针对每个IP定义一个存储session状态的容器。这个示例中定义了一个10m的容器,按照32bytes/session,可以处理320000个session。
limit_conn one 1;
限制每个IP只能发起一个并发连接。
limit_rate 300k;
对每个连接限速300k. 注意,这里是对连接限速,而不是对IP限速。如果一个IP允许两个并发连接,那么这个IP就是限速limit_rate×2。
加快回收time_wait的连接
sysctl -w net.ipv4.tcp_tw_reuse=1
sysctl -w net.ipv4.tcp_tw_recycle=1
net.ipv4.tcp_fin_timeout=30
#当KEEPALIVE起作用时,发送keepalive消息的频率,默认2小时,改为20分钟
net.ipv4.tcp_keepalive_time=1200
#开启SYN Cookies,当SYN等待列队溢出,启用cookies来处理,默认关闭,改为开启
net.ipv4.tcp_syncookies=1
#开启重用,允许将TIME-WAIT状态sockets重新用于新的TCP连接,默认关闭,改为开启
net.ipv4.tcp_tw_reuse=1
#启用TCP连接中TIME-WAIT sockets的快速回收,默认关闭,改为开启
net.ipv4.tcp_tw_recycle=1
#用户向外连接的端口范围,默认32768~61000,改为1024~65000
net.ipv4.ip_local_port_range=1024 65000
#表示SYN列队的长度,默认1024,改为8192,可容纳更多处于等待状态的连接
net.ipv4.tcp_max_syn_backlog=8192
#表示系统同时保持TIME-WAIT套接字的最大数量,如果超过将立即清除,默认180000,改为5000
net.ipv4.tcp_max_tw_buckets=5000
Procs
-r: 运行的和等待(CPU时间片)运行的进程数,这个值也可以判断是否需要增加CPU(长期大于1)
-b: 处于不可中断状态的进程数,常见的情况是由I/O引起的。
MEMORY
-swap:切换到交换内存上的内存(默认以KB为单位) 如果SWAP的值不为0,或者还比较大,比如超过100M了,但是SI,SO的值长期为0,这种情况我们可以不用担心,不会影响系统性能。
-free:p空闲的物理内存
- buff:作为buffer cache的内存,对块设备的读写进行缓冲
-cache:作为page cache的内存,文件系统的cache 如果cache的值大的时候,说明cache处的文件数多,如果频繁访问到的文件都能被cache处,那么磁盘的读IO bi会非常小。
SWAP
-si:交换内存使用,由磁盘调入内存
-so:交换内存使用,由内存调入磁盘 内存够用的时候,这2个值都是0,如果这2个值长期大于0时,系统性能会受到影响,磁盘IO和CPU资源都会被消耗。
我发现有些朋友看到空闲内存(FREE)很少的或接近于0时,就认为内存不够用了,实际上不能光看这一点,还要结合si,so,如果free很少,但是si,so也很少(大多时候是0),那么不用担心,系统性能这时不会受到影响的。
IO
-bi:从块设备读入的数据总量(读磁盘)(KB/S)
-bo:写入到块设备的数据总量(写磁盘)(KB/S) 随机磁盘读写的时候,这2个值越大(如超出1M),能看到CPU在IO等待的值也会越大
SYSTEM
--in:每秒产生的中断次数 --cs:每秒产生的上下文切换次数 上面2个值越大,会看到由内核消耗的CPU时间会越大
CPU
-us:用户进程消耗的CPU时间百分 us的值比较高时,说明用户进程消耗的CPU时间多,但是如果长期超50%的使用,那么我们就该考虑优化程序算法或者进行加速(比如PHP/PERL)
-sy:内核进程消耗的CPU时间百分比(sy的值高时,说明系统内核消耗的CPU资源多,这并不是良性表现,我们应该检查原因)
-wa:IO等待消耗的CPU时间百分比 wa的值高时,说明IO等待比较严重,这可能由于磁盘大量作随机访问造成,也有可能磁盘出现瓶颈(块操作)。
-id:CPU处于空闲状态时间百分比
情景分析: vmstat的输出哪些信息值得关注?
--proc r:运行的进程比较多,系统很繁忙
--IO bo:磁盘写的数据量稍大,如果大文件的写,10以内基本不用担心,如果是小文件2M以前基本正常,
--CPU us:持续大于50,服务高峰期可以接受
--CPU wa:稍微有些同 --CPU id:持续小于50,服务高峰期可以接受
TOP命令:
这个命令可以查看系统中运行的进程的状况,CPU使用状况,系统负载,内存使用等。它是检查系统进程运行状况最方便的工具了。它默认显示部分活动的进程,并按照进程使用CPU的多少排序,
top参数:
-D 不可中断休眠,通常是IO操作处的状态
-R 正在执行的或者处在等街待的进程队列中
-S 休眠中
-T 暂停刮起的
-Z 僵尸进程,进程执行完成,但由于其父进程没有销毁该进程,而被INIT进程接管进行销毁。
-W 没有使用物理内存,所占用的物理内存被切换到交换内存
----------------------
举例:安装一个半虚拟化客户机,512MB 内存,5G 磁盘,通过使用http提供的安装树,要求使用 text-only 模式。
# virt-install --paravirt --name rhel5u4 --ram 512 --file /var/lib/xen/images\/rhel5u4.img -file-size 6 --nographics --location http://192.168.0.254/rhel5u4
以下是一些安装命令的举例:
#virt-install --name rhel5u4 --ram 512 --file=/var/lib/libvirt/images/rhel5u4 \
.img --file-size=3 --vnc --cdrom=/var/lib/libvirt/images/rhel5u4.iso --network\ \network=default
#virt-install -p -n rhel5u4 -r 512 -f /var/lib/libvirt/images/rhel5u4.img -s 3 \ –vnc --cdrom=/var/lib/libvirt/images/rhel5u4 .iso -w network=default
#virt-install -p -n rhel5u4 -r 512 -f /var/lib/libvirt/images/rhel5u4.img -s 3\
–vnc -l http://192.168.0.254/rhel5u4 -w network=default
#virt-install -p -n rhel5u4 -r 512 -f /var/lib/libvirt/images/rhel5u4.img -s 3 \
–vnc --location=http://192.168.0.2/rhel5u4 -x ks=http://192.168.122.1/ks.cfg -w \
network=default
#virt-install -p -n rhel5u4 -r 512 -f /var/lib/libvirt/images/rhel5u4 .img -s 3 \
--vnc -l http://192.168.0.254/rhel5u4 ---extra-args='ks=http://192.168.122.1 \
ks.cfg' -w network=default
常用参数介绍:
-n NAME, --name=NAME 指定 Guest 名字
-r MEMORY, --ram=MEMORY 指定内存大小
-u UUID, --uuid=UUID 指定 uuid 号
可以使用 uuidgen 命令来产生 uuid:
# uuidgen
a89a3751-3555-4be5-8157-5e205ddba5bb
或者使用如下命令:
# echo 'import virtinst.util ; print\
virtinst.util.uuidToString(virtinst.util.randomUUID())' | python
4217ef56-b0d9-071d-6157-c98d0e6d240a
--vcpus=VCPUS 指定虚拟机的 CPU 数量
-p, --paravirt 指定客户机为半虚拟化 Guest
-f DISKFILE, --file=DISKFILE 虚拟机的虚拟磁盘,磁盘可以是文件、磁盘分区或者是
lvm。此选项用来指定虚拟磁盘的路径
-s DISKSIZE, --file-size=DISKSIZE 指定虚拟磁盘的大小,单位是 G;如果—file 指定
的文件路径不存在,并且—nonsparse 选项没有指
定,对这个文件不会预先分配存储空间。
-w NETWORK, --network=NETWORK NETWORK 有三种选择,bridge:BRIDGE ,
network:NAME 和 user
-c CDROM, --cdrom=CDROM 指定用于全虚拟化 Guest 的虚拟 CD,可以是一个 ISO 镜
像文件,也可以是一个 CDROM 设备,也可以是一个通
过 URL 可以访问和获取到的 boot.iso 镜像。如果将其忽
略,那么在—location 选项中必须指定 kernel 和 initrd
的位置,也可以使用—pxe 参数通过网络进行安装。
--pxe 使用 PXE boot 协议来加载初始化的 ramdisk 和 kernel,
以便于启动 Guset 段的安装进进程。如果没有指定—pxe,那么
就必须指定—cdrom 和--location 其中一个。
-l LOCATION, --location=LOCATION 指定 kernel 和 initrd 的安装源,这对于半虚拟化是
必须的。对于全虚拟化,要么使用--location 要么使用
--cdrom 来指定 ISO 或 CDROM 镜像。其必须符合下面的
四种格式:
DIRECTORY
nfs:host:/path
http://host/path
ftp://host/path
-x EXTRA, --extra-args=EXTRA 用来给加载的 kernel 和 initrd 提供额外的内核命令行参
数。
(跟详细的参数及使用方法详见 man virt-install)
XEN是目前Linux上的最佳的虚拟化解决方案,特别适合于服务器应用,如用于将多个服务器合并到一台物理服务器上,以节省运营成本(机房空间、电力消耗);或者是出于安全角度的考虑,需要将不同的应用进行分区,以便降低安全风险等。
名词:
完全虚拟化(Full Virtualization):full virtualized
半虚拟化(Para Virtualization):paravirtualized
查看CPU对虚拟化的支持程度:
Intel和AMD的半虚拟化支持标识 - PAE
# cat /proc/cpuinfo | grep flags
flags : fpu tsc msr pae mce cx8 apic mtrr mca cmov pat pse36 clflush dts acpi mmx fxsr sse sse2 ss nx constant_tsc pni ssse3
Intel全虚拟化支持标识 - VMX
# cat /proc/cpuinfo | grep flags
flags : fpu tsc msr pae mce cx8 apic mtrr mca cmov pat pse36 clflush dts acpi mmx fxsr sse sse2 ss ht tm pbe nx lm constant_tsc up pni monitor ds_cpl vmx est tm2 cx16 xtpr lahf_lm
AMD全虚拟化支持标识 - SVM
# cat /proc/cpuinfo | grep flags
flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush mmx fxsr sse sse2 ht syscall nx mmxext fxsr_opt rdtscp lm 3dnowext 3dnow pni cx16 lahf_lm cmp_legacy svm extapic cr8legacy 3dnowprefetch ts fid vid ttp tm stc 100mhzsteps
XEN的运行环境:Domain-0与Domain-U
Domain-0即虚拟母机或称为宿主机,与Linux主机为同一系统,以XEN的Linux内核启动的主机,负责管理和控制客户机。
Domain-U即虚拟客户机或称VPS,在Domain-0上可以建立多个虚拟客户机。
Domain-0与Domain-U的区别就是Domain-0是虚拟机,Domain-U是虚拟机上的操作系统。用过Windows上VMWare的可以把Domain-0理解为VMWare软件,Domain-U则是运行在VMWare上的操作系统。
XEN的运行方式:
XEN分成多个层级 (layer) 执行。它将Linux的核心修改后,再使用修改过的核心开机,而开机后先载入XEN的监控器 (Hypervisor) , 并且启动第一个操作系统,称为domain-0。在Xen上面所谓的一个domain就是指一个虚拟机。
Domain-0之所以要先被载入是因为Domain-0含有其他虚拟机启动所必须的控制指令,并且domain-0也是控制虚拟装置的重要主控系统。在domain-0上最重要的就是一个xend的常住进程,其他的domain都是由这个xend来管理的。至於命名方面,除了domain-0之外的其他虚拟机就依序被称为domain-1, domain-2等等, 我们统称为domain-U。
Domain-0是很重要的,因为它直接控制Xen的监控器(Hypervisor),而且掌握了真实的Linux驱动程序 (drivers)。而其他的虚拟机(domain-U)则是透过Xen监控器来与真实的硬件以及domain-0进行交互。为了让domain-0能够与Xen结合,我们必须要修改domain-0的核心才能顺利运行。并且需要使用domain-0的核心来开机才可以。domain-0是所有虚拟机的基础,所以它可以尽量简洁,其他的个别服务则可以放置到不同的domain中。
xend可以管理domain-0与其他domain之间的启动与交互,提供一个终端控制 (console) 界面来让 domain-0 登入其他的 domain。
XEN的安装:
在CentOS(5.4)上安装XEN
首先确认XEN是否已经安装
# yum grouplist
如果Virtualization位于Available Groups而非Installed Groups里则说明XEN并未安装在系统中
安装命令有两种,任选其一,效果是一样的
安装方式一
# yum -y install xen <开始安装XEN>
安装方式二
# yum groupinstall Virtualization -y <开始安装XEN>
安装完成后编辑/etc/grub.conf修改开机启动顺序,将default=1修改为改default=0,以XEN的Linux核心为默认启动系统
安装完成,重启。
运行
# xm list
Name ID Mem(MiB) VCPUs State Time(s)
Domain-0 0 491 2 r----- 7797.5
显示以上内容表示安装无误,Domain-0正常启动运行。
安装客户机 - Domain-U:
半虚拟化安装客户机操作系统CentOS(5.4)
首先为虚拟机创建磁盘并进行格式化
创建磁盘:
# dd if=/dev/zero of=/home/vm01 bs=4096 seek=1024k count=0
参数说明:
if 文件输入位置
of 创建磁盘文件
bs 设置磁盘大小
seek 描述 bs 每一块的单位
count 复制的块数
将磁盘文件格式化为ext3文件格式:
# mkfs -t ext3 /home/vm01
关闭防火墙使用NFS作为安装源:
一般防火墙是默认打开的,如果防火墙已经打开且开放了NFS服务则不需要关闭防火墙
# /etc/init.d/iptables stop <关闭防火墙>
挂载操作系统:
# mkdir /tmp/os
# mount /dev/cdrom /tmp/os
启动NFS服务:
# service nfs start
开放NFS服务的目录:
编辑 /etc/exports 添加一行 /tmp/os 192.168.1.*(ro) ,注意根据个人情况修改IP
激活
# exportfs -rv
开始安装:
#virt-install -n domain01 -r 512 --vcpus=2 -p -f /home/vm01 --nographics -l /tmp/os
进入安装选项->选择语言->选择NFS方式安装->选择IPV4 DHCP ->输入主机ip[192.168.1.1]->输入目录[/tmp/os]
选择TEXT安装模式,以后的安装过程和正常安装CentOS没有区别
安装程序参数列表:
-n 设置虚拟主机名
-r 设置虚拟主机内存 这里设置的是512M
--vcpus 设置cpu个数
-f 设置虚拟主机的磁盘位置
--nographics 不使用图形界面安装
-l 设置系统安装源的位置
-p 半虚拟化客户机
-c 用于全虚拟化的虚拟CD,可以是一个ISO镜像文件或CDROM设备或URL可以访问的boot.iso镜像
将虚拟主机加入开机自动启动:
# chkconfig --add xendomains
# ln -s /etc/xen/domain01 /etc/xen/auto/domain01 <放在auto目录中的虚拟主机会开机自启动>
xendomains服务器的启动/停止/重启/状态查询命令:
一般的情况下,xend服务器启动了,xendomains也会自动启动。
# /etc/init.d/xend start 启动xend
# /etc/init.d/xend stop 停止xend
# /etc/init.d/xend restart 重启xend
# /etc/init.d/xend status 查看xend状态
# /etc/init.d/xendomains start 启动xendomains
# /etc/init.d/xendomains stop 停止xendomains
# /etc/init.d/xendomains restart 重启xendomains
# /etc/init.d/xendomains status 查看xendomains状态
XEN控制虚拟主机的常用命令:
虚拟主机列表
# xm list
关闭虚拟主机,domain01为虚拟主机名,也可用id代替
# xm shutdown domain01
启动一个虚拟主机,domain01为虚拟主机名
# xm create domain01
通过-c 参数调用 console 启动并跟踪虚拟主机状态
# xm create domain01 -c
显示虚拟机的控制台
# xm console domain01
重起虚拟机
# xm reboot domain01
销毁并立即停止虚拟机,类似关掉电源一样关机
# xm destroy domain01
存储正在运行的虚拟操作系统的状态
# xm save domain01 <File>
唤醒虚拟操作系统
# xm restore <File>
暂停正在运行的虚拟操作系统
# xm pause domain01
激活停止的虚拟操作系统
# xm unpause domain01
调整虚拟平台/虚拟操作系统的占用内存
# xm mem-set domain01 128
调整虚拟平台及虚拟操作系统的虚拟CPU个数
# xm vcpu-set domain01 2
查看虚拟系统运行的状态
# xm top
或
# xentop
常见错误描述及解决办法
通过http或NFS安装客户机操作系统出现 Unable to retrieve 错误:....
多数原因是防火墙造成的,如果使用http安装方式时可以先停止防火墙,也可以采用以下方式解决
通过/etc/init.d/iptables status命令查询是否有打开80端口
或通过 sudo netstat -antup 命令查看网络端口状态
修改vi /etc/sysconfig/iptables添加以下代码开放80端口:
-A RH-Firewall-1-INPUT -p tcp -m state --state NEW -m tcp --dport 80 -j ACCEPT
执行 /etc/init.d/iptables restart 激活操作
出现类似下面的错误:
POST operation failed: xend_post: error from xen daemon: (xend.err 'Error creating domain: I need 262144 KiB, but dom0_min_mem is 262144 and shrinking to 262144 KiB would leave only 244672 KiB free.')
说明新增的虚拟主机内存设置过高了,需要调小些