Let's Go!

发布新日志

  • java取版本号

    2015-07-14 14:39:55


    java取版本号

    需要注意的是
    java -version的输出结果不在标准输出,在标准错误输出,
    所以需要将标准错误输出重定向到标准输出,然后进行处理


    $ java -version 2>&1 | awk '/version/{print $3}'
    这样更简单



    ------------------------------------------------------
    java -version 2>&1 | grep version | awk '{print $3}'
    "1.7.0_55"


    java -version 2>&1 | awk -F\" '/version/{print $2}'
    1.7.0_67
  • How many virtual users do I need? 计算需要的vuser

    2015-05-06 12:01:24



    基本公式:
    --------
    English:
    Total Transations = TPS * Vuser
    ==>
    Vuser = Total Transations / TPS
    =====================================
    中文:
    高峰时段的访问量 = Vuser数量 * 访问频率(由平均访问时长计算)
    ==>
    Vuser数量 = 高峰时段的访问量 / 访问频率(由平均访问时长计算)
    ------------------------------------
    说明:访问频率是平均访问时长的倒数
    ------------------------------------
    比如:
    Peak visit rate (visits/hour)  : 20000

    Average visit length (minutes/visit) : 3

    计算 Virtual Users required ?
    ----------------------------------
    访问频率 =  1 / (3 minutes/visit) = 1/3 visit/minutes = 20 visits/hour

    Vuser =  (20000 visits/hour ) / (20 visits/hour) = 1000

    ----------------------------------

    参考:
    http://www.webperformance.com/library/tutorials/CalculateNumberOfLoadtestUsers/





  • Loadrunner Licese 支持6.5万用户 global类型 AEACFSJI-YJKJKJJKEJIJD-BCLBR

    2012-09-24 16:26:38

    Loadrunner Licese 支持6.5万用户 global类型

    AEACFSJI-YJKJKJJKEJIJD-BCLBR



    http://www.51testing.com/?uid-116228-action-viewspace-itemid-238362

  • 获取web前端性能数据

    2012-06-19 23:47:48



    通过Java程序获取Dynatrace数据

    http://www.taobaotest.com/blogs/qa?bid=15540


    通过java程序获取Yslow上传数据

    http://www.taobaotest.com/blogs/qa?bid=15532
  • EXTJS 同步和异步请求

    2012-03-28 11:24:39

    ext3.0之前都是这样来提交:
    var responsea = Ext.lib.Ajax.getConnectionObject().conn; 
    responsea.open("POST", your url,false);  //"GET"
    responsea.send(null);
    alert("返回来的数据为:"+responsea.responseText);


    ext3之后好像不能这样提交了,这时候需要引入一个新的js文件,叫做ext-basex.js,

    可以在这里下载:http://lihao130999580.javaeye.com/blog/700880

    具体写法很好看,跟一直以来的异步提交方式很相像:
    Ext.Ajax.request({
        url: your url,
        method: 'post',    //'get' //params: 配置提交的参数
        async :  false,//同步请求数据

        //这个是关键,默认是true,否则只是请求成功就向下执行

        success: function(result, request) { 
            alert(result.responseText);

        },
        failure: function(result, request) {
            Ext.MessageBox.alert('系统异常', '请求数据失败!');
        }

    });


    转自:

    http://www.cnblogs.com/fireicesion/archive/2010/11/30/1891796.html

    另一种方式:使用callback函数:
        var 全局变量 
        var requestConfig ={
            url:'your URL',
            callback : function(options,success,response){
                var res = response.responseText;
                 //返回值进行处理
                 //给全局变量赋值
            }
        }

    Ext.Ajax.request(requestConfig) ;
    //继续处理 全局变量


    其他:
    http://exceptioneye.iteye.com/blog/1112958
    http://exceptioneye.iteye.com/blog/1218353
    http://holdbelief.iteye.com/blog/353281
  • 实用小工具

    2012-03-14 10:54:37


    http://www.xdowns.com/soft/softdown.asp?softid=48355


    ALTRun
    程序快速入口设置

    桌面管理
    http://www.xdowns.com/soft/6/15/2010/Soft_60403.html
  • TortoiseSVN下载

    2012-02-22 11:08:14

     
    官方下载页面:
    http://tortoisesvn.net/downloads.html
    下载
        1.)TortoiseSVN-1.7.5.22551-win32-svn-1.7.3.msi (TortoiseSVN安装程序)
        2.)LanguagePack_1.7.5.22551-win32-zh_CN.msi (TortoiseSVN语言包)
       先安装主程序(可能会重启计算机),再安装语言包。
       之后点击:开始→程序→TortoiseSVN→Settings 打开设置界面,在第一项常规设置界面中,将程序语言换成:中文(简体)即可汉化。具体使用说明请参照TortoiseSVN的帮助文档。^_^
  • Linux 性能监控分析(二) (转)

    2011-12-14 18:41:25



    3.1  vmstat

    # vmstat 1procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu------ r  b   swpd   free   buff  cache   si   so    bi    bo   in   cs us sy id wa st 0  3 252696   2432    268   7148 3604 2368  3608  2372  288  288  0  0 21 78  1 0  2 253484   2216    228   7104 5368 2976  5372  3036  930  519  0  0  0 100  0 0  1 259252   2616    128   6148 19784 18712 19784 18712 3821 1853  0  1  3 95  1 1  2 260008   2188    144   6824 11824 2584 12664  2584 1347 1174 14  0  0 86  0 2  1 262140   2964    128   5852 24912 17304 24952 17304 4737 2341 86 10  0  0  4 部分参数说明:(1).      swpd,已使用的 SWAP 空间大小,KB 为单位;

    (2).      free,可用的物理内存大小,KB 为单位;

    (3).      buff,物理内存用来缓存读写操作的 buffer 大小,KB 为单位;

    (4).      cache,物理内存用来缓存进程地址空间的 cache 大小,KB 为单位;

    (5).      si,数据从 SWAP 读取到 RAM(swap in)的大小,KB 为单位;

    (6).      so,数据从 RAM 写到 SWAP(swap out)的大小,KB 为单位;

    (7).      bi,磁盘块从文件系统或 SWAP 读取到 RAM(blocks in)的大小,block 为单位;

    (8).      bo,磁盘块从 RAM 写到文件系统或 SWAP(blocks out)的大小,block 为单位;

    上面是一个频繁读写交换区的例子,可以观察到以下几点:

    (1).      物理可用内存 free 基本没什么显著变化,swapd 逐步增加,说明最小可用的内存始终保持在 256MB(物理内存大小) * 10% = 2.56MB 左右,当脏页达到10%的时候(vm.dirty_background_ratio = 10)就开始大量使用 swap;

    (2).      buff 稳步减少说明系统知道内存不够了,kwapd 正在从 buff 那里借用部分内存;

    (3).      kswapd 持续把脏页面写到 swap 交换区(so),并且从 swapd 逐渐增加看出确实如此。根据上面讲的 kswapd 扫描时检查的三件事,如果页面被修改了,但不是被文件系统修改的,把页面写到 swap,所以这里 swapd 持续增加。

    四. IO

           磁盘通常是计算机最慢的子系统,也是最容易出现性能瓶颈的地方,因为磁盘离 CPU 距离最远而且 CPU 访问磁盘要涉及到机械操作,比如转轴、寻轨等。访问硬盘和访问内存之间的速度差别是以数量级来计算的,就像1天和1分钟的差别一样。要监测 IO 性能,有必要了解一下基本原理和 Linux 是如何处理硬盘和内存之间的 IO 的。

    4.1 内存页

    在第三节Memory中提到了内存和硬盘之间的 IO 是以页为单位来进行的,在 Linux 系统上1页的大小为 4K。可以用以下命令查看系统默认的页面大小:

    $ /usr/bin/time -v date

           ...

           Page size (bytes): 4096

           ...

    4.2 缺页中断

           Linux 利用虚拟内存极大的扩展了程序地址空间,使得原来物理内存不能容下的程序也可以通过内存和硬盘之间的不断交换(把暂时不用的内存页交换到硬盘,把需要的内存页从硬盘读到内存)来赢得更多的内存,看起来就像物理内存被扩大了一样。事实上这个过程对程序是完全透明的,程序完全不用理会自己哪一部分、什么时候被交换进内存,一切都有内核的虚拟内存管理来完成。当程序启动的时候,Linux 内核首先检查 CPU 的缓存和物理内存,如果数据已经在内存里就忽略,如果数据不在内存里就引起一个缺页中断(Page Fault),然后从硬盘读取缺页,并把缺页缓存到物理内存里。缺页中断可分为主缺页中断(Major Page Fault)和次缺页中断(Minor Page Fault),要从磁盘读取数据而产生的中断是主缺页中断;数据已经被读入内存并被缓存起来,从内存缓存区中而不是直接从硬盘中读取数据而产生的中断是次缺页中断。

           上面的内存缓存区起到了预读硬盘的作用,内核先在物理内存里寻找缺页,没有的话产生次缺页中断从内存缓存里找,如果还没有发现的话就从硬盘读取。很显然,把多余的内存拿出来做成内存缓存区提高了访问速度,这里还有一个命中率的问题,运气好的话如果每次缺页都能从内存缓存区读取的话将会极大提高性能。要提高命中率的一个简单方法就是增大内存缓存区面积,缓存区越大预存的页面就越多,命中率也会越高。

           下面的 time 命令可以用来查看某程序第一次启动的时候产生了多少主缺页中断和次缺页中断:

    $ /usr/bin/time -v date        ...        Major (requiring I/O) page faults: 1        Minor (reclaiming a frame) page faults: 260        ... 4.3  File Buffer Cache

           从上面的内存缓存区(也叫文件缓存区 File Buffer Cache)读取页比从硬盘读取页要快得多,所以 Linux 内核希望能尽可能产生次缺页中断(从文件缓存区读),并且能尽可能避免主缺页中断(从硬盘读),这样随着次缺页中断的增多,文件缓存区也逐步增大,直到系统只有少量可用物理内存的时候 Linux 才开始释放一些不用的页。我们运行 Linux 一段时间后会发现虽然系统上运行的程序不多,但是可用内存总是很少,这样给大家造成了 Linux 对内存管理很低效的假象,事实上 Linux 把那些暂时不用的物理内存高效的利用起来做预存(内存缓存区)呢。下面是一台 Sun 服务器上的物理内存和文件缓存区的情况:

    $ cat /proc/meminfoMemTotal:      8182776 kBMemFree:       3053808 kBBuffers:        342704 kBCached:        3972748 kB       这台服务器总共有 8GB 物理内存(MemTotal),3GB 左右可用内存(MemFree),343MB 左右用来做磁盘缓存(Buffers),4GB 左右用来做文件缓存区(Cached),可见 Linux 真的用了很多物理内存做 Cache,而且这个缓存区还可以不断增长。

    4.4 页面类型

    Linux 中内存页面有三种类型:

    (1).      Read pages,只读页(或代码页),那些通过主缺页中断从硬盘读取的页面,包括不能修改的静态文件、可执行文件、库文件等。当内核需要它们的时候把它们读到内存中,当内存不足的时候,内核就释放它们到空闲列表,当程序再次需要它们的时候需要通过缺页中断再次读到内存。

    (2).      Dirty pages,脏页,指那些在内存中被修改过的数据页,比如文本文件等。这些文件由 pdflush 负责同步到硬盘,内存不足的时候由 kswapd 和 pdflush 把数据写回硬盘并释放内存。

    (3).      Anonymous pages,匿名页,那些属于某个进程但是又和任何文件无关联,不能被同步到硬盘上,内存不足的时候由 kswapd 负责将它们写到交换分区并释放内存。

    4.5  IO’s Per Second(IOPS)

           每次磁盘 IO 请求都需要一定的时间,和访问内存比起来这个等待时间简直难以忍受。在一台 2001 年的典型 1GHz PC 上,磁盘随机访问一个 word 需要 8,000,000 nanosec = 8 millisec,顺序访问一个 word 需要 200 nanosec;而从内存访问一个 word 只需要 10 nanosec.(数据来自:Teach Yourself Programming in Ten Years)这个硬盘可以提供 125 次 IOPS(1000 ms / 8 ms)。

    4.6  顺序 IO 和 随机 IO

           IO 可分为顺序 IO 和 随机 IO 两种,性能监测前需要弄清楚系统偏向顺序 IO 的应用还是随机 IO 应用。

           (1)顺序 IO 是指同时顺序请求大量数据,比如数据库执行大量的查询、流媒体服务等,顺序 IO 可以同时很快的移动大量数据。可以这样来评估 IOPS 的性能,用每秒读写 IO 字节数除以每秒读写 IOPS 数,rkB/s 除以 r/s,wkB/s 除以 w/s. 下面显示的是连续2秒的 IO 情况,可见每次 IO 写的数据是增加的(45060.00 / 99.00 = 455.15 KB per IO,54272.00 / 112.00 = 484.57 KB per IO)。

           相对随机 IO 而言,顺序 IO 更应该重视每次 IO 的吞吐能力(KB per IO):

    $ iostat -kx 1avg-cpu:  %user   %nice %system %iowait  %steal   %idle           0.00    0.00    2.50   25.25    0.00   72.25 Device:  rrqm/s   wrqm/s   r/s   w/s    rkB/s    wkB/s avgrq-sz avgqu-sz   await  svctm  %utilsdb       24.00 19995.00 29.00 99.00  4228.00 45060.00   770.12    45.01  539.65   7.80  99.80 avg-cpu:  %user   %nice %system %iowait  %steal   %idle           0.00    0.00    1.00   30.67    0.00   68.33 Device:  rrqm/s   wrqm/s   r/s   w/s    rkB/s    wkB/s avgrq-sz avgqu-sz   await  svctm  %utilsdb        3.00 12235.00  3.00 112.00   768.00 54272.00   957.22   144.85  576.44   8.70 100.10       (2)随机 IO 是指随机请求数据,其 IO 速度不依赖于数据的大小和排列,依赖于磁盘的每秒能 IO 的次数,比如 Web 服务、Mail 服务等每次请求的数据都很小,随机 IO 每秒同时会有更多的请求数产生,所以磁盘的每秒能 IO 多少次是关键。

    $ iostat -kx 1avg-cpu:  %user   %nice %system %iowait  %steal   %idle           1.75    0.00    0.75    0.25    0.00   97.26 Device:  rrqm/s   wrqm/s   r/s   w/s    rkB/s    wkB/s avgrq-sz avgqu-sz   await  svctm  %utilsdb        0.00    52.00  0.00 57.00     0.00   436.00    15.30     0.03    0.54   0.23   1.30 avg-cpu:  %user   %nice %system %iowait  %steal   %idle           1.75    0.00    0.75    0.25    0.00   97.24 Device:  rrqm/s   wrqm/s   r/s   w/s    rkB/s    wkB/s avgrq-sz avgqu-sz   await  svctm  %utilsdb        0.00    56.44  0.00 66.34     0.00   491.09    14.81     0.04    0.54   0.19   1.29       按照上面的公式得出:436.00 / 57.00 = 7.65 KB per IO,491.09 / 66.34 = 7.40 KB per IO. 与顺序 IO 比较发现,随机 IO 的 KB per IO 小到可以忽略不计,可见对于随机 IO 而言重要的是每秒能 IOPS 的次数,而不是每次 IO 的吞吐能力(KB per IO)。

    4.7 SWAP

           当系统没有足够物理内存来应付所有请求的时候就会用到 swap 设备,swap 设备可以是一个文件,也可以是一个磁盘分区。不过要小心的是,使用 swap 的代价非常大。如果系统没有物理内存可用,就会频繁 swapping,如果 swap 设备和程序正要访问的数据在同一个文件系统上,那会碰到严重的 IO 问题,最终导致整个系统迟缓,甚至崩溃。swap 设备和内存之间的 swapping 状况是判断 Linux 系统性能的重要参考,我们已经有很多工具可以用来监测 swap 和 swapping 情况,比如:top、cat /proc/meminfo、vmstat 等:

    $ cat /proc/meminfoMemTotal:      8182776 kBMemFree:       2125476 kBBuffers:        347952 kBCached:        4892024 kBSwapCached:        112 kB...SwapTotal:     4096564 kBSwapFree:      4096424 kB... $ vmstat 1procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu------ r  b   swpd   free   buff  cache   si   so    bi    bo   in   cs us sy id wa st 1  2 260008   2188    144   6824 11824 2584 12664  2584 1347 1174 14  0  0 86  0 2  1 262140   2964    128   5852 24912 17304 24952 17304 4737 2341 86 10  0  0五. network

           网络的监测是所有 Linux 子系统里面最复杂的,有太多的因素在里面,比如:延迟、阻塞、冲突、丢包等,更糟的是与 Linux 主机相连的路由器、交换机、无线信号都会影响到整体网络并且很难判断是因为 Linux 网络子系统的问题还是别的设备的问题,增加了监测和判断的复杂度。现在我们使用的所有网卡都称为自适应网卡,意思是说能根据网络上的不同网络设备导致的不同网络速度和工作模式进行自动调整。我们可以通过 ethtool 工具来查看网卡的配置和工作模式:

    # /sbin/ethtool eth0Settings for eth0:        Supported ports: [ TP ]        Supported link modes:   10baseT/Half 10baseT/Full                                100baseT/Half 100baseT/Full                                1000baseT/Half 1000baseT/Full        Supports auto-negotiation: Yes        Advertised link modes:  10baseT/Half 10baseT/Full                                100baseT/Half 100baseT/Full                                1000baseT/Half 1000baseT/Full        Advertised auto-negotiation: Yes        Speed: 100Mb/s        Duplex: Full        Port: Twisted Pair        PHYAD: 1        Transceiver: internal        Auto-negotiation: on        Supports Wake-on: g        Wake-on: g        Current message level: 0x000000ff (255)        Link detected: yes       上面给出的例子说明网卡有 10baseT,100baseT 和 1000baseT 三种选择,目前正自适应为 100baseT(Speed: 100Mb/s)。可以通过 ethtool 工具强制网卡工作在 1000baseT 下:

    # /sbin/ethtool -s eth0 speed 1000 duplex full autoneg off 5.1  iptraf

           两台主机之间有网线(或无线)、路由器、交换机等设备,测试两台主机之间的网络性能的一个办法就是在这两个系统之间互发数据并统计结果,看看吞吐量、延迟、速率如何。iptraf 就是一个很好的查看本机网络吞吐量的好工具,支持文字图形界面,很直观。下面图片显示在 100 mbps 速率的网络下这个 Linux 系统的发送传输率有点慢,Outgoing rates 只有 66 mbps.

    # iptraf -d eth05.2  netperf

           netperf 运行在 client/server 模式下,比 iptraf 能更多样化的测试终端的吞吐量。先在服务器端启动 netserver:

    # netserverStarting netserver at port 12865Starting netserver at hostname 0.0.0.0 port 12865 and family AF_UNSPEC然后在客户端测试服务器,执行一次持续10秒的 TCP 测试:

    # netperf -H 172.16.38.36 -l 10TCP STREAM TEST from 0.0.0.0 (0.0.0.0) port 0 AF_INET to 172.16.38.36 (172.16.38.36) port 0 AF_INETRecv   Send    SendSocket Socket  Message  ElapsedSize   Size    Size     Time     Throughputbytes  bytes   bytes    secs.    10^6bits/sec    87380  16384  16384    10.32      93.68       从以上输出可以看出,网络吞吐量在 94mbps 左右,对于 100mbps 的网络来说这个性能算的上很不错。上面的测试是在服务器和客户端位于同一个局域网,并且局域网是有线网的情况,你也可以试试不同结构、不同速率的网络,比如:网络之间中间多几个路由器、客户端在 wi-fi、VPN 等情况。

           netperf 还可以通过建立一个 TCP 连接并顺序地发送数据包来测试每秒有多少 TCP 请求和响应。下面的输出显示在 TCP requests 使用 2K 大小,responses 使用 32K 的情况下处理速率为每秒243:

     # netperf -t TCP_RR -H 172.16.38.36 -l 10 -- -r 2048,32768TCP REQUEST/RESPONSE TEST from 0.0.0.0 (0.0.0.0) port 0 AF_INET to 172.16.38.36 (172.16.38.36) port 0 AF_INETLocal /RemoteSocket Size   Request  Resp.   Elapsed  Trans.Send   Recv   Size     Size    Time     Ratebytes  Bytes  bytes    bytes   secs.    per sec    16384  87380  2048     32768   10.00     243.0316384  87380 5.3  iperf

           iperf 和 netperf 运行方式类似,也是 server/client 模式,先在服务器端启动 iperf:

    # iperf -s -D------------------------------------------------------------Server listening on TCP port 5001TCP window size: 85.3 KByte (default)------------------------------------------------------------Running Iperf Server as a daemonThe Iperf daemon process ID : 5695       然后在客户端对服务器进行测试,客户端先连接到服务器端(172.16.38.36),并在30秒内每隔5秒对服务器和客户端之间的网络进行一次带宽测试和采样:

    # iperf -c 172.16.38.36 -t 30 -i 5------------------------------------------------------------Client connecting to 172.16.38.36, TCP port 5001TCP window size: 16.0 KByte (default)------------------------------------------------------------[  3] local 172.16.39.100 port 49515 connected with 172.16.38.36 port 5001[ ID] Interval       Transfer     Bandwidth[  3]  0.0- 5.0 sec  58.8 MBytes  98.6 Mbits/sec[ ID] Interval       Transfer     Bandwidth[  3]  5.0-10.0 sec  55.0 MBytes  92.3 Mbits/sec[ ID] Interval       Transfer     Bandwidth[  3] 10.0-15.0 sec  55.1 MBytes  92.4 Mbits/sec[ ID] Interval       Transfer     Bandwidth[  3] 15.0-20.0 sec  55.9 MBytes  93.8 Mbits/sec[ ID] Interval       Transfer     Bandwidth[  3] 20.0-25.0 sec  55.4 MBytes  92.9 Mbits/sec[ ID] Interval       Transfer     Bandwidth[  3] 25.0-30.0 sec  55.3 MBytes  92.8 Mbits/sec[ ID] Interval       Transfer     Bandwidth[  3]  0.0-30.0 sec    335 MBytes  93.7 Mbits/sec 5.4  tcpdump 和 tcptrace

           tcmdump 和 tcptrace 提供了一种更细致的分析方法,先用 tcpdump 按要求捕获数据包把结果输出到某一文件,然后再用 tcptrace 分析其文件格式。这个工具组合可以提供一些难以用其他工具发现的信息:

    # /usr/sbin/tcpdump -w network.dmptcpdump: listening on eth0, link-type EN10MB (Ethernet), capture size 96 bytes511942 packets captured511942 packets received by filter0 packets dropped by kernel # tcptrace network.dmp1 arg remaining, starting with 'network.dmp'Ostermann's tcptrace -- version 6.6.7 -- Thu Nov  4, 2004 511677 packets seen, 511487 TCP packets tracedelapsed wallclock time: 0:00:00.510291, 1002714 pkts/sec analyzedtrace file elapsed time: 0:02:35.836372TCP connection info:  1: zaber:54581 - boulder:111 (a2b)                   6>    5<  (complete)  2: zaber:833 - boulder:32774 (c2d)                   6>    5<  (complete)  3: zaber:pcanywherestat - 172.16.39.5:53086 (e2f)    2>    3<  4: zaber:716 - boulder:2049 (g2h)                  347>  257<  5: 172.16.39.100:58029 - zaber:12865 (i2j)           7>    5<  (complete)  6: 172.16.39.100:47592 - zaber:36814 (k2l)        255380> 255378<  (reset)  7: breakpoint:45510 - zaber:7012 (m2n)               9>    5<  (complete)  8: zaber:35813 - boulder:111 (o2p)                   6>    5<  (complete)  9: zaber:837 - boulder:32774 (q2r)                   6>    5<  (complete) 10: breakpoint:45511 - zaber:7012 (s2t)               9>    5<  (complete) 11: zaber:59362 - boulder:111 (u2v)                   6>    5<  (complete) 12: zaber:841 - boulder:32774 (w2x)                   6>    5<  (complete) 13: breakpoint:45512 - zaber:7012 (y2z)               9>    5<  (complete)       tcptrace 功能很强大,还可以通过过滤和布尔表达式来找出有问题的连接,比如,找出转播大于100 segments 的连接:

    # tcptrace -f'rexmit_segs>100' network.dmp如果发现连接 #10 有问题,可以查看关于这个连接的其他信息:

    # tcptrace -o10 network.dmp下面的命令使用 tcptrace 的 slice 模式,程序自动在当前目录创建了一个 slice.dat 文件,这个文件包含了每隔15秒的转播信息:

    # tcptrace -xslice network.dmp # cat slice.datdate                segs    bytes  rexsegs rexbytes      new   active--------------- -------- -------- -------- -------- -------- --------16:58:50.244708    85055  4513418        0        0        6        616:59:05.244708   110921  5882896        0        0        0        216:59:20.244708   126107  6697827        0        0        1        316:59:35.244708   151719  8043597        0        0        0        216:59:50.244708    37296  1980557        0        0        0        317:00:05.244708       67     8828        0        0        2        317:00:20.244708      149    22053        0        0        1        217:00:35.244708       30     4080        0        0        0        117:00:50.244708       39     5688        0        0        0        117:01:05.244708       67     8828        0        0        2        317:01:11.081080       37     4121        0        0        1        3

    详细出处参考:http://www.jb51.net/LINUXjishu/34607.html


  • Linux 性能监控分析(一) (转)

    2011-12-14 18:39:35

    Linux 性能监控分析



    详细出处参考:http://www.jb51.net/LINUXjishu/34607.html


           系统由若干子系统构成,通常修改一个子系统有可能影响到另外一个子系统,甚至会导致整个系统不稳定、崩溃。所以说优化、监测、测试通常是连在一起的,而且是一个循环而且长期的过程,通常监测的子系统有以下这些:

    (1).      CPU

    (2).      Memory

    (3).      IO

    (4).      Network

           这些子系统互相依赖,了解这些子系统的特性,监测这些子系统的性能参数以及及时发现可能会出现的瓶颈对系统优化很有帮助。

    1.1  应用类型

           不同的系统用途也不同,要找到性能瓶颈需要知道系统跑的是什么应用、有些什么特点,比如 web server 对系统的要求肯定和 file server 不一样,所以分清不同系统的应用类型很重要,通常应用可以分为两种类型:

           (1)IO 相关,IO 相关的应用通常用来处理大量数据,需要大量内存和存储,频繁 IO 操作读写数据,而对 CPU 的要求则较少,大部分时候 CPU 都在等待硬盘,比如,数据库服务器、文件服务器等。

           (2)CPU 相关,CPU 相关的应用需要使用大量 CPU,比如高并发的 web/mail 服务器、图像/视频处理、科学计算等都可被视作 CPU 相关的应用。

    看看实际中的例子,第1个是文件服务器拷贝一个大文件时表现出来的特征:

    $ vmstat 1procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu------ r  b   swpd   free   buff  cache   si   so    bi    bo   in   cs us sy id wa st 0  4    140 1962724 335516 4852308  0    0   388 65024 1442  563  0  2 47 52  0 0  4    140 1961816 335516 4853868  0    0   768 65536 1434  522  0  1 50 48  0 0  4    140 1960788 335516 4855300  0    0   768 48640 1412  573  0  1 50 49  0 0  4    140 1958528 335516 4857280  0    0  1024 65536 1415  521  0  1 41 57  0 0  5    140 1957488 335516 4858884  0    0   768 81412 1504  609  0  2 50 49  0 第2个是 CPU 做大量计算时表现出来的特征:

    $ vmstat 1procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu------ r  b   swpd   free   buff  cache   si   so    bi    bo   in   cs us sy id wa st 4  0    140 3625096 334256 3266584  0    0     0    16 1054  470 100 0  0  0  0 4  0    140 3625220 334264 3266576  0    0     0    12 1037  448 100 0  0  0  0 4  0    140 3624468 334264 3266580  0    0     0   148 1160  632 100 0  0  0  0 4  0    140 3624468 334264 3266580  0    0     0     0 1078  527 100 0  0  0  0 4  0    140 3624712 334264 3266580  0    0     0    80 1053  501 100 0  0  0  0       上面两个例子最明显的差别就是 id 一栏,代表 CPU 的空闲率,拷贝文件时候 id 维持在 50% 左右,CPU 大量计算的时候 id 基本为 0。

    1.2  底线

           事先建立一个底线,如果性能监测得到的统计数据跨过这条线,我们就可以说这个系统性能差,如果数据能保持在线内我们就说性能好。建立这样底线需要知道一些理论、额外的负载测试和系统管理员多年的经验。如果自己没有多年的经验,有一个简单划底线的办法就是:把这个底线建立在自己对系统的期望上。自己期望这个系统有个什么样的性能,这是一个底线,如果没有达到这个要求就是性能差。

    1.3  监测工具

    工具
     简单介绍
     
    top
     查看进程活动状态以及一些系统状况
     
    vmstat
     查看系统状态、硬件和系统信息等
     
    iostat
     查看CPU 负载,硬盘状况
     
    sar
     综合工具,查看系统状况
     
    mpstat
     查看多处理器状况
     
    netstat
     查看网络状况
     
    iptraf
     实时网络状况监测
     
    tcpdump
     抓取网络数据包,详细分析
     
    mpstat
     查看多处理器状况
     
    tcptrace
     数据包分析工具
     
    netperf
     网络带宽工具
     
    dstat
     综合工具,综合了 vmstat, iostat, ifstat, netstat 等多个信息
     


     

    vmstat 是报告关于进程,内存,IO,CPU活动的一个统计报告。

    在不同的系统中,特别是linux和unix中显示的相关选项会有很大差别。

    我们先以ubuntu为例:

    一般VMSTAT工具的使用是通过两个数字参数来完成的,第一个参数是采样的时间间隔数,单位是秒,第二个参数是采样的次数。

    1
    2
    3
    4
    5
    6
    7
    8
    9
    ipcpu@ubuntu:~$ vmstat 5 10 
    procs -----------memory---------- ---swap-- -----io---- -system-- ----cpu----
    r b swpd free buff cache si so bi bo in cs us sy id wa
    1 0 0 6797712 147668 884660 0 0 3 21 162 146 1 1 98 0
    0 0 0 6797696 147668 884660 0 0 0 3 35 37 1 0 99 0
    1 0 0 6797332 147668 884660 0 0 0 24 62 95 1 0 99 0
    0 0 0 6811632 147668 884692 0 0 0 5 25 26 1 0 99 0
    0 0 0 6818360 147668 884704 0 0 0 5 70 265 1 3 96 0
    0 0 0 6817468 147668 884728 0 0 0 316 253 474 3 2 95 0

    procs相关选项: 
    r    在运行队列中等待的进程数
    b    在等待io的进程数

    memoy 
    swapd    现时可用的交换内存(k表示)
    free    空闲的内存(k表示)
    buff    作为buffer cache的内存数量,一般对块设备的读写才需要缓冲。
    cache    作为page cache的内存数量,一般作为文件系统的cache,

    如果cache较大,说明用到cache的文件较多,如果此时IO中bi比较小,说明文件系统效率比较好。

    swap
    si     由内存进入内存交换区数量。
    so    由内存交换区进入内存数量。
    如今的大内存也让swap渐渐淡出了人们的视线,这个不好分析。

    IO
    bi     从块设备读入数据的总量(读磁盘)(每秒kb)。
    bo     向块设备写入数据的总量(写磁盘)(每秒kb)

    system 显示采集间隔内发生的中断数
    in     列表示在某一时间间隔中观测到的每秒设备中断数。
    cs    列表示每秒产生的上下文切换次数。

    如当 cs 比磁盘 I/O 和网络信息包速率高得多,都应进行进一步调查。

    cpu相关状态
    cs[user]    用户进程消耗的CPU时间百分比
    sy[system]    内核进程消耗的CPU时间百分比
    id[idle]    cpu空闲的时间
    wa[wait]    IO等待消耗的CPU时间百分比

    us的值比较高时,说明用户进程消耗的cpu时间多,但是如果长期大于50%,需要考虑优化用户的程序。
    us+sy 大于 80%说明可能存在CPU不足。
    wa超过30%,说明IO等待严重,这可能是磁盘大量随机访问造成的,也可能磁盘或者磁盘访问控制器的带
    宽瓶颈造成的(主要是块操作)。wa长期超过10% 就该考虑了。

    *注意:
    NFS由于是在内核里面运行的,所以NFS活动所占用的cpu时间反映在sy里面。这个数字经常很大的话,就需要注意是否某个内核进程,比如NFS任务比较繁重。如果us和sy同时都比较大的话,就需要考虑将某些用户程序分离到另外的服务器上面,以免互相影响。

    CPU问题现象:
    1) 如果在processes中运行的序列(process r)是连续的大于在系统中的CPU的个数表示系统现在运行比较慢,有多数的进程等待CPU。
    2) 如果r的输出数大于系统中可用CPU个数的4倍的话,则系统面临着CPU短缺的问题,或者是CPU的速率过低,系统中有多数的进程在等待CPU,造成系统中进程运行过慢。
    3) 如果空闲时间(cpu id)持续为0并且系统时间(cpu sy)是用户时间的两倍(cpu us) 系统则面临着CPU资源的短缺。

    解决办法:
    当发生以上问题的时候请先调整应用程序对CPU的占用情况。使得应用程序能够更有效的使用CPU。同时可以考虑增加更多的CPU。
    关于CPU的使用情况还可以结合mpstat,   ps aux top   prstat等等一些相应的命令来综合考虑关于具体的CPU的使用情况,和那些进程在占用大量的CPU时间。一般情况下,应用程序的问题会比较大一些。比 如一些SQL语句不合理等等都会造成这样的现象。

    Unix中的vmstat

    1 
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    freebsd7.2中的vmstat 
    [
    ipcpu@freebsd ~]$ vmstat
    procs memory page disk faults cpu
    r b w avm fre flt re pi po fr sr ad4 in sy cs us sy id
    0 0 0 152M 7448M 131 0 0 0 132 0 0 167 644 860 0 1 99
    [ipcpu@freebsd ~]$  

    AIX 5.3中的vmstat -bash-3.00
    $ vmstat  
    System
    configuration: lcpu=4 mem=1904MB  
    kthr memory page faults cpu
    ----- ----------- ------------------------ ------------ -----------
    r b avm fre re pi po fr sr cy in sy cs us sy id wa
    1 1 308679 55310 0 0 0 0 1 0 94 4501 333 1 1 98 0

    -
    bash-3.00$  
    SunOS 5.10的vmstat   -
    bash-3.00$ vmstat
    kthr memory page disk faults cpu
    r b w swap free re mf pi po fr de sr s0 s1 s2 s5 in sy cs us sy id
    0 0 0 2584720 2665344 3 10 1 0 0 0 0 0 0 0 0 495 249 235 0 0 99 -bash-3.00$

    这里稍微介绍下page相关选项:
    re    回收的页面
    mf    非严重错误的页面
    pi    进入页面数(k表示)
    po    出页面数(k表示)
    fr    空余的页面数(k表示)
    de    提前读入的页面中的未命中数
    sr    通过时钟算法扫描的页面

    Tips小提示Linux的块设备和字符设备
    他们根本区别在于是否可以被随机访问——换句话说就是,能否在访问设备时随意地从一个位置跳转到另一个位置。

    举个例子,键盘这种设备提供的就是一个数据流,只能按照你敲击的字母顺序进行录入,所以键盘就是一种典型的字符设备。

    硬盘设备的驱动可能要求读取磁盘上任意块的内容,然后又转去读取别的块的内容,而被读取的块在磁盘上位置不一定要连续,所以说硬盘可以被随机访问,而不是以流的方式被访问,显然它是一个块设备。


      

     

    二. CPU

           CPU 的占用主要取决于什么样的资源正在 CPU 上面运行,比如拷贝一个文件通常占用较少 CPU,因为大部分工作是由 DMA(Direct Memory Access)完成,只是在完成拷贝以后给一个中断让 CPU 知道拷贝已经完成;科学计算通常占用较多的 CPU,大部分计算工作都需要在 CPU 上完成,内存、硬盘等子系统只做暂时的数据存储工作。要想监测和理解 CPU 的性能需要知道一些的操作系统的基本知识,比如:中断、进程调度、进程上下文切换、可运行队列等。    这里用个例子来简单介绍一下这些概念和他们的关系,CPU每时每刻都有工作在做(进程、线程)并且自己有一张工作清单(可运行队列),由老板(进程调度)来决定他该干什么,他需要和老板沟通以便得到老板的想法并及时调整自己的工作(上下文切换),部分工作做完以后还需要及时向老板汇报(中断),所以打工仔(CPU)除了做自己该做的工作以外,还有大量时间和精力花在沟通和汇报上。

           CPU 也是一种硬件资源,和任何其他硬件设备一样也需要驱动和管理程序才能使用,我们可以把内核的进程调度看作是 CPU 的管理程序,用来管理和分配 CPU 资源,合理安排进程抢占 CPU,并决定哪个进程该使用 CPU、哪个进程该等待。操作系统内核里的进程调度主要用来调度两类资源:进程(或线程)和中断,进程调度给不同的资源分配了不同的优先级,优先级最高的是硬件中断,其次是内核(系统)进程,最后是用户进程。每个 CPU 都维护着一个可运行队列,用来存放那些可运行的线程。线程要么在睡眠状态(blocked 正在等待 IO)要么在可运行状态,如果 CPU 当前负载太高而新的请求不断,就会出现进程调度暂时应付不过来的情况,这个时候就不得不把线程暂时放到可运行队列里。

    可以从以下几个方面监控CPU的信息:

    (1)中断;

    (2)上下文切换;

    (3)可运行队列;

    (4)CPU 利用率。

    2.1 底线

    通常我们期望我们的系统能到达以下目标:

           (1)CPU 利用率,如果 CPU 有 100% 利用率,那么应该到达这样一个平衡:65%-70% User Time,30%-35% System Time,0%-5% Idle Time;

           (2)上下文切换,上下文切换应该和 CPU 利用率联系起来看,如果能保持上面的 CPU 利用率平衡,大量的上下文切换是可以接受的;

           (3)可运行队列,每个可运行队列不应该有超过1-3个线程(每处理器),比如:双处理器系统的可运行队列里不应该超过6个线程。

    2.2  vmstat

           vmstat 是个查看系统整体性能的小工具,小巧、即使在很 heavy 的情况下也运行良好,并且可以用时间间隔采集得到连续的性能数据。

    $ vmstat 1procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu------ r  b   swpd   free   buff  cache   si   so    bi    bo   in   cs us sy id wa st 2  1    140 2787980 336304 3531996  0    0     0   128 1166 5033  3  3 70 25  0 0  1    140 2788296 336304 3531996  0    0     0     0 1194 5605  3  3 69 25  0 0  1    140 2788436 336304 3531996  0    0     0     0 1249 8036  5  4 67 25  0 0  1    140 2782688 336304 3531996  0    0     0     0 1333 7792  6  6 64 25  0 3  1    140 2779292 336304 3531992  0    0     0    28 1323 7087  4  5 67 25  0参数介绍:

    (1).      r,可运行队列的线程数,这些线程都是可运行状态,只不过 CPU 暂时不可用;

    (2).      b,被 blocked 的进程数,正在等待 IO 请求;

    (3).      in,被处理过的中断数

    (4).      cs,系统上正在做上下文切换的数目

    (5).      us,用户占用 CPU 的百分比

    (6).      sys,内核和中断占用 CPU 的百分比

    (7).      wa,所有可运行的线程被 blocked 以后都在等待 IO,这时候 CPU 空闲的百分比

    (8).      id,CPU 完全空闲的百分比

    举两个现实中的例子来实际分析一下:

    $ vmstat 1procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu------ r  b   swpd   free   buff  cache   si   so    bi    bo   in   cs us sy id wa st 4  0    140 2915476 341288 3951700  0    0     0     0 1057  523 19 81  0  0  0 4  0    140 2915724 341296 3951700  0    0     0     0 1048  546 19 81  0  0  0 4  0    140 2915848 341296 3951700  0    0     0     0 1044  514 18 82  0  0  0 4  0    140 2915848 341296 3951700  0    0     0    24 1044  564 20 80  0  0  0 4  0    140 2915848 341296 3951700  0    0     0     0 1060  546 18 82  0  0  0从上面的数据可以看出几点:

    (1).      interrupts(in)非常高,context switch(cs)比较低,说明这个 CPU 一直在不停的请求资源;

    (2).      user time(us)一直保持在 80% 以上,而且上下文切换较低(cs),说明某个进程可能一直霸占着 CPU;

    (3).      run queue(r)刚好在4个。

    $ vmstat 1procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu------ r  b   swpd   free   buff  cache   si   so    bi    bo   in   cs us sy id wa st14  0    140 2904316 341912 3952308  0    0     0   460 1106 9593 36 64  1  0  017  0    140 2903492 341912 3951780  0    0     0     0 1037 9614 35 65  1  0  020  0    140 2902016 341912 3952000  0    0     0     0 1046 9739 35 64  1  0  017  0    140 2903904 341912 3951888  0    0     0    76 1044 9879 37 63  0  0  016  0    140 2904580 341912 3952108  0    0     0     0 1055 9808 34 65  1  0  0从上面的数据可以看出几点:

    (1).      context switch(cs)比 interrupts(in)要高得多,说明内核不得不来回切换进程;

    (2).      进一步观察发现 system time(sy)很高而 user time(us)很低,而且加上高频度的上下文切换(cs),说明正在运行的应用程序调用了大量的系统调用(system call);

    (3).      run queue(r)在14个线程以上,按照这个测试机器的硬件配置(四核),应该保持在12个以内。

    我上午CPU 100%时的信息:

    top - 11:49:08 up 50 days, 22:25,  6 users,  load average: 59.79, 59.98, 60.50

    Tasks: 200 total,  61 running, 139 sleeping,   0 stopped,   0 zombie

    Cpu0  : 26.5%us, 73.5%sy,  0.0%ni,  0.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st

    Cpu1  : 25.0%us, 75.0%sy,  0.0%ni,  0.0%id,  0.0%wa,  0.0%hi,  0.0%si,  0.0%st

    Mem:   1939780k total,  1744412k used,   195368k free,    95704k buffers

    Swap:  4401800k total,   662836k used,  3738964k free,   811124k cached

    [root@localhost ~]# vmstat 2 10

    procs -----------memory---------- ---swap-- -----io---- --system-- -----cpu------

     r  b   swpd   free   buff  cache   si   so    bi    bo   in   cs us sy id wa st

    58  1 662836 195988  95428 810740    0    0     4   106    4    1 23  4 72  1  0

    59  1 662836 195988  95448 810732    0    0     0   128  235  221 28 72  0  0  0

    59  1 662836 195988  95448 810768    0    0     0     0  216  209 28 72  0  0  0

    2.3  mpstat

           mpstat 和 vmstat 类似,不同的是 mpstat 可以输出多个处理器的数据。

    注意:需要安装sysstat 包后才有这个命令,可以使用yum安装:

           #yum install sysstat

           sysstat 包含iostat、mpstat、sar、命令。

    [root@localhost gmail]# export LANG=en_US[root@localhost gmail]# mpstat -P ALL    Linux 2.6.18-8.el5xen (localhost.localdomain)   02/21/2011 10:20:16 PM  CPU   %user   %nice    %sys %iowait    %irq   %soft  %steal   %idle    intr/s10:20:16 PM  all   11.49    0.00    2.58    1.04    0.01    0.13    0.01   84.74    314.6110:20:16 PM    0   15.73    0.00    2.56    0.55    0.02    0.23    0.01   80.89    241.0910:20:16 PM    1    7.25    0.00    2.60    1.53    0.00    0.02    0.01   88.59     73.52[root@localhost gmail]# mpstat -P ALL 1Linux 2.6.18-8.el5xen (localhost.localdomain)   02/21/2011 10:20:18 PM  CPU   %user   %nice    %sys %iowait    %irq   %soft  %steal   %idle    intr/s10:20:19 PM  all    0.00    0.00    0.00    0.00    0.00    0.00    0.00  100.00    136.6310:20:19 PM    0    0.00    0.00    0.00    0.00    0.00    0.00    0.00  100.00     86.1410:20:19 PM    1    0.00    0.00    0.00    0.00    0.00    0.00    0.00  100.00     50.50 10:20:19 PM  CPU   %user   %nice    %sys %iowait    %irq   %soft  %steal   %idle    intr/s10:20:20 PM  all    0.00    0.00    0.00    0.47    0.00    0.00    0.00   99.53    105.0010:20:20 PM    0    0.00    0.00    0.00    0.00    0.00    0.00    0.00  100.00     79.0010:20:20 PM    1    0.00    0.00    0.00    0.90    0.00    0.00    0.00   99.10     26.00 2.4  ps

    查看某个程序、进程占用了多少 CPU 资源:

    [root@localhost gmail]#  while :; do ps -eo pid,ni,pri,pcpu,psr,comm | grep 'oracle'; sleep 1; done  PID  NI PRI %CPU PSR COMMAND 3668   0  24  0.0   0 oracle 3670   0  21  0.0   0 oracle 3672   0  24  0.0   0 oracle 3674   0  23  0.0   0 oracle 3676   0  24  0.0   1 oracle 3678   0  23  0.0   0 oracle 3680   0  21  0.0   1 oracle 3682   0  24  0.0   1 oracle 3684   0  24  0.0   0 oracle 3686   0  21  0.0   0 oracle三. Memory

           这里的讲到的 “内存” 包括物理内存和虚拟内存,虚拟内存(Virtual Memory)把计算机的内存空间扩展到硬盘,物理内存(RAM)和硬盘的一部分空间(SWAP)组合在一起作为虚拟内存为计算机提供了一个连贯的虚拟内存空间,好处是我们拥有的内存 ”变多了“,可以运行更多、更大的程序,坏处是把部分硬盘当内存用整体性能受到影响,硬盘读写速度要比内存慢几个数量级,并且 RAM 和 SWAP之间的交换增加了系统的负担。

           在操作系统里,虚拟内存被分成页,在 x86 系统上每个页大小是 4KB。 Linux 内核读写虚拟内存是以 “页” 为单位操作的,把内存转移到硬盘交换空间(SWAP)和从交换空间读取到内存的时候都是按页来读写的。内存和 SWAP 的这种交换过程称为页面交换(Paging),值得注意的是 paging 和 swapping 是两个完全不同的概念,国内很多参考书把这两个概念混为一谈,swapping 也翻译成交换,在操作系统里是指把某程序完全交换到硬盘以腾出内存给新程序使用,和 paging 只交换程序的部分(页面)是两个不同的概念。纯粹的 swapping 在现代操作系统中已经很难看到了,因为把整个程序交换到硬盘的办法既耗时又费力而且没必要,现代操作系统基本都是 paging 或者 paging/swapping 混合,swapping 最初是在 Unix system V 上实现的。

    在这里只介绍和性能监测有关的两个内核进程:kswapd 和 pdflush。

           (1)kswapd daemon 用来检查 pages_high 和 pages_low,如果可用内存少于 pages_low,kswapd 就开始扫描并试图释放 32个页面,并且重复扫描释放的过程直到可用内存大于 pages_high 为止。

           扫描的时候检查3件事:

           1)如果页面没有修改,把页放到可用内存列表里;

           2)如果页面被文件系统修改,把页面内容写到磁盘上;

           3)如果页面被修改了,但不是被文件系统修改的,把页面写到交换空间。

           (2)pdflush daemon 用来同步文件相关的内存页面,把内存页面及时同步到硬盘上。比如打开一个文件,文件被导入到内存里,对文件做了修改后并保存后,内核并不马上保存文件到硬盘,由 pdflush 决定什么时候把相应页面写入硬盘,这由一个内核参数 vm.dirty_background_ratio 来控制,比如下面的参数显示脏页面(dirty pages)达到所有内存页面10%的时候开始写入硬盘。

    # /sbin/sysctl -n vm.dirty_background_ratio

    10

    3.1  vmstat


  • 结合netstat和awk命令来统计网络连接数 (转)

    2011-12-14 18:38:40

    结合netstat和awk命令来统计网络连接数



    From: http://hi.baidu.com/thinkinginlamp/blog/item/afbcab64b1ad81f3f6365453.html

    netstat -n | awk '/^tcp/ {++state[$NF]} END {for(key in state) print key,"\t",state[key]}'

    会得到类似下面的结果,具体数字会有所不同:

    LAST_ACK 1
    SYN_RECV 14
    ESTABLISHED 79
    FIN_WAIT1 28
    FIN_WAIT2 3
    CLOSING 5
    TIME_WAIT 1669

    状态:描述
    CLOSED:无连接是活动的或正在进行
    LISTEN:服务器在等待进入呼叫
    SYN_RECV:一个连接请求已经到达,等待确认
    SYN_SENT:应用已经开始,打开一个连接
    ESTABLISHED:正常数据传输状态
    FIN_WAIT1:应用说它已经完成
    FIN_WAIT2:另一边已同意释放
    ITMED_WAIT:等待所有分组死掉
    CLOSING:两边同时尝试关闭
    TIME_WAIT:另一边已初始化一个释放
    LAST_ACK:等待所有分组死掉

    也就是说,这条命令可以把当前系统的网络连接状态分类汇总。

    下面解释一下为啥要这样写:

    一个简单的管道符连接了netstat和awk命令。

    ------------------------------------------------------------------

    先来看看netstat:

    netstat -n

    Active Internet connections (w/o servers)
    Proto Recv-Q Send-Q Local Address Foreign Address State
    tcp 0 0 123.123.123.123:80 234.234.234.234:12345 TIME_WAIT

    你实际执行这条命令的时候,可能会得到成千上万条类似上面的记录,不过我们就拿其中的一条就足够了。

    ------------------------------------------------------------------

    再来看看awk:

    /^tcp/
    滤出tcp开头的记录,屏蔽udp, socket等无关记录。

    state[]
    相当于定义了一个名叫state的数组

    NF
    表示记录的字段数,如上所示的记录,NF等于6

    $NF
    表示某个字段的值,如上所示的记录,$NF也就是$6,表示第6个字段的值,也就是TIME_WAIT

    state[$NF]
    表示数组元素的值,如上所示的记录,就是state[TIME_WAIT]状态的连接数

    ++state[$NF]
    表示把某个数加一,如上所示的记录,就是把state[TIME_WAIT]状态的连接数加一

    END
    表示在最后阶段要执行的命令

    for(key in state)
    遍历数组

    print key,"\t",state[key]
    打印数组的键和值,中间用\t制表符分割,美化一下。

    如发现系统存在大量TIME_WAIT状态的连接,通过调整内核参数解决,
    vim /etc/sysctl.conf
    编辑文件,加入以下内容:

    1.net.ipv4.tcp_syncookies = 1
    2.net.ipv4.tcp_tw_reuse = 1
    3.net.ipv4.tcp_tw_recycle = 1
    4.net.ipv4.tcp_fin_timeout = 30

    然后执行 /sbin/sysctl -p 让参数生效。

    net.ipv4.tcp_syncookies = 1 表示开启SYN Cookies。当出现SYN等待队列溢出时,启用cookies来处理,可防范少量SYN攻击,默认为0,表示关闭;
    net.ipv4.tcp_tw_reuse = 1 表示开启重用。允许将TIME-WAIT sockets重新用于新的TCP连接,默认为0,表示关闭;
    net.ipv4.tcp_tw_recycle = 1 表示开启TCP连接中TIME-WAIT sockets的快速回收,默认为0,表示关闭。
    net.ipv4.tcp_fin_timeout 修改系統默认的 TIMEOUT 时间

    下面附上TIME_WAIT状态的意义:

    客户端与服务器端建立TCP/IP连接后关闭SOCKET后,服务器端连接的端口
    状态为TIME_WAIT

    是不是所有执行主动关闭的socket都会进入TIME_WAIT状态呢?
    有没有什么情况使主动关闭的socket直接进入CLOSED状态呢?

    主动关闭的一方在发送最后一个 ack 后
    就会进入 TIME_WAIT 状态 停留2MSL(max segment lifetime)时间
    这个是TCP/IP必不可少的,也就是“解决”不了的。

    也就是TCP/IP设计者本来是这么设计的
    主要有两个原因
    1。防止上一次连接中的包,迷路后重新出现,影响新连接
    (经过2MSL,上一次连接中所有的重复包都会消失)
    2。可靠的关闭TCP连接
    在主动关闭方发送的最后一个 ack(fin) ,有可能丢失,这时被动方会重新发
    fin, 如果这时主动方处于 CLOSED 状态 ,就会响应 rst 而不是 ack。所以
    主动方要处于 TIME_WAIT 状态,而不能是 CLOSED 。

    TIME_WAIT 并不会占用很大资源的,除非受到攻击。

    还有,如果一方 send 或 recv 超时,就会直接进入 CLOSED 状态

    netstat -an | grep SYN | awk '{print $5}' | awk -F: '{print $1}' | sort | uniq -c | sort -nr | more

    1. netstat -tna | cut -b 49- |grep TIME_WAIT | sort
      取出目前所有 TIME_WAIT 的连接 IP ( 排序过 )

    2.   net.ipv4.tcp_syncookies = 1 表示开启SYN Cookies。当出现SYN等待队列溢出时,启用cookies来处理,可防范少量SYN攻击,默认为0,表示关闭;
        net.ipv4.tcp_tw_reuse = 1 表示开启重用。允许将TIME-WAIT sockets重新用于新的TCP连接,默认为0,表示关闭;
        net.ipv4.tcp_tw_recycle = 1 表示开启TCP连接中TIME-WAIT sockets的快速回收,默认为0,表示关闭。
        net.ipv4.tcp_fin_timeout = 30 表示如果套接字由本端要求关闭,这个参数决定了它保持在FIN-WAIT-2状态的时间。
        net.ipv4.tcp_keepalive_time = 1200 表示当keepalive起用的时候,TCP发送keepalive消息的频度。缺省是2小时,改为20分钟。
        net.ipv4.ip_local_port_range = 1024 65000 表示用于向外连接的端口范围。缺省情况下很小:32768到61000,改为1024到65000。
        net.ipv4.tcp_max_syn_backlog = 8192 表示SYN队列的长度,默认为1024,加大队列长度为8192,可以容纳更多等待连接的网络连接数。
        net.ipv4.tcp_max_tw_buckets = 5000 表示系统同时保持TIME_WAIT套接字的最大数量,如果超过这个数字,TIME_WAIT套接字将立刻被清除并打印警告信息。默认为180000,改 为5000。对于Apache、Nginx等服务器,上几行的参数可以很好地减少TIME_WAIT套接字数量,但是对于Squid,效果却不大。此项参 数可以控制TIME_WAIT套接字的最大数量,避免Squid服务器被大量的TIME_WAIT套接字拖死。

       

       

      在怀疑有Dos攻击的时候,可以输入

      1 netstat -na | grep :80 |awk '{print $5}'|awk -F '::ffff:' '{print $2}' grep ':' awk -F: '{print $1}' sort uniq -c |sort -r | awk -F' ' '{if ($1 > 50) print $2}' sed 's/^.*$/iptables -I firewall 1 -p tcp -s & --dport 80 --syn -j REJECT/' | sh

      先把冲击量最大的前50个IP给封了.

      还可以加几个例外的白名单IP

      1 netstat -na | grep :80 |awk '{print $5}'|awk -F '::ffff:' '{print $2}' grep ':' awk -F: '{print $1}' sort uniq -c |sort -r | awk -F' ' '{if ($1 > 50) print $2}' grep -v xxx.xxx.xxx.xxx | sed 's/^.*$/iptables -I RH-Firewall-1-INPUT 1 -p tcp -m tcp -s & --dport 80 --syn -j REJECT/' | sh
      以上的命令还没有实际考证过, 放在这里做参考.


      转自:
      http://www.cnblogs.com/derekchen/archive/2011/02/26/1965839.html
  • web管理常用命令二 (转)

    2011-12-14 18:37:33

    web管理常用命令二


    原文链接:http://bbs.linuxtone.org/thread-16-1-1.html IT运维专家网--"自由平等,互助分享!" 
    作者:NetSeek

    1.删除0字节文件
    引用
    find -type f -size 0 -exec rm -rf {} \;

    2.查看进程
    按内存从大到小排列
    引用
    ps -e  -o "%C  : %p : %z : %a"|sort -k5 -nr

    3.按cpu利用率从大到小排列
    引用
    ps -e  -o "%C  : %p : %z : %a"|sort  -nr

    4.打印说cache里的URL
    引用
    grep -r -a  jpg /data/cache/* | strings | grep "http:" | awk -F'http:' '{print "http:"$2;}'

    5.查看http的并发请求数及其TCP连接状态:
    引用
    netstat -n | awk '/^tcp/ {++S[$NF]} END {for(a in S) print a, S[a]}'

    6.sed 替换的使用
    引用
    sed -i '/Root/s/no/yes/' /etc/ssh/sshd_config  sed在这个文里Root的一行,匹配Root一行,将no替换成yes.

    7.如何杀掉mysql进程:
    引用
    (1):ps aux|grep mysql|grep -v grep|awk '{print $2}'|xargs kill -9   (从中了解到awk的用途)
    (2):pgrep mysql |xargs kill -9
    (3):killall -TERM mysqld
    (4):kill -9 `cat /usr/local/apache2/logs/httpd.pid`  试试查杀进程PID

    8.显示运行3级别开启的服务:
    引用
    ls /etc/rc3.d/S* |cut -c 15-  (从中了解到cut的用途,截取数据)

    9.如何在编写SHELL显示多个信息,用EOF
    引用
    cat << EOF
    +--------------------------------------------------------------+
    |         === Welcome to www.6curl.com===                   |
    +--------------------------------------------------------------+
    EOF

    10. for 的巧用(如给mysql建软链接)
    引用
    cd /usr/local/mysql/bin
    for i in *
    do ln /usr/local/mysql/bin/$i /usr/bin/$i
    done

    11. 取IP地址:
    引用
    (1):ifconfig eth0|sed -n '2p'|awk '{print $2}'|cut -c 6-30
    (2):ifconfig eth0 |grep "inet addr:" |awk '{print $2}'|cut -c 6-
    (3):ifconfig  | grep 'inet addr:'| grep -v '127.0.0.1' | cut -d: -f2 | awk '{ print $1}'
    (4):ifconfig eth0 | sed -n '/inet /{s/.*addr://;s/ .*//;p}'
    Perl实现获取IP的方法:
    ifconfig -a | perl -ne 'if ( m/^\s*inet (?:addr:)?([\d.]+).*?cast/ ) { print qq($1\n); exit 0; }'

    12.内存的大小:
    引用
    free -m |grep "Mem" | awk '{print $2}'

    13.
    引用
    netstat -an -t | grep ":80" | grep ESTABLISHED | awk '{printf "%s %s\n",$5,$6}' | sort

    14.查看Apache的并发请求数及其TCP连接状态:
    引用
    netstat -n | awk '/^tcp/ {++S[$NF]} END {for(a in S) print a, S[a]}'

    15.因为同事要统计一下服务器下面所有的jpg的文件的大小,写了个shell给他来统计.原来用xargs实现,但他一次处理一部分,搞的有多个总和....,下面的命令就能解决啦.
    引用
    find / -name *.jpg -exec wc -c {} \;|awk '{print $1}'|awk '{a+=$1}END{print a}'

    16  CPU负载
    引用
    cat /proc/loadavg
    检查前三个输出值是否超过了系统逻辑CPU的4倍.
    cat /proc/cpuinfo |grep -c processor (多核CPU)

    18  CPU负载,检查%idle是否过低(比如小于5%)
    引用
    #mpstat 1 1

    19  内存空间  
    引用
    # free
    检查free值是否过低  也可以用 # cat /proc/meminfo

    20  swap空间
    引用
    # free
    检查swap used值是否过高  如果swap used值过高,进一步检查swap动作是否频繁:
    # vmstat 1 5
    观察si和so值是否较大

    21  磁盘空间
    # df -h
    引用
    检查是否有分区使用率(Use%)过高(比如超过90%)  如发现某个分区空间接近用尽,可以进入该分区的挂载点,用以下命令找出占用空间最多的文件或目录:
    # du -cks * | sort -rn | head -n 10

    22  磁盘I/O负载  
    引用
    # iostat -x 1 2
    检查I/O使用率(%util)是否超过100%

    23  网络负载
    引用
    # sar -n DEV
    检查网络流量(rxbyt/s, txbyt/s)是否过高

    24  网络错误  
    引用
    # netstat -i
    检查是否有网络错误(drop fifo colls carrier)  
    cat /proc/net/dev

    25 网络连接数目
    引用
    # netstat -an | grep -E “^(tcp)” | cut -c 68- | sort | uniq -c | sort -n

    26  进程总数  
    引用
    # ps aux | wc -l
    检查进程个数是否正常 (比如超过250)

    27  可运行进程数目
    引用
    # vmwtat 1 5
    列给出的是可运行进程的数目,检查其是否超过系统逻辑CPU的4倍

    28  进程  
    引用
    # top -id 1
    观察是否有异常进程出现

    29  网络状态
    引用
    检查DNS, 网关等是否可以正常连通

    30  用户
    引用
    # who | wc -l
    检查登录用户是否过多 (比如超过50个)  
    也可以用命令:# uptime

    31  系统日志
    引用
    # cat /var/log/rflogview/*errors
    # grep -i error /var/log/messages
    # grep -i fail /var/log/messages
    # egrep -i 'error|warn' /var/log/messages 查看系统异常

    32  核心日志  
    # dmesg
    检查是否有异常错误记录
    33  系统时间
    # date
    检查系统时间是否正确
    34  打开文件数目
    引用
    # lsof | wc -l
    检查打开文件总数是否过多

    35  日志
    引用
    # logwatch –print  配置/etc/log.d/logwatch.conf,将 Mailto 设置为自己的email 地址,启动mail服务 (sendmail或者postfix),这样就可以每天收到日志报告了。
    缺省logwatch只报告昨天的日志,可以用# logwatch –print –range all 获得所有的日志分析结果。
    可以用# logwatch –print –detail high 获得更具体的日志分析结果(而不仅仅是出错日志)。

    36.杀掉80端口相关的进程
    引用
    lsof -i :80|grep -v "PID"|awk '{print "kill -9",$2}'|sh

    37.清除僵死进程。
    引用
    ps -eal | awk '{ if ($2 == "Z") {print $4}}' | kill -9

    38.tcpdump 抓包 ,用来防止80端口被人攻击时可以分析数据
    引用
    # tcpdump -c 10000 -i eth0 -n dst port 80 > /root/pkts

    39.然后检查IP的重复数 并从小到大排序 注意 "-t\ +0"  中间是两个空格
    引用
    # less pkts | awk {'printf $3"\n"'} | cut -d. -f 1-4 | sort | uniq -c | awk {'printf $1" "$2"\n"'} | sort -n -t\ +0

    40.查看有多少个活动的php-cgi进程
    引用
    netstat -anp | grep php-cgi | grep ^tcp | wc -l

    41.利用iptables对应简单攻击
    引用
    netstat -an | grep -v LISTEN | awk ‘{print $5}’ |grep -v 127.0.0.1|grep -v 本机ip|sed  “s/::ffff://g”|awk ‘BEGIN { FS=”:” } { Num[$1]++ } END { for(i in Num) if(Num>8) { print i} }’ |grep ‘[0-9]\{1,3\}\.[0-9]\{1,3\}\.[0-9]\{1,3\}\.[0-9]\{1,3\}’|  xargs -i[] iptables -I INPUT -s [] -j DROP


    ps: Num>8部分设定值为阀值,这条句子会自动将netstat -an 中查到的来自同一IP的超过一定量的连接的列入禁止范围。   基中本机ip改成你的服务器的ip地址
    42. 怎样知道某个进程在哪个CPU上运行?
    引用
    # ps -eo pid,args,psr

    43. 查看硬件制造商
    引用
    dmidecode -s system-product-name


    转自:http://www.cnblogs.com/derekchen/archive/2011/02/26/1965834.html



  • web管理常用命令一 (转)

    2011-12-14 18:36:36

    web管理常用命令一


    实时查看正在执行的sql语句
    #/usr/sbin/tcpdump -i eth0 -s 0 -l -w - dst port 3306 | strings | egrep -i 'SELECT|UPDATE|DELETE|INSERT|SET|COMMIT|ROLLBACK|CREATE|DROP|ALTER|CALL'
     
    查看http连接
    netstat -n | awk '/^tcp/ {++state[$NF]} END {for(key in state) print key,"t",state[key]}'
     
    查看SYN状态的http连接
    netstat -an | grep SYN | awk '{print $5}' | awk -F: '{print $1}' | sort | uniq -c | sort -nr | more
     
    查看TIME_WAIT状态的http连接
    netstat -tna | cut -b 49- |grep TIME_WAIT | sort |more
    netstat -an | grep TIME_WAIT | awk '{print $5}' | awk -F: '{print $1}' | sort | uniq -c | sort -nr | more
     
    查看ESTABLISHED状态的http连接
    netstat -an | grep ESTABLISHED | awk '{print $5}' | awk -F: '{print $1}' | sort | uniq -c | sort -nr | morenetstat -an | grep ":80" | grep ESTABLISHED | sort | more
    批量kill进程
    ps -efww|grep sqlr-listener|grep -v grep|cut -c 9-15|xargs kill -9
     
    查看活动的php-cgi连接数
    netstat -anpo|grep php-cgi|wc -l

     

     

    判断CC攻击 netstat命令详解,快速找出有问题的ip

     

     

    网站排障分析常用的命令】
    系统连接状态篇:
    1.查看TCP连接状态
    netstat -nat |awk '{print $6}'|sort|uniq -c|sort -rn 
    netstat -n | awk '/^tcp/ {++S[$NF]};END {for(a in S) print a, S[a]}' 或
    netstat -n | awk '/^tcp/ {++state[$NF]}; END {for(key in state) print key,"\t",state[key]}'
    netstat -n | awk '/^tcp/ {++arr[$NF]};END {for(k in arr) print k,"\t",arr[k]}'
    netstat -n |awk '/^tcp/ {print $NF}'|sort|uniq -c|sort -rn 
    netstat -ant | awk '{print $NF}' | grep -v '[a-z]' | sort | uniq -c
    2.查找请求数请20个IP(常用于查找攻来源):
    netstat -anlp|grep 80|grep tcp|awk '{print $5}'|awk -F: '{print $1}'|sort|uniq -c|sort -nr|head -n20
    netstat -ant |awk '/:80/{split($5,ip,":");++A[ip[1]]}END{for(i in A) print A[i],i}' |sort -rn|head -n20
    3.用tcpdump嗅探80端口的访问看看谁最高
    tcpdump -i eth0 -tnn dst port 80 -c 1000 | awk -F"." '{print $1"."$2"."$3"."$4}' | sort | uniq -c | sort -nr |head -20
    4.查找较多time_wait连接
    netstat -n|grep TIME_WAIT|awk '{print $5}'|sort|uniq -c|sort -rn|head -n20
    5.找查较多的SYN连接
    netstat -an | grep SYN | awk '{print $5}' | awk -F: '{print $1}' | sort | uniq -c | sort -nr | more
    6.根据端口列进程
    netstat -ntlp | grep 80 | awk '{print $7}' | cut -d/ -f1
    7.计算httpd占用内存的平均数
    ps aux|grep -v grep|awk '/httpd/{sum+=$6;n++};END{print sum/n}'
    网站日志分析篇1(Apache):
    1.获得访问前10位的ip地址
    cat access.log|awk '{print $1}'|sort|uniq -c|sort -nr|head -10
    cat access.log|awk '{counts[$(11)]+=1}; END {for(url in counts) print counts[url], url}'
    2.访问次数最多的文件或页面,取前20
    cat access.log|awk '{print $11}'|sort|uniq -c|sort -nr|head -20
    3.列出传输最大的几个exe文件(分析下载站的时候常用)
    cat access.log |awk '($7~/\.exe/){print $10 " " $1 " " $4 " " $7}'|sort -nr|head -20
    4.列出输出大于200000byte(约200kb)的exe文件以及对应文件发生次数
    cat access.log |awk '($10 > 200000 && $7~/\.exe/){print $7}'|sort -n|uniq -c|sort -nr|head -100
    5.如果日志最后一列记录的是页面文件传输时间,则有列出到客户端最耗时的页面
    cat access.log |awk  '($7~/\.php/){print $NF " " $1 " " $4 " " $7}'|sort -nr|head -100
    6.列出最最耗时的页面(超过60秒的)的以及对应页面发生次数
    cat access.log |awk '($NF > 60 && $7~/\.php/){print $7}'|sort -n|uniq -c|sort -nr|head -100
    7.列出传输时间超过 30 秒的文件
    cat access.log |awk '($NF > 30){print $7}'|sort -n|uniq -c|sort -nr|head -20
    8.统计网站流量(G)
    cat access.log |awk '{sum+=$10} END {print sum/1024/1024/1024}'
    9.统计404的连接
    awk '($9 ~/404/)' access.log | awk '{print $9,$7}' | sort
    10. 统计http status.
    cat access.log |awk '{counts[$(9)]+=1}; END {for(code in counts) print code, counts[code]}'
    cat access.log |awk '{print $9}'|sort|uniq -c|sort -rn
    10.蜘蛛分析
    查看是哪些蜘蛛在抓取内容。
    /usr/sbin/tcpdump -i eth0 -l -s 0 -w - dst port 80 | strings | grep -i user-agent | grep -i -E 'bot|crawler|slurp|spider'

    网站日分析2(Squid篇)

    2.按域统计流量
    zcat squid_access.log.tar.gz| awk '{print $10,$7}' |awk 'BEGIN{FS="[ /]"}{trfc[$4]+=$1}END{for(domain in trfc){printf "%s\t%d\n",domain,trfc[domain]}}'
    效率更高的perl版本请到此下载:http://docs.linuxtone.org/soft/tools/tr.pl
    数据库篇
    1.查看数据库执行的sql
    /usr/sbin/tcpdump -i eth0 -s 0 -l -w - dst port 3306 | strings | egrep -i 'SELECT|UPDATE|DELETE|INSERT|SET|COMMIT|ROLLBACK|CREATE|DROP|ALTER|CALL'

    系统Debug分析篇
    1.调试命令
    strace -p pid
    2.跟踪指定进程的PID
    gdb -p pid



    转自:http://www.cnblogs.com/derekchen/archive/2011/02/26/1965806.html
  • Linux的sysctl 命令 参数

    2011-12-14 17:59:28



    Linux内核通过/proc虚拟文件系统向用户导出内核信息,用户也可以通过/proc文件系统或通过sysctl命令动态配置内核。比如,如果我们想启动NAT,除了加载模块、配置防火墙外,还需要启动内核转发功能。我们有三种方法:

    1. 直接写/proc文件系统
    # echo 1 > /proc/sys/net/ipv4/ip_forward

    2. 利用sysctl命令
    # sysctl -w net.ipv4.ip_forward=1
    sysctl -a可以查看内核所有导出的变量

    3. 编辑/etc/sysctl.conf
    添加如下一行,这样系统每次启动后,该变量的值就是1
    net.ipv4.ip_forward = 1

    sysctl是procfs软件中的命令,该软件包还提供了w, ps, vmstat, pgrep, pkill, top, slabtop等命令。

    sysctl配置与显示在/proc/sys目录中的内核参数.可以用sysctl来设置或重新设置联网功能,如IP转发、IP碎片去除以及源路由检查等。用户只需要编辑/etc/sysctl.conf文件,即可手工或自动执行由sysctl控制的功能。

        命令格式:
        sysctl [-n] [-e] -w variable=value
        sysctl [-n] [-e] -p <filename> (default /etc/sysctl.conf)
        sysctl [-n] [-e] -a
        常用参数的意义:
        -w   临时改变某个指定参数的值,如
             sysctl -w net.ipv4.ip_forward=1
        -a   显示所有的系统参数
        -p   从指定的文件加载系统参数,如不指定即从/etc/sysctl.conf中加载
        如果仅仅是想临时改变某个系统参数的值,可以用两种方法来实现,例如想启用IP路由转发功能:
        1) #echo 1 > /proc/sys/net/ipv4/ip_forward
        2) #sysctl -w net.ipv4.ip_forward=1
        以上两种方法都可能立即开启路由功能,但如果系统重启,或执行了
         # service network restart
    命令,所设置的值即会丢失,如果想永久保留配置,可以修改/etc/sysctl.conf文件
    将 net.ipv4.ip_forward=0改为net.ipv4.ip_forward=1



    sysctl是一个允许您改变正在运行中的Linux系统的接口。它包含一些 TCP/IP 堆栈和虚拟内存系统的高级选项, 这可以让有经验的管理员提高引人注目的系统性能。用sysctl可以读取设置超过五百个系统变量。基于这点,sysctl(8) 提供两个功能:读取和修改系统设置。
    查看所有可读变量:
    % sysctl -a
    读一个指定的变量,例如 kern.maxproc:
    % sysctl kern.maxproc kern.maxproc: 1044
    要设置一个指定的变量,直接用 variable=value 这样的语法:
    # sysctl kern.maxfiles=5000
    kern.maxfiles: 2088 -> 5000
    您可以使用sysctl修改系统变量,也可以通过编辑sysctl.conf文件来修改系统变量。sysctl.conf 看起来很像 rc.conf。它用 variable=value 的形式来设定值。指定的值在系统进入多用户模式之后被设定。并不是所有的变量都可以在这个模式下设定。
    sysctl 变量的设置通常是字符串、数字或者布尔型。 (布尔型用 1 来表示'yes',用 0 来表示'no')。

    sysctl -w kernel.sysrq=0
    sysctl -w kernel.core_uses_pid=1
    sysctl -w net.ipv4.conf.default.accept_redirects=0
    sysctl -w net.ipv4.conf.default.accept_source_route=0
    sysctl -w net.ipv4.conf.default.rp_filter=1
    sysctl -w net.ipv4.tcp_syncookies=1
    sysctl -w net.ipv4.tcp_max_syn_backlog=2048
    sysctl -w net.ipv4.tcp_fin_timeout=30
    sysctl -w net.ipv4.tcp_synack_retries=2
    sysctl -w net.ipv4.tcp_keepalive_time=3600
    sysctl -w net.ipv4.tcp_window_scaling=1
    sysctl -w net.ipv4.tcp_sack=1

    配置sysctl

    编辑此文件:

    vi /etc/sysctl.conf


    如果该文件为空,则输入以下内容,否则请根据情况自己做调整:

    # Controls source route verification
    # Default should work for all interfaces
    net.ipv4.conf.default.rp_filter = 1
    # net.ipv4.conf.all.rp_filter = 1
    # net.ipv4.conf.lo.rp_filter = 1
    # net.ipv4.conf.eth0.rp_filter = 1

    # Disables IP source routing
    # Default should work for all interfaces
    net.ipv4.conf.default.accept_source_route = 0
    # net.ipv4.conf.all.accept_source_route = 0
    # net.ipv4.conf.lo.accept_source_route = 0
    # net.ipv4.conf.eth0.accept_source_route = 0

    # Controls the System Request debugging functionality of the kernel
    kernel.sysrq = 0

    # Controls whether core dumps will append the PID to the core filename.
    # Useful for debugging multi-threaded applications.
    kernel.core_uses_pid = 1

    # Increase maximum amount of memory allocated to shm
    # Only uncomment if needed!
    # kernel.shmmax = 67108864

    # Disable ICMP Redirect Acceptance
    # Default should work for all interfaces
    net.ipv4.conf.default.accept_redirects = 0
    # net.ipv4.conf.all.accept_redirects = 0
    # net.ipv4.conf.lo.accept_redirects = 0
    # net.ipv4.conf.eth0.accept_redirects = 0

    # Enable Log Spoofed Packets, Source Routed Packets, Redirect Packets
    # Default should work for all interfaces
    net.ipv4.conf.default.log_martians = 1
    # net.ipv4.conf.all.log_martians = 1
    # net.ipv4.conf.lo.log_martians = 1
    # net.ipv4.conf.eth0.log_martians = 1

    # Decrease the time default value for tcp_fin_timeout connection
    net.ipv4.tcp_fin_timeout = 25

    # Decrease the time default value for tcp_keepalive_time connection
    net.ipv4.tcp_keepalive_time = 1200

    # Turn on the tcp_window_scaling
    net.ipv4.tcp_window_scaling = 1

    # Turn on the tcp_sack
    net.ipv4.tcp_sack = 1

    # tcp_fack should be on because of sack
    net.ipv4.tcp_fack = 1

    # Turn on the tcp_timestamps
    net.ipv4.tcp_timestamps = 1

    # Enable TCP SYN Cookie Protection
    net.ipv4.tcp_syncookies = 1

    # Enable ignoring broadcasts request
    net.ipv4.icmp_echo_ignore_broadcasts = 1

    # Enable bad error message Protection
    net.ipv4.icmp_ignore_bogus_error_responses = 1

    # Make more local ports available
    # net.ipv4.ip_local_port_range = 1024 65000

    # Set TCP Re-Ordering value in kernel to ‘5′
    net.ipv4.tcp_reordering = 5

    # Lower syn retry rates
    net.ipv4.tcp_synack_retries = 2
    net.ipv4.tcp_syn_retries = 3

    # Set Max SYN Backlog to ‘2048′
    net.ipv4.tcp_max_syn_backlog = 2048

    # Various Settings
    net.core.netdev_max_backlog = 1024

    # Increase the maximum number of skb-heads to be cached
    net.core.hot_list_length = 256

    # Increase the tcp-time-wait buckets pool size
    net.ipv4.tcp_max_tw_buckets = 360000

    # This will increase the amount of memory available for socket input/output queues
    net.core.rmem_default = 65535
    net.core.rmem_max = 8388608
    net.ipv4.tcp_rmem = 4096 87380 8388608
    net.core.wmem_default = 65535
    net.core.wmem_max = 8388608
    net.ipv4.tcp_wmem = 4096 65535 8388608
    net.ipv4.tcp_mem = 8388608 8388608 8388608
    net.core.optmem_max = 40960

    如果希望屏蔽别人 ping 你的主机,则加入以下代码:

    # Disable ping requests
    net.ipv4.icmp_echo_ignore_all = 1

    编辑完成后,请执行以下命令使变动立即生效:

    /sbin/sysctl -p
    /sbin/sysctl -w net.ipv4.route.flush=1

    我们常常在 Linux 的 /proc/sys 目录下,手动设定一些 kernel 的参数或是直接 echo 特定的值给一个 proc下的虚拟档案,俾利某些档案之开启,常见的例如设定开机时自动启动 IP Forwarding: 
    echo “1” > /proc/sys/net/ipv4/ip_forward 

    其实,在 Linux 我们还可以用 sysctl command 便可以简易的去检视、设定或自动配置 特定的 kernel 设定。我们可以在系统提示符号下输入「sysctl -a」,摘要如后:abi.defhandler_coff = 117440515 

    dev.raid.speed_limit_max = 100000 

    net.ipv4.conf.default.send_redirects = 1 

    net.ipv4.conf.default.secure_redirects = 1 

    net.ipv4.conf.default.accept_redirects = 1 

    net.ipv4.conf.default.mc_forwarding = 0 

    net.ipv4.neigh.lo.delay_first_probe_time = 5 

    net.ipv4.neigh.lo.base_reachable_time = 30 

    net.ipv4.icmp_ratelimit = 100 

    net.ipv4.inet_peer_gc_mintime = 10 

    net.ipv4.igmp_max_memberships = 20 

    net.ipv4.ip_no_pmtu_disc = 0 

    net.core.no_cong_thresh = 20 

    net.core.netdev_max_backlog = 300 

    net.core.rmem_default = 65535 

    net.core.wmem_max = 65535 

    vm.kswapd = 512 32 8 

    vm.overcommit_memory = 0 

    vm.bdflush = 30 64 64 256 500 3000 60 0 0 

    vm.freepages = 351 702 1053 

    kernel.sem = 250 32000 32 128 

    kernel.panic = 0 

    kernel.domainname = (none) 

    kernel.hostname = pc02.shinewave.com.tw 

    kernel.version = #1 Tue Oct 30 20:11:04 EST 2001 

    kernel.osrelease = 2.4.9-13 

    kernel.ostype = Linux 

    fs.dentry-state = 1611 969 45 0 0 0 

    fs.file-nr = 1121 73 8192 

    fs.inode-state = 1333 523 0 0 0 0 0 

    从上述的语法我们大概可看出 sysctl 的表示法乃把目录结构的「/」以「.」表示,一层一层的连结下去。当然以echo 特定的值给一个 proc下的虚拟档案也是可以用 sysctl加以表示,例如: 

    #sysctl –w net.ipv4.ip_forward =”1” 


    或是直接在 /etc/sysctl.conf 增删修改特定档案的 0,1值亦可: 

    # Enables packet forwarding 

    net.ipv4.ip_forward = 1 

    # Enables source route verification 

    net.ipv4.conf.default.rp_filter = 1 

    # Disables the magic-sysrq key 

    kernel.sysrq = 0 

    当然如果考虑 reboot 后仍有效, 直接在 /etc/sysctl.conf 增删修改特定档案的 0,1值才可使之保留设定(以RedHat 为例,每次开机系统启动后, init 会执行 /etc/rc.d/rc.sysinit,便会使用 /etc/sysctl.conf 的预设值去执行 sysctl)。 

    相关参考档案: 

    /sbin/sysctl 

    /etc/sysctl.conf 

    sysctl 及sysctl.conf manpage 

    /usr/src/linux-x.y.z/Documentation/sysctl/* 

    /usr/share/doc/kernel-doc-x.y.z/sysctl/* (RedHat)

    http://hi.baidu.com/caosicong/blog/item/0a592360d438cfda8db10d9b.html
    http://hi.baidu.com/phpfamer/blog/item/932e276eb39c30de80cb4a3c.htmlsysctl配置与显示在/proc/sys目录中的内核参数.可以用sysctl来设置或重新设置联网功能,如IP转发、IP碎片去除以及源路由检查等。用户只需要编辑/etc/sysctl.conf文件,即可手工或自动执行由sysctl控制的功能。
        命令格式:
        sysctl [-n] [-e] -w variable=value
        sysctl [-n] [-e] -p <filename> (default /etc/sysctl.conf)
        sysctl [-n] [-e] -a
        常用参数的意义:
        -w   临时改变某个指定参数的值,如
             sysctl -w net.ipv4.ip_forward=1
        -a   显示所有的系统参数
        -p   从指定的文件加载系统参数,如不指定即从/etc/sysctl.conf中加载
        如果仅仅是想临时改变某个系统参数的值,可以用两种方法来实现,例如想启用IP路由转发功能:
        1) #echo 1 > /proc/sys/net/ipv4/ip_forward
        2) #sysctl -w net.ipv4.ip_forward=1
        以上两种方法都可能立即开启路由功能,但如果系统重启,或执行了
         # service network restart
    命令,所设置的值即会丢失,如果想永久保留配置,可以修改/etc/sysctl.conf文件
    将 net.ipv4.ip_forward=0改为net.ipv4.ip_forward=1



    sysctl是一个允许您改变正在运行中的Linux系统的接口。它包含一些 TCP/IP 堆栈和虚拟内存系统的高级选项, 这可以让有经验的管理员提高引人注目的系统性能。用sysctl可以读取设置超过五百个系统变量。基于这点,sysctl(8) 提供两个功能:读取和修改系统设置。
    查看所有可读变量:
    % sysctl -a
    读一个指定的变量,例如 kern.maxproc:
    % sysctl kern.maxproc kern.maxproc: 1044
    要设置一个指定的变量,直接用 variable=value 这样的语法:
    # sysctl kern.maxfiles=5000
    kern.maxfiles: 2088 -> 5000
    您可以使用sysctl修改系统变量,也可以通过编辑sysctl.conf文件来修改系统变量。sysctl.conf 看起来很像 rc.conf。它用 variable=value 的形式来设定值。指定的值在系统进入多用户模式之后被设定。并不是所有的变量都可以在这个模式下设定。
    sysctl 变量的设置通常是字符串、数字或者布尔型。 (布尔型用 1 来表示'yes',用 0 来表示'no')。

    sysctl -w kernel.sysrq=0
    sysctl -w kernel.core_uses_pid=1
    sysctl -w net.ipv4.conf.default.accept_redirects=0
    sysctl -w net.ipv4.conf.default.accept_source_route=0
    sysctl -w net.ipv4.conf.default.rp_filter=1
    sysctl -w net.ipv4.tcp_syncookies=1
    sysctl -w net.ipv4.tcp_max_syn_backlog=2048
    sysctl -w net.ipv4.tcp_fin_timeout=30
    sysctl -w net.ipv4.tcp_synack_retries=2
    sysctl -w net.ipv4.tcp_keepalive_time=3600
    sysctl -w net.ipv4.tcp_window_scaling=1
    sysctl -w net.ipv4.tcp_sack=1

    配置sysctl

    编辑此文件:

    vi /etc/sysctl.conf


    如果该文件为空,则输入以下内容,否则请根据情况自己做调整:

    # Controls source route verification
    # Default should work for all interfaces
    net.ipv4.conf.default.rp_filter = 1
    # net.ipv4.conf.all.rp_filter = 1
    # net.ipv4.conf.lo.rp_filter = 1
    # net.ipv4.conf.eth0.rp_filter = 1

    # Disables IP source routing
    # Default should work for all interfaces
    net.ipv4.conf.default.accept_source_route = 0
    # net.ipv4.conf.all.accept_source_route = 0
    # net.ipv4.conf.lo.accept_source_route = 0
    # net.ipv4.conf.eth0.accept_source_route = 0

    # Controls the System Request debugging functionality of the kernel
    kernel.sysrq = 0

    # Controls whether core dumps will append the PID to the core filename.
    # Useful for debugging multi-threaded applications.
    kernel.core_uses_pid = 1

    # Increase maximum amount of memory allocated to shm
    # Only uncomment if needed!
    # kernel.shmmax = 67108864

    # Disable ICMP Redirect Acceptance
    # Default should work for all interfaces
    net.ipv4.conf.default.accept_redirects = 0
    # net.ipv4.conf.all.accept_redirects = 0
    # net.ipv4.conf.lo.accept_redirects = 0
    # net.ipv4.conf.eth0.accept_redirects = 0

    # Enable Log Spoofed Packets, Source Routed Packets, Redirect Packets
    # Default should work for all interfaces
    net.ipv4.conf.default.log_martians = 1
    # net.ipv4.conf.all.log_martians = 1
    # net.ipv4.conf.lo.log_martians = 1
    # net.ipv4.conf.eth0.log_martians = 1

    # Decrease the time default value for tcp_fin_timeout connection
    net.ipv4.tcp_fin_timeout = 25

    # Decrease the time default value for tcp_keepalive_time connection
    net.ipv4.tcp_keepalive_time = 1200

    # Turn on the tcp_window_scaling
    net.ipv4.tcp_window_scaling = 1

    # Turn on the tcp_sack
    net.ipv4.tcp_sack = 1

    # tcp_fack should be on because of sack
    net.ipv4.tcp_fack = 1

    # Turn on the tcp_timestamps
    net.ipv4.tcp_timestamps = 1

    # Enable TCP SYN Cookie Protection
    net.ipv4.tcp_syncookies = 1

    # Enable ignoring broadcasts request
    net.ipv4.icmp_echo_ignore_broadcasts = 1

    # Enable bad error message Protection
    net.ipv4.icmp_ignore_bogus_error_responses = 1

    # Make more local ports available
    # net.ipv4.ip_local_port_range = 1024 65000

    # Set TCP Re-Ordering value in kernel to ‘5′
    net.ipv4.tcp_reordering = 5

    # Lower syn retry rates
    net.ipv4.tcp_synack_retries = 2
    net.ipv4.tcp_syn_retries = 3

    # Set Max SYN Backlog to ‘2048′
    net.ipv4.tcp_max_syn_backlog = 2048

    # Various Settings
    net.core.netdev_max_backlog = 1024

    # Increase the maximum number of skb-heads to be cached
    net.core.hot_list_length = 256

    # Increase the tcp-time-wait buckets pool size
    net.ipv4.tcp_max_tw_buckets = 360000

    # This will increase the amount of memory available for socket input/output queues
    net.core.rmem_default = 65535
    net.core.rmem_max = 8388608
    net.ipv4.tcp_rmem = 4096 87380 8388608
    net.core.wmem_default = 65535
    net.core.wmem_max = 8388608
    net.ipv4.tcp_wmem = 4096 65535 8388608
    net.ipv4.tcp_mem = 8388608 8388608 8388608
    net.core.optmem_max = 40960

    如果希望屏蔽别人 ping 你的主机,则加入以下代码:

    # Disable ping requests
    net.ipv4.icmp_echo_ignore_all = 1

    编辑完成后,请执行以下命令使变动立即生效:

    /sbin/sysctl -p
    /sbin/sysctl -w net.ipv4.route.flush=1

    我们常常在 Linux 的 /proc/sys 目录下,手动设定一些 kernel 的参数或是直接 echo 特定的值给一个 proc下的虚拟档案,俾利某些档案之开启,常见的例如设定开机时自动启动 IP Forwarding: 
    echo “1” > /proc/sys/net/ipv4/ip_forward 

    其实,在 Linux 我们还可以用 sysctl command 便可以简易的去检视、设定或自动配置 特定的 kernel 设定。我们可以在系统提示符号下输入「sysctl -a」,摘要如后:abi.defhandler_coff = 117440515 

    dev.raid.speed_limit_max = 100000 

    net.ipv4.conf.default.send_redirects = 1 

    net.ipv4.conf.default.secure_redirects = 1 

    net.ipv4.conf.default.accept_redirects = 1 

    net.ipv4.conf.default.mc_forwarding = 0 

    net.ipv4.neigh.lo.delay_first_probe_time = 5 

    net.ipv4.neigh.lo.base_reachable_time = 30 

    net.ipv4.icmp_ratelimit = 100 

    net.ipv4.inet_peer_gc_mintime = 10 

    net.ipv4.igmp_max_memberships = 20 

    net.ipv4.ip_no_pmtu_disc = 0 

    net.core.no_cong_thresh = 20 

    net.core.netdev_max_backlog = 300 

    net.core.rmem_default = 65535 

    net.core.wmem_max = 65535 

    vm.kswapd = 512 32 8 

    vm.overcommit_memory = 0 

    vm.bdflush = 30 64 64 256 500 3000 60 0 0 

    vm.freepages = 351 702 1053 

    kernel.sem = 250 32000 32 128 

    kernel.panic = 0 

    kernel.domainname = (none) 

    kernel.hostname = pc02.shinewave.com.tw 

    kernel.version = #1 Tue Oct 30 20:11:04 EST 2001 

    kernel.osrelease = 2.4.9-13 

    kernel.ostype = Linux 

    fs.dentry-state = 1611 969 45 0 0 0 

    fs.file-nr = 1121 73 8192 

    fs.inode-state = 1333 523 0 0 0 0 0 

    从上述的语法我们大概可看出 sysctl 的表示法乃把目录结构的「/」以「.」表示,一层一层的连结下去。当然以echo 特定的值给一个 proc下的虚拟档案也是可以用 sysctl加以表示,例如: 

    #sysctl –w net.ipv4.ip_forward =”1” 


    或是直接在 /etc/sysctl.conf 增删修改特定档案的 0,1值亦可: 

    # Enables packet forwarding 

    net.ipv4.ip_forward = 1 

    # Enables source route verification 

    net.ipv4.conf.default.rp_filter = 1 

    # Disables the magic-sysrq key 

    kernel.sysrq = 0 

    当然如果考虑 reboot 后仍有效, 直接在 /etc/sysctl.conf 增删修改特定档案的 0,1值才可使之保留设定(以RedHat 为例,每次开机系统启动后, init 会执行 /etc/rc.d/rc.sysinit,便会使用 /etc/sysctl.conf 的预设值去执行 sysctl)。 



    转自:http://hi.baidu.com/michaelhan/blog/item/b2784b7b45538ef10bd1872b.html
  • Tokyo Tyrant(TTServer)系列-启动参数和配置 (转)

    2011-12-14 17:56:27

    [文章作者:孙立  链接:http://www.cnblogs.com/sunli/  更新时间:2009-03-18]
    启动参数介绍
        继续上一篇Tokyo Tyrant(TTServer)系列-介绍和安 我们继续来看启动参数和配置。
        ttserver命令可以启动一个数据库实例。因为数据库已经实现了Tokyo Cabinet的抽象API,所以可以在启动的时候指定数据库的配置类型。
    支持的数据库类型有:
    内存hash数据库
    内存tree数据库
    hash数据库
    B+ tree数据库,
      命令通过下面的格式来使用,‘dbname’制定数据库名,如果省略,则被视作内存hash数据库。
    ttserver [-host name] [-port num] [-thnum num] [-tout num] [-dmn] [-pid path] [-log path] [-ld|-le] [-ulog path] [-ulim num] [-uas] [-sidnum] [-mhost name] [-mport num] [-rts path] [-ext path] [-extpc name period] [-mask expr] [dbname] 
    下面来说这些参数的功能:
    -host name :指明服务器的hostname或者ip地址。默认服务器的所有地址都会被绑定。比如:指定127.0.0.1这样的ip,就只是本地可以访问了。
    -port num : 指定服务启动的端口. 默认1978.如果要启动多个数据库实例,端口需要不一样。
    -thnum num : 指定服务工作的线程数。默认8.
    -tout num : 指定每个会话的超时时间。默认永不超时。
    -dmn : 以守护进程方式运行。
    -pid path : 输出进程IP到指定的文件。
    -log path : 输出日志信息到指定文件。
    -ld : 日志中记录debug信息。
    -le :日志中只记录错误信息。
    -ulog path : 指定存放更新日志(update log)的目录.可以用来备份恢复数据库,主从库之间的同步。
    -ulim num : 指定每个更新日志文件的大小限制.
    -uas :使用异步IO记录更新日志。(使用此项可以减少写入日志的IO开销,但是在服务器意外关机,进程被kill时可能会丢失数据。根据经验,一般可以不使用)。
    -sid num : 指定服务的ID号。主从复制的时候通过不同的ID号来识别。
    -mhost name : 指定主从复制模式下的主服务器的IP或域名。
    -mport num : 指定主从模式下主服务器的端口号.
    -rts path : 指定用于主从复制的时间戳存放文件.
    -ext path : 指定扩展脚本语言文件。
    -extpc name period : 指定被周期调用的函数名和间隔时间.
    -mask expr : 指定被禁止的命令名(比如可以禁止使用清空vanish).
    -unmask expr : 指定被允许的命令名.
    数据库类型
       下面我们再来看下数据库类型的详细配置。
        数据库名的命名方式被Tokyo Cabinet的抽象API指定。
        如果数据库名为"*",表示内存hash数据库。
        如果数据库名为"+"表示内存tree数据库。
        如果数据库名为".tch",则数据库为hash数据库。
        如果数据库名的后缀为".tcb",数据库将为B+ tree数据库。
        如果数据库名的后缀为".tcf"。则数据库将为fixed-length数据库。
        如果数据库名的后缀为".tct",则数据将为一个table数据库(有表的概念)。
    数据库的调整参数通过数据库名的延伸来指定,通过"#"分开,每个参数通过一个参数名和值来指定,用"="隔开。
    内存hash数据库支持"bnum", "capnum", 和 "capsiz"
    内存tree数据库支持"capnum" 和 "capsiz"
         capnum指定记录的最大容量,capsiz指定最大的内存使用量(在内存数据库中),记录通过存储的顺序移除。
    hash数据库支持"mode", "bnum", "apow", "fpow", "opts", "rcnum", 和 "xmsiz". 
    `rcnum'指定最大的缓存记录数。如果它不大于零,那么缓存记录不可用。默认不可用。
     xmsiz   指定外部内存的大小。如果不大于0,内存不可用。默认是67108864,即64M。
    `bnum' 指定bucket存储桶的数量。如果指定的数目不大于0,将会使用默认的数值131071.推荐数量应该在所有需要存储的记录总数的0.4-4倍
    `apow' 跟一个key关联的记录数,2的N次方表示.  如果不指定,默认2^4=16.
    `fpow' specifies the maximum number of elements of the free block pool by power of 2.  默认2^10=1024.
    `opts' 指定选项,位或:`HDBTLARGE' 指定数据库的大小通过使用64位数组桶能够超过2G。
                           `HDBTDEFLATE'  指定每个记录被Deflate encoding压缩。
                          `HDBTBZIP' 指定每个记录被BZIP2 encoding压缩
                           `HDBTTCBS'指定每个记录被 TCBS encoding压缩.
    B+ tree数据库支持"mode", "lmemb", "nmemb", "bnum", "apow", "fpow", "opts", "lcnum", "ncnum", 和 "xmsiz". 
    Fixed-length 数据库 支持 "mode", "width", and "limsiz". 
    Table 数据库支持 "mode", "bnum", "apow", "fpow", "opts", "rcnum", "lcnum", "ncnum", "xmsiz", 和 "idx"
          "idx"指定表的索引。
         "mode"可以包含 "w" 写, "r" 读, "c" 创建, "t" 截断,"e" 无锁,和"f" 非阻塞锁。默认的的mod为"wc"。
    优化性能
         如果使用hash数据库我们可以指定#bnum=xxx来提高性能。xxx大于或等我我们的记录总数。
          如果使用B+ tree数据库我们可以通过指定"#lcnum=xxx#bnum=yyy" 来提高性能.第一个参数指定被缓存的最大叶子节点数,受内存容量限制,第二个参数指定桶的数量,它应该大于总记录数的1/128.
        如果有大量的客户端连接,确保我们的文件描述符够用。系统默认是1024,我们可以用使用“ulimit”来重新设定
       比如下面的单机实例启动脚本(一个正在线上运行的脚本):
    #!/bin/sh
    ulimit -SHn 51200
    ttserver -host 192.168.0.136  -port 11212 -thnum 8 -dmn -pid /data/ttserver/ttserver.pid -log /data/ttserver/ttserver.log -le -ulog /data/ttserver/ -ulim 128m -sid 1 -rts /data/ttserver/ttserver.rts /data/ttserver/database.tch#bnum=10000000#xmsiz=434217728#rcnum=20000
    使用hash数据库,最大会缓存20000个记录,最大使用内存434217728bytes(414M),bucket存储桶的数量10000000。
    目前的库大小:
    -rw-r--r--  1 root root  28G Mar  8 12:19 bbsdatabase.tch
    因为使用了64位操作系统,所以文件大小不受2G的限制。
    我们再看下读取数据的速度:
    当前获取memcache Threads_cdb_threads_tid3565732_displayorder_0 使用时间 0.00054812431335449 以上是程序打印出来的通过memcache协议读取key为memcache Threads_cdb_threads_tid3565732_displayorder_0的数据所花的时间0.00054812431335449(s),可以看到速度还是非常快的。
    启动实例
    个人推荐通过修改ttservctl来实现启动。下面我们举几个简单的启动例子。
    单机启动例子,下面是ttservctl文件的部分:
    #! /bin/sh
    #----------------------------------------------------------------
    # Startup script. for the server of Tokyo Tyrant
    #----------------------------------------------------------------
    # configuration variables
    prog="ttservctl"
    cmd="ttserver"
    basedir="/var/ttserver" #数据库存放的路径,比如改为"/data/mydata"
    port="1978" #启动的端口
    pidfile="$basedir/pid"
    logfile="$basedir/log"
    ulogdir="$basedir/ulog"
    ulimsiz="256m"
    sid=1
    dbname="$basedir/casket.tch#bnum=1000000" #上面讲的数据库类型配置
    maxcon="65536"
    retval=0

    双机互为主辅模式,比如两台机器的Ip分别为192.168.1.176和192.168.1.1.177,以下为ttservctl文件的一部分。
    176的配置:
    #! /bin/sh
    #----------------------------------------------------------------
    # Startup script. for the server of Tokyo Tyrant
    #----------------------------------------------------------------
    # configuration variables
    prog="ttservctl"
    cmd="ttserver"
    basedir="/data/data/data1"
    port="11211"
    pidfile="$basedir/pid"
    logfile="$basedir/log"
    ulogdir="$basedir/"
    mhost="192.168.1.177" #主ip即另外机器的ip
    ulimsiz="256m"
    sid=6#注意要每台机器不一样
    dbname="$basedir/casket.tch#bnum=100000000#xmsiz=104857600#rcnum=1000000"
    rts="$basedir/ttserver.rts" #在ttservctl基础上增加
    maxcon="65536"
    retval=0
    # locale clear
    LANG=C
    LC_ALL=C
    export LANG LC_ALL
    # start the server
    start(){
      printf 'Starting the server of Tokyo Tyrant\n'
      ulimit -n "$maxcon"
      mkdir -p "$basedir"
      if [ -f "$pidfile" ] ; then
        pid=`cat "$pidfile"`
        printf 'Existing process: %d\n' "$pid"
        retval=1
      else
        $cmd \
          -port "$port" \
          -dmn \
          -pid "$pidfile" \
          -log "$logfile" \
          -ulog "$ulogdir" \
          -ulim "$ulimsiz" \
          -sid "$sid" \
          -mhost "$mhost" \#在ttservctl基础上增加
          -mport "$port" \#在ttservctl基础上增加
          -rts "$rts" \#在ttservctl基础上增加
          "$dbname"
        if [ "$?" -eq 0 ] ; then
          printf 'Done\n'
        else
          printf 'The server could not started\n'
          retval=1
        fi
      fi
    }
    177的配置:
    #! /bin/sh
    #----------------------------------------------------------------
    # Startup script. for the server of Tokyo Tyrant
    #----------------------------------------------------------------
    # configuration variables
    prog="ttservctl"
    cmd="ttserver"
    basedir="/data/data/data1"
    port="11211"
    pidfile="$basedir/pid"
    logfile="$basedir/log"
    ulogdir="$basedir/"
    mhost="192.168.1.176" #主ip即另外机器的ip
    ulimsiz="256m"
    sid=7#注意要每台机器不一样
    dbname="$basedir/casket.tch#bnum=100000000#xmsiz=104857600#rcnum=1000000"
    rts="$basedir/ttserver.rts" #在ttservctl基础上增加
    maxcon="65536"
    retval=0
    # locale clear
    LANG=C
    LC_ALL=C
    export LANG LC_ALL
    # start the server
    start(){
      printf 'Starting the server of Tokyo Tyrant\n'
      ulimit -n "$maxcon"
      mkdir -p "$basedir"
      if [ -f "$pidfile" ] ; then
        pid=`cat "$pidfile"`
        printf 'Existing process: %d\n' "$pid"
        retval=1
      else
        $cmd \
          -port "$port" \
          -dmn \
          -pid "$pidfile" \
          -log "$logfile" \
          -ulog "$ulogdir" \
          -ulim "$ulimsiz" \
          -sid "$sid" \
          -mhost "$mhost" \#在ttservctl基础上增加
          -mport "$port" \#在ttservctl基础上增加
          -rts "$rts" \#在ttservctl基础上增加
          "$dbname"
        if [ "$?" -eq 0 ] ; then
          printf 'Done\n'
        else
          printf 'The server could not started\n'
          retval=1
        fi
      fi
    }
     
    新浪微博:http://t.sina.com.cn/sunli1223 


  • php-fpm – 配置详解(转)

    2011-12-14 17:55:39

    php-fpm – 配置详解(转)

    版权声明:转载时请以超链接形式标明文章原始出处和作者信息及本声明
    http://duyongguang.blogbus.com/logs/156375484.html

    php5.3自带php-fpm

    /usr/local/php/etc/php-fpm.conf

    pid = run/php-fpm.pid
    pid设置,默认在安装目录中的var/run/php-fpm.pid,建议开启

    error_log = log/php-fpm.log
    错误日志,默认在安装目录中的var/log/php-fpm.log

    log_level = notice
    错误级别. 可用级别为: alert(必须立即处理), error(错误情况), warning(警告情况), notice(一般重要信息), debug(调试信息). 默认: notice.

    emergency_restart_threshold = 60
    emergency_restart_interval = 60s
    表示在emergency_restart_interval所设值内出现SIGSEGV或者SIGBUS错误的php-cgi进程数如果超过 emergency_restart_threshold个,php-fpm就会优雅重启。这两个选项一般保持默认值。

    process_control_timeout = 0
    设置子进程接受主进程复用信号的超时时间. 可用单位: s(秒), m(分), h(小时), 或者 d(天) 默认单位: s(秒). 默认值: 0.

    daemonize = yes
    后台执行fpm,默认值为yes,如果为了调试可以改为no。

    在FPM中,可以使用不同的设置来运行多个进程池。 这些设置可以针对每个进程池单独设置。

    listen = 127.0.0.1:9000
    fpm监听端口,即nginx中php处理的地址,一般默认值即可。
    可用格式为: ‘ip:port’, ‘port’, ‘/path/to/unix/socket’. 每个进程池都需要设置.

    listen.backlog = -1
    backlog数,-1表示无限制,由操作系统决定,此行注释掉就行。backlog含义参考:

    http://www.3gyou.cc/?p=41

    listen.allowed_clients = 127.0.0.1
    允许访问FastCGI进程的IP,设置any为不限制IP,如果要设置其他主机的nginx也能访问这台FPM进程,listen处要设置成本地可被访问的IP。默认值是any。
    每个地址是用逗号分隔. 如果没有设置或者为空,则允许任何服务器请求连接

    listen.owner = www
    listen.group = www
    listen.mode = 0666
    unix socket设置选项,如果使用tcp方式访问,这里注释即可。

    user = www
    group = www
    启动进程的帐户和组

    pm = dynamic
    如何控制子进程,选项有static和dynamic。
    如果选择static,则由pm.max_children指定固定的子进程数。
    如果选择dynamic,则由下开参数决定:
    pm.max_children ,子进程最大数
    pm.start_servers ,启动时的进程数
    pm.min_spare_servers ,保证空闲进程数最小值,如果空闲进程小于此值,则创建新的子进程
    pm.max_spare_servers ,保证空闲进程数最大值,如果空闲进程大于此值,此进行清理
    对于专用服务器,pm可以设置为static。

    pm.max_requests = 1000
    设置每个子进程重生之前服务的请求数. 对于可能存在内存泄漏的第三方模块来说是非常有用的. 如果设置为 ’0′ 则一直接受请求. 等同于 PHP_FCGI_MAX_REQUESTS 环境变量. 默认值: 0.

    pm.status_path = /status
    FPM状态页面的网址. 如果没有设置, 则无法访问状态页面. 默认值: none.

    ping.path = /ping
    FPM监控页面的ping网址. 如果没有设置, 则无法访问ping页面. 该页面用于外部检测FPM是否存活并且可以响应请求. 请注意必须以斜线开头 (/)。

    ping.response = pong
    用于定义ping请求的返回相应. 返回为 HTTP 200 的 text/plain 格式文本. 默认值: pong.

    request_terminate_timeout = 0
    设置单个请求的超时中止时间. 该选项可能会对php.ini设置中的’max_execution_time’因为某些特殊原因没有中止运行的脚本有用. 设置为 ’0′ 表示 ‘Off’.
    当经常出现502错误时可以尝试更改此选项。

    request_slowlog_timeout = 10s
    当一个请求该设置的超时时间后,就会将对应的PHP调用堆栈信息完整写入到慢日志中. 设置为 ’0′ 表示 ‘Off’

    slowlog = log/$pool.log.slow
    慢请求的记录日志,配合request_slowlog_timeout使用

    rlimit_files = 1024
    设置文件打开描述符的rlimit限制. 默认值: 系统定义值
    系统默认可打开句柄是1024,可使用 ulimit -n查看,ulimit -n 2048修改。

    rlimit_core = 0
    设置核心rlimit最大限制值. 可用值: ‘unlimited’ 、0或者正整数. 默认值: 系统定义值.

    chroot =
    启动时的Chroot目录. 所定义的目录需要是绝对路径. 如果没有设置, 则chroot不被使用.

    chdir =
    设置启动目录,启动时会自动Chdir到该目录. 所定义的目录需要是绝对路径. 默认值: 当前目录,或者/目录(chroot时)

    catch_workers_output = yes
    重定向运行过程中的stdout和stderr到主要的错误日志文件中. 如果没有设置, stdout 和 stderr 将会根据FastCGI的规则被重定向到 /dev/null . 默认值: 空.


    转自:http://hi.baidu.com/bianxuehui/blog/item/411c3decada90ec8b21cb1c5.html
  • Linux下chkconfig命令详解和service命令

    2011-12-14 17:49:13

    Linux下chkconfig命令详解



    chkconfig命令主要用来更新(启动或停止)和查询系统服务的运行级信息。谨记chkconfig不是立即自动禁止或激活一个服务,它只是简单的改变了符号连接。

    使用语法:
    chkconfig [--add][--del][--list][系统服务] 或 chkconfig [--level <等级代号>][系统服务][on/off/reset]

    chkconfig在没有参数运行时,显示用法。如果加上服务名,那么就检查这个服务是否在当前运行级启动。如果是,返回true,否则返回false。如果在服务名后面指定了on,off或者reset,那么chkconfi 会改变指定服务的启动信息。on和off分别指服务被启动和停止,reset指重置服务的启动信息,无论有问题的初始化脚本指定了什么。on和off开关,系统默认只对运行级3,4,5有效,但是reset可以对所有运行级有效。

    参数用法:
       --add  增加所指定的系统服务,让chkconfig指令得以管理它,并同时在系统启动的叙述文件内增加相关数据。
       --del  删除所指定的系统服务,不再由chkconfig指令管理,并同时在系统启动的叙述文件内删除相关数据。
       --level<等级代号>  指定读系统服务要在哪一个执行等级中开启或关毕。
          等级0表示:表示关机
          等级1表示:单用户模式
          等级2表示:无网络连接的多用户命令行模式
          等级3表示:有网络连接的多用户命令行模式
          等级4表示:不可用
          等级5表示:带图形界面的多用户模式
          等级6表示:重新启动
          需要说明的是,level选项可以指定要查看的运行级而不一定是当前运行级。对于每个运行级,只能有一个启动脚本或者停止脚本。当切换运行级时,init不会重新启动已经启动的服务,也不会再次去停止已经停止的服务。

        chkconfig --list [name]:显示所有运行级系统服务的运行状态信息(on或off)。如果指定了name,那么只显示指定的服务在不同运行级的状态。
        chkconfig --add name:增加一项新的服务。chkconfig确保每个运行级有一项启动(S)或者杀死(K)入口。如有缺少,则会从缺省的init脚本自动建立。
        chkconfig --del name:删除服务,并把相关符号连接从/etc/rc[0-6].d删除。
        chkconfig [--level levels] name:设置某一服务在指定的运行级是被启动,停止还是重置。

    运行级文件:
    每个被chkconfig管理的服务需要在对应的init.d下的脚本加上两行或者更多行的注释。第一行告诉chkconfig缺省启动的运行级以及启动和停止的优先级。如果某服务缺省不在任何运行级启动,那么使用 - 代替运行级。第二行对服务进行描述,可以用\ 跨行注释。
    例如,random.init包含三行:
    # chkconfig: 2345 20 80
    # description: Saves and restores system entropy pool for \
    # higher quality random number generation.

    使用范例:
    chkconfig --list        #列出所有的系统服务
    chkconfig --add httpd        #增加httpd服务
    chkconfig --del httpd        #删除httpd服务
    chkconfig --level httpd 2345 on        #设置httpd在运行级别为2、3、4、5的情况下都是on(开启)的状态
    chkconfig --list        #列出系统所有的服务启动情况
    chkconfig --list mysqld        #列出mysqld服务设置情况
    chkconfig --level 35 mysqld on        #设定mysqld在等级3和5为开机运行服务,--level 35表示操作只在等级3和5执行,on表示启动,off表示关闭
    chkconfig mysqld on        #设定mysqld在各等级为on,“各等级”包括2、3、4、5等级

    如何增加一个服务:
    1.服务脚本必须存放在/etc/ini.d/目录下;
    2.chkconfig --add servicename
        在chkconfig工具服务列表中增加此服务,此时服务会被在/etc/rc.d/rcN.d中赋予K/S入口了;
    3.chkconfig --level 35 mysqld on
        修改服务的默认启动等级。



    --------------------------------------------------------------------------------------------


    linux  service命令

    service命令,顾名思义,就是用于管理Linux操作系统中服务的命令。

    1. 声明:这个命令不是在所有的linux发行版本中都有。主要是在redhat、fedora、mandriva和centos中。

    2. 此命令位于/sbin目录下,用file命令查看此命令会发现它是一个脚本命令。

    3. 分析脚本可知此命令的作用是去/etc/init.d目录下寻找相应的服务,进行开启和关闭等操作。

    4. 开启httpd服务器:service httpd start

    start可以换成restart表示重新启动,stop表示关闭,reload表示重新载入配置。

    5. 关闭mysql服务器:service mysqld stop

    6. 强烈建议大家将service命令替换为/etc/init.d/mysqld stop (因为有一些linux的版本不支持service)

     

     

     

    Usage: service < option > | --status-all | [ service_name [ command | --full-restart ] ]

    service oracle start

    service oracle stop

    service oracle restart

    service oracle status





    转自:http://www.cnblogs.com/panjun-Donet/archive/2010/08/10/1796873.html


    http://blog.sina.com.cn/s/blog_51dc0fba0100rjrb.html
  • linux awk用法

    2011-12-14 17:34:55

    用法:awk '{pattern + action}' {filenames} 
    pattern指在每一行中进行匹配的条件,action指针对符合条件的行进行的操作,filenames是输入的文件名。

    假设data文件中有以下数据:

        1 donald 305 20050129
        2 chin 102 20040129
        3 mark 304 20040229
    --------------------------------------------------------------
    awk '{action}' {filenames} 
     范例:awk '{print $1, $2, $3, $4}' data
           输出data文件的1,2,3,4列

    awk '{pattern + action}' {filenames} 
    范例:awk '/donald/ {print $4}' data
             匹配当data文件中包含字符串"donald"的行,输出第4列的值:
    ----------------------------------------------------

    pattern指在每一行中进行匹配的条件,action指针对符合条件的行进行的操作,filenames是输入的文件名。

    假设data文件中有以下数据:

        1 donald 305 20050129
        2 chin 102 20040129
        3 mark 304 20040229


    下面对这个文件进行操作:

        awk '{print $1, $2, $3, $4}' data


    输出:

        1 donald 305 20050129
        2 chin 102 20040129
        3 mark 304 20040229



        awk '{print $1"\t", $2"\t", $3"\t", $4}' data


    输出:

        1 donald 305 20050129
        2 chin 102 20040129
        3 mark 304 20040229


    这里显示的格式并不是输出的真实格式,真实格式是中间会有一个tab符号,格式对的很整齐,只不过在html里看不出来。

        awk '/donald/ {print $4}' data

    匹配当data文件中包含字符串"donald"的行,输出第4列的值:

        20050129

        awk '/donald|chin/ {print $1, $2}' data

    这里的"|"应该是或的作用,而不是管道,输出:

        1 donald
        2 chin

        awk '/a[rl]/ {print $1, $2}' data

    兼容perl的正则表达式,匹配包含"ar"或"al"的列,输出:

        1 donald
        3 mark

        awk '/a[rl]/ {print $1, $2, $3+1}' data

    给第三列加上1再输出:

        1 donald 306
        3 mark 305

        awk '/a[rl]/ {print $1, $2} {print $3+1}' data

    匹配只对第一对花括号产生作用,输出:

        1 donald
        306
        103
        3 mark
        305

        awk 'FS="n" {print $1}' data

    使用"n"而不是空格做为分隔符,输出:

        1
        2 chi
        3 mark 304 20040229

        awk 'FS="n" {OFS="-"} {print $1, $2}' data

    把分隔符输出:

        1-donald
        2 chi- 102 20040129
        3 mark 304 20040229-

        awk 'FS="n" {OFS="-"} {print NR, $1, $2}' data

    使用NR变量,num of row,即行号,输出:

        1-1-donald
        2-2 chi- 102 20040129
        3-3 mark 304 20040229-

        awk '{x=x+$3} {print NR, $3, x}' data

    使用变量进行累加计算,输出:

        1 305 305
        2 102 407
        3 304 711

        awk '{x=x+$3} END {print NR, $3, x}' data

    使用BEGIN和END在处理之前或之后显示结果,输出:

        3 304 711

        awk '{x=x+$3} {print NR, $3, x | "sort -nr"}' data

    在awk内使用管道进行排序,输出:

        3 304 711
        2 102 407
        1 305 305

        cat command
        {x=x+$3}
        {print NR, $3, x | "sort -nr"}

        awk -f command data

    将指定写在文件中,输出:

        3 304 711
        2 102 407
        1 305 305

    如果简单的输出不能处理您的程序中所需要的复杂信息,则可以尝试由 printf 命令获得的更加复杂的输出,其语法是

    printf( format, value, value ...)

    该语法类似于 C 语言中的 printf 命令,而格式的规格是相同的。通过插入一项定义如何打印数值的规格,可以定义该格式。格式规格包含一个跟有字母的 %。类似于打印命令,printf 不必包含在圆括号中,但是可以认为使用圆括号是一种良好的习惯。

    下表列出 printf 命令提供的各种规格。

    规格 说明
    %c 打印单个 ASCII 字符
    %d 打印十进制数
    %e 打印数字的科学计数表示
    %f 打印浮点表示
    %g 打印 %e 或 %f;两种方式都更简短
    %o 打印无符号的八进制数
    s 打印 ASCII 字符串
    %x 打印无符号的十六进制数
    %% 打印百分号;不执行转换

    可以在 % 与字符之间提供某些附加的格式化参数。这些参数进一步改进数值的打印方式:

    参数 说明
    - 将字段中的表达式向左对齐
    ,width 根据需要将字段补齐到指定宽度(前导零使用零将字段补齐)
    .prec 小数点右面数字的最大字符串宽度或最大数量



    转自:http://bbs.linuxtone.org/thread-222-1-1.html


    ----------------------------------------------------
    awk 用法:awk ' pattern {action} '  data

    变量名                含义
    ARGC                命令行变元个数
    ARGV                命令行变元数组
    FILENAME        当前输入文件
    FNR                当前文件中的记录号
    FS                输入域分隔符,默认为一个空格
    RS                输入记录分隔符
    NF                当前记录里域个数
    NR                到目前为止记录数
    OFS                输出域分隔符
    ORS                输出记录分隔符

    1、awk '/101/'               file 显示文件file中包含101的匹配行。
       awk '/101/,/105/'         file
       awk '$1 == 5'             file
       awk '$1 == "CT"'          file 注意必须带双引号
       awk '$1 * $2 >100 '       file 
       awk '$2 >5 && $2<=15'     file
    2、awk '{print NR,NF,$1,$NF,}' file 显示文件file的当前记录号、域数和每一行的第一个和最后一个域。
       awk '/101/ {print $1,$2 + 10}' file 显示文件file的匹配行的第一、二个域加10。
       awk '/101/ {print $1$2}'  file
       awk '/101/ {print $1 $2}' file 显示文件file的匹配行的第一、二个域,但显示时域中间没有分隔符。
    3、df | awk '$4>1000000 '         通过管道符获得输入,如:显示第4个域满足条件的行。
    4、awk -F "|" '{print $1}'   file 按照新的分隔符“|”进行操作。
       awk  'BEGIN { FS="[: \t|]" }
       {print $1,$2,$3}'              file 通过设置输入分隔符(FS="[: \t|]")修改输入分隔符。

       Sep="|"
       awk -F $Sep '{print $1}'  file 按照环境变量Sep的值做为分隔符。   
       awk -F '[ :\t|]' '{print $1}' file 按照正则表达式的值做为分隔符,这里代表空格、:、TAB、|同时做为分隔符。
       awk -F '[][]'    '{print $1}' file 按照正则表达式的值做为分隔符,这里代表[、]
    5、awk -f awkfile              file 通过文件awkfile的内容依次进行控制。
       cat awkfile
    /101/{print "\047 Hello! \047"} --遇到匹配行以后打印 ' Hello! '.\047代表单引号。
    {print $1,$2}                   --因为没有模式控制,打印每一行的前两个域。
    6、awk '$1 ~ /101/ {print $1}' file 显示文件中第一个域匹配101的行(记录)。
    7、awk   'BEGIN { FS="%"}
       {print $1,$2}'           file 通过设置输出分隔符(OFS="%")修改输出格式。
    8、awk   'BEGIN { max=100 ;print "max=" max}             BEGIN 表示在处理任意行之前进行的操作。
       {max=($1 >max ?$1:max); print $1,"Now max is "max}' file 取得文件第一个域的最大值。
       (表达式1?表达式2:表达式3 相当于:
       if (表达式1)
           表达式2
       else
           表达式3
       awk '{print ($1>4 ? "high "$1: "low "$1)}' file 
    9、awk '$1 * $2 >100 {print $1}' file 显示文件中第一个域匹配101的行(记录)。
    10、awk '{$1 == 'Chi' {$3 = 'China'; print}' file 找到匹配行后先将第3个域替换后再显示该行(记录)。
        awk '{$7 %= 3; print $7}'  file 将第7域被3除,并将余数赋给第7域再打印。
    11、awk '/tom/ {wage=$2+$3; printf wage}' file 找到匹配行后为变量wage赋值并打印该变量。
    12、awk '/tom/ {count++;} 
             END {print "tom was found "count" times"}' file END表示在所有输入行处理完后进行处理。
    13、awk 'gsub(/\$/,"");gsub(/,/,""); cost+=$4;
             END {print "The total is $" cost>"filename"}'    file gsub函数用空串替换$和,再将结果输出到filename中。
        1 2 3 $1,200.00
        1 2 3 $2,300.00
        1 2 3 $4,000.00

        awk '{gsub(/\$/,"");gsub(/,/,"");
        if ($4>1000&&$4<2000) c1+=$4;
        else if ($4>2000&&$4<3000) c2+=$4;
        else if ($4>3000&&$4<4000) c3+=$4;
        else c4+=$4; }
        END {printf  "c1=[%d];c2=[%d];c3=[%d];c4=[%d]\n",c1,c2,c3,c4}"' file
        通过if和else if完成条件语句

        awk '{gsub(/\$/,"");gsub(/,/,"");
        if ($4>3000&&$4<4000) exit;
        else c4+=$4; }
        END {printf  "c1=[%d];c2=[%d];c3=[%d];c4=[%d]\n",c1,c2,c3,c4}"' file
        通过exit在某条件时退出,但是仍执行END操作。
        awk '{gsub(/\$/,"");gsub(/,/,"");
        if ($4>3000) next;
        else c4+=$4; }
        END {printf  "c4=[%d]\n",c4}"' file
        通过next在某条件时跳过该行,对下一行执行操作。


    14、awk '{ print FILENAME,$0 }' file1 file2 file3>fileall 把file1、file2、file3的文件内容全部写到fileall中,格式为
        打印文件并前置文件名。
    15、awk ' $1!=previous { close(previous); previous=$1 }   
        {print substr($0,index($0," ") +1)>$1}' fileall 把合并后的文件重新分拆为3个文件。并与原文件一致。
    16、awk 'BEGIN {"date"|getline d; print d}'         通过管道把date的执行结果送给getline,并赋给变量d,然后打印。 
    17、awk 'BEGIN {system("echo \"Input your name:\\c\""); getline d;print "\nYour name is",d,"\b!\n"}'
        通过getline命令交互输入name,并显示出来。
        awk 'BEGIN {FS=":"; while(getline< "/etc/passwd" >0) { if($1~"050[0-9]_") print $1}}'
        打印/etc/passwd文件中用户名包含050x_的用户名。

    18、awk '{ i=1;while(i<NF) {print NF,$i;i++}}' file 通过while语句实现循环。
        awk '{ for(i=1;i<NF;i++) {print NF,$i}}'   file 通过for语句实现循环。    
        type file|awk -F "/" '
        { for(i=1;i<NF;i++)
        { if(i==NF-1) { printf "%s",$i }
        else { printf "%s/",$i } }}'               显示一个文件的全路径。
        用for和if显示日期
        awk  'BEGIN {
    for(j=1;j<=12;j++)
    { flag=0;
      printf "\n%d月份\n",j;
            for(i=1;i<=31;i++)
            {
            if (j==2&&i>28) flag=1;
            if ((j==4||j==6||j==9||j==11)&&i>30) flag=1;
            if (flag==0) {printf "%02d%02d ",j,i}
            }
    }
    }'
    19、在awk中调用系统变量必须用单引号,如果是双引号,则表示字符串
    Flag=abcd
    awk '{print '$Flag'}'   结果为abcd
    awk '{print  "$Flag"}'   结果为$Flag


    转自:http://bbs.chinaunix.net/viewthread.php?tid=691456&extra=page%3D2
  • linux sed用法

    2011-12-06 18:09:11

    linux sed用法  



    今天学习了sed的基本用法,如有不对的地方希望大家指出。.      

             使用sed命令行格式为:
              # sed [-nefri] 'command[aidcsp]' 输入文本        

    常用选项:
           
     -n∶使用安静(silent)模式。在一般 sed 的用法中,所有来自 STDIN的资料一般都会被列出到萤幕上。但如果加上 -n 参数后,则只有经过sed 特殊处理的那一行(或者动作)才会被列出来。
            -e∶直接在指令列模式上进行 sed 的动作编辑;
            -f∶直接将 sed 的动作写在一个档案内, -f filename 则可以执行 filename 内的sed 动作;即通过读取文件脚本执行sed命令
            -r∶sed 的动作支援的是延伸型正规表示法的语法。(预设是基础正规表示法语法)
             -i∶直接修改读取的档案内容,而不是由屏幕输出。      

    常用命令:
            a   ∶新增, a 的后面可以接字串,而这些字串会在新的一行出现(目前的下一行)~

      ∶插入, i 的后面可以接字串,而这些字串会在新的一行出现(目前的上一行);

            d   ∶删除,因为是删除啊,所以 d 后面通常不接任何咚咚;
            c   ∶取代, c 的后面可以接字串,这些字串可以取代 n1,n2 之间的行!
             
     ∶取代,可以直接进行取代的工作哩!通常这个 s 的动作可以搭配正规表示法!例如 1,20s/old/new/g 就是啦!
             p  ∶打印,亦即将某个选择的行打印到屏幕。通常 p 会与参数 sed -n 一起运作~
             

    举例:(假设我们有一文件名为ab)
         删除某行
         [root@localhost ruby# sed '1d' ab              #删除第一行 
         [root@localhost ruby] # sed '$d' ab              #删除最后一行
         [root@localhost ruby] # sed '1,2d' ab           #删除第一行到第二行
         [root@localhost ruby] # sed '2,$d' ab           #删除第二行到最后一行
         显示某行
    .    [root@localhost ruby# sed -n '1p' ab           #显示第一行 
         [root@localhost ruby] # sed -n '$p' ab           #显示最后一行
         [root@localhost ruby] # sed -n '1,2p' ab        #显示第一行到第二行
         [root@localhost ruby] # sed -n '2,$p' ab        #显示第二行到最后一行
         使用模式进行查询
         [root@localhost ruby] # sed -n '/ruby/p' ab    #查询包括关键字ruby所在所有行
         [root@localhost ruby] # sed -n '/\$/p' ab        #查询包括关键字¥所在所有行,使用反斜线\屏蔽特殊含义
         增加一行或多行字符串
         [root@localhost ruby]# cat ab
         Hello!
         ruby is me,welcome to my blog.
         end
         [root@localhost ruby] # sed '1a drink tea' ab  #第一行后增加字符串"drink tea"
         Hello!
         drink tea
         ruby is me,welcome to my blog. 
         end
         [root@localhost ruby] # sed '1,3a drink tea' ab #第一行到第三行后增加字符串"drink tea"
         Hello!
         drink tea
         ruby is me,welcome to my blog.
         drink tea
         end
         drink tea
         [root@localhost ruby] # sed '1a drink tea\nor coffee' ab   #第一行后增加多行,使用换行符\n
         Hello!
         drink tea
         or coffee
         ruby is me,welcome to my blog.
         end
         代替一行或多行
         [root@localhost ruby] # sed '1c Hi' ab                #第一行代替为Hi
         Hi
         ruby is me,welcome to my blog.
         end
         [root@localhost ruby] # sed '1,2c Hi' ab             #第一行到第二行代替为Hi
         Hi
         end
        

     插入:前面的都是改变文件内容输出到屏幕,文件本身内容未被改变,-i则是直接修改文件内容本身
         [root@localhost ruby] # sed -i '$a bye' ab         #在文件ab中最后一行直接输入"bye"
         [root@localhost ruby]# cat ab
         Hello!
         ruby is me,welcome to my blog.
         end
         bye





    ====================================================
    sed的其他用法范例:

    sed用法: 
    sed 'Command' filename(s) 只显示结果而不修改文件

    1、sed    '2,5d'    file 显示文件file,除去2-5行,但行数超过文件实际行数时不会报错。
       sed    '/10[1-4]/d'      file 显示文件file,除去包含101-104的行。
       sed    '2,$d'            file 显示文件,只显示第一行。sed '2,$!d' file则只显示除第一行外的其它行。
       sed    '/^ *$/d          file 删除文件中的空行。
    2、sed    -n '/10[1-4]/p'   file 只显示文件file中包含101-104的行。(-n和p必须同时使用,否则只有p时显示全部文件并多显示一次找到的行)
       sed    -n '5p'           file 只显示文件的第5行
    3、sed 's/moding/moden/g'   file 将moding替换为moden
    4、sed -n 's/^west/north/p' file 将west开头的行替换为north并显示出来。
    5、sed 's/[0-9][0-9][0-9]$/&.5/' file将file文件中以3个数字结尾的行替换为原数字加".5",&代表搜索到的字符串。
    6、sed 's/\(mod\)ing/\1en/g file 将mod做为模式1封装在括号里,然后替换。
       sed 's/...$//'           file 删除每一行的最后三个字符。
       sed 's/^...//'           file 删除每一行的头三个字符。
    7、sed 's#moding#moden#g'   file 将moding替换为moden,s后面的#代表搜索串和替换串之间的分界符。
    8、sed -n '/101/,/105/p'    file 显示从101的匹配行到105的匹配行。如果只找到101的匹配行,则从101的匹配行到文件末。
       sed -n '2,/999/p'        file 显示从第2行到匹配行。
    9、sed '/101/,/105/s/$/  20050119/' file将从101的匹配行到105的匹配行的行末增加"        20050119"内容。
    10、sed -e '1,3d' -e 's/moding/moden/g' file 先删除文件的1-3行,再进行替换。
        sed -e '/^#/!d'         file 显示文件以#开头的行。
    11、sed '/101/r newfile'    file 在每个匹配行增加文件newfile的内容
        sed '/101/w newfile'    file 把匹配行写入newfile。
    12、sed '/101/a\ 
        > ###'                     file 在匹配行后增加一新行。
        sed '/101/i\
        > ###'                    file 在匹配行前增加一新行。
        sed '/101/c\
        > ###'                    file 用新行替换匹配行。

    13、sed 'y/abcd/ABCD/'      file 将a、b、c、d分别替换为ABCD。 
    14、sed '5q'                file 显示到第5行时退出。
    15、sed '/101/{ n; s/moding/moden/g; }' file 在文件中找到匹配行的后一行(n)再进行替换。
        sed '/101/{ s/moding/moden/g; q; }' file 在文件中找到第一个匹配行后进行替换后再退出。
    16、sed -e '/101/{ h; d; }' -e '/104/{ G; }' file 在文件中找到与101匹配行后先存在一个缓存中,再放在与104匹配行后。
        sed -e '/101/{ h; d; }' -e '/104/{ g; }' file 在文件中找到与101匹配行后先存在一个缓存中,再替代104的匹配行。
        sed -e '/101/h' -e '$G'                  file 将最后一个匹配行放在文件末。
        sed -e '/101/h' -e '$g'                  file 将最后一个匹配行替换文件末行。
        sed -e '/101/h' -e '/104/x'              file 在文件中找到与101匹配行后先存在一个缓存中,再与104的匹配行进行互换。
    17、sed -f sfile                             file 根据文件sfile的命令列表进行操作。
        cat sfile
    /101/a\
    ####101####\
    ****101****
    /104/c\
    ####104 deleted####\
    ****104 deleted****
    1i\
    ####test####\
    ****test****



    http://bbs.chinaunix.net/thread-691881-1-1.html






     sed在行首(行尾)添加字符串;在某行后添加多行字符串
    分类: linux shell 2013-03-13 19:17 1013人阅读 评论(0) 收藏 举报
    SHELLLinux

    sed在行首添加字符串;

    sed ‘s/^/xxx/'  filename >output:^符号代表行首

    sed在行尾添加字符串;

    sed ‘s/$/string/' filename>output:$符号代表行尾



    sed在匹配某行后添加一行字符串:

    sed '/string1/c\string1\nstring2' filename>output:用string1替代string1,同时在string1后面加个回车换行后再添加string2


    sed在每行后添加多行:

    先在每一行字符串后面添加一行字符串,然后再用多行替换一行;

    sed 'a\string1'  filename >filename1

    sed '/string1/c\string2\nstring3' filename1>output


    ------------------------------------------------------
    sed 在指定行号的前面增加#,同时直接修改原文件

    [root@testrelease ~]# cat test.txt
    1
    2
    3
    4
    5
    [root@testrelease ~]# sed '2s/^/#/'  test.txt
    1
    #2
    3
    4
    5
    [root@testrelease ~]# cat test.txt
    1
    2
    3
    4
    5
    =====>说明:未修改原文件
    [root@testrelease ~]# sed -i '2s/^/#/'  test.txt
    [root@testrelease ~]# cat test.txt
    1
    #2
    3
    4
    5
    ====>增加 -i 参数后,直接修改原文件

  • 如何在面试时选择合适的测试人员? (转)

    2011-12-06 17:54:39

    [原创]如何在面试时选择合适的测试人员?

     

       各位,大家好!今天分享一下我在面试测试人员时常问的一些问题及为什么,仅供各位参考,谢谢!

    你最近3-5年的职业规划是什么?

       重点考察测试人员的职业发展方向是否与当前职位招聘相符? 从其中可以侧面看出来其员工稳定性。

     

    一个项目测试结束,有没什么经验总结?如果有,具体是如何开展的?

       重点考察测试人员对自己能力提升方面,有没有提高总结的地方,从项目中吸取的经验与教训。从中可以看出来,测试人员是否属行自我驱动型人才!

     

    为什么会选择做测试这份工作?

       重点考察测试人员对待测试工作的态度及是否有发展潜力?面试过很多测试人员,经常见到的回答,自己是女孩子,做测试细心,各位你认为这样回答你会满意吗?其码不是我想要的答案!

     

    请说出一个你以前参与项目,对你测试经验提升很高的,具体是哪方面?

       重点考察测试人员在以往的测试工作中能力提升方面,有哪些?然后重点询问此部分内容,是否测试经验增长,具备一定的深度?

     

    通常做测试时会碰到,提交的某个bug开发人员不认同你的观点?这时你如何办?

       重点考察测试人员是否坚持自已的价值观?是否具备协调沟通处理问题能力?

     

    6有没有看过什么测试书,具体是哪本?带给你的收获是?

      重点考察测试人员是否为测试这个职业肯付出多少?从中也可以看出这个测试人员是否上进心?是否有求知心?我的定义是如果哪个应聘者来面试时,都没系统的看过一本测试书籍,基本上不会录取!

     

    如果安排一项测试技术研究工作,你如何应对?

    重点考察测试人员是否具体测试技术专研精神?是否喜欢接受挑战?是否属于以后培养骨干对象?

     

    某个项目上线后,出现问题,恰巧你是负责的,你如何应对这突如其来的事件?

    重点考察测试人员应对问题的压力,责任感,及如何处理项目上线后的技术问题及应对解决能力。

     

    周末放假有什么业余爱好?

       重点考察面试测试人员性格特质,测试工作本身就是复杂且富有技术性的工作,而且不同的职位所需要的测试人员性格品质差异性很大。

     

    10 公司产品,具体应用什么编程技术?具体的架构是?具体的应用场景有哪些?

       重点考察测试人员对以往的工作所负责的产品测试,是否具备一定的深度!通常我都是让面试者自己讲述或是在纸上画出具体系统架构的图!

     

    11 公司测试团队的规模如何,具体你所处的角色是什么?

       重点考察测试人员在以往的公司测试团队中,具体的工作职责,评判其工作是否与当要求职位是否符合?是否有哪些优缺点?

     

    12 特定测试技术考察:性能测试,安全性测试,自动化测试等以前有开展过没?如果有,具体是如何实施的?

       重点考察测试人员技术能力,是否在各方面都有所涉及?或是在各方面技术上都有一定深度?当然从中也能看出一个测试人员是否属于是技术路线发展方向!

     

    13你自己所期待加入的测试团队是什么样的?

       重点考察测试人员在以前测试团队中有哪些不协调?当然最重要的是也能提供给你一些信息,这个员工以后如何更好的管理与沟通!


    转自:http://www.cnblogs.com/mayingbao/archive/2011/12/01/2270452.html



    HttpWatch工具简介及使用技巧

    http://www.cnblogs.com/mayingbao/archive/2007/11/30/978530.html
  • 浏览器是如何工作的?(工作原理)(三)

    2011-12-06 17:29:02


    对规则进行处理以简化匹配过程

    样式规则有几个来源:

    · 外部样式表或style标签内的css规则

    · 行内样式属性

    · html可视化属性(映射为相应的样式规则)

    后面两个很容易匹配到元素,因为它们所拥有的样式属性和html属性可以将元素作为key进行映射。

    就像前面问题2所提到的,css的规则匹配可能很狡猾,为了解决这个问题,可以先对规则进行处理,以使其更容易被访问。

    解析完样式表之后,规则会根据选择符添加一些hash映射,映射可以是根据id、class、标签名或是任何不属于这些分类的综合映射。如果选择符为id,规则将被添加到id映射,如果是class,则被添加到class映射,等等。

    这个处理是匹配规则更容易,不需要查看每个声明,我们能从映射中找到一个元素的相关规则,这个优化使在进行规则匹配时减少了95+%的工作量。

    来看下面的样式规则:

    p.error {color:red}

    #messageDiv {height:50px}

    div {margin:5px}

    第一条规则将被插入class映射,第二条插入id映射,第三条是标签映射。

    下面这个html片段:

    <p class=”error”>an error occurred </p>

    <div id=” messageDiv”>this is a message</div>

    我们首先找到p元素对应的规则,class映射将包含一个“error”的key,找到p.error的规则,div在id映射和标签映射中都有相关的规则,剩下的工作就是找出这些由key对应的规则中哪些确实是正确匹配的。

    例如,如果div的规则是

    table div {margin:5px}

    这也是标签映射产生的,因为key是最右边的选择符,但它并不匹配这里的div元素,因为这里的div没有table祖先。

    Webkit和Firefox都会做这个处理。

    以正确的级联顺序应用规则

    样式对象拥有对应所有可见属性的属性,如果特性没有被任何匹配的规则所定义,那么一些特性可以从parent的样式对象中继承,另外一些使用默认值。

    这个问题的产生是因为存在不止一处的定义,这里用级联顺序解决这个问题。

    样式表的级联顺序

    一个样式属性的声明可能在几个样式表中出现,或是在一个样式表中出现多次,因此,应用规则的顺序至关重要,这个顺序就是级联顺序。根据css2的规范,级联顺序为(从低到高):

    1. 浏览器声明

    2. 用户声明

    3. 作者的一般声明

    4. 作者的important声明

    5. 用户important声明

    浏览器声明是最不重要的,用户只有在声明被标记为important时才会覆盖作者的声明。具有同等级别的声明将根据specifity以及它们被定义时的顺序进行排序。Html可视化属性将被转换为匹配的css声明,它们被视为最低优先级的作者规则。

    Specifity

    Css2规范中定义的选择符specifity如下:

    · 如果声明来自style属性,而不是一个选择器的规则,则计1,否则计0(=a)

    · 计算选择器中id属性的数量(=b)

    · 计算选择器中class及伪类的数量(=c)

    · 计算选择器中元素名及伪元素的数量(=d)

    连接a-b-c-d四个数量(用一个大基数的计算系统)将得到specifity。这里使用的基数由分类中最高的基数定义。例如,如果a为14,可以使用16进制。不同情况下,a为17时,则需要使用阿拉伯数字17作为基数,这种情况可能在这个选择符时发生html body div div …(选择符中有17个标签,一般不太可能)。

    一些例子:

    * {} /* a=0 b=0 c=0 d=0 -> specificity = 0,0,0,0 */

    li {} /* a=0 b=0 c=0 d=1 -> specificity = 0,0,0,1 */

    li:first-line {} /* a=0 b=0 c=0 d=2 -> specificity = 0,0,0,2 */

    ul li {} /* a=0 b=0 c=0 d=2 -> specificity = 0,0,0,2 */

    ul ol+li {} /* a=0 b=0 c=0 d=3 -> specificity = 0,0,0,3 */

    h1 + *[rel=up]{} /* a=0 b=0 c=1 d=1 -> specificity = 0,0,1,1 */

    ul ol li.red {} /* a=0 b=0 c=1 d=3 -> specificity = 0,0,1,3 */

    li.red.level {} /* a=0 b=0 c=2 d=1 -> specificity = 0,0,2,1 */

    #x34y {} /* a=0 b=1 c=0 d=0 -> specificity = 0,1,0,0 */

    style=”” /* a=1 b=0 c=0 d=0 -> specificity = 1,0,0,0 */

    规则排序

    规则匹配后,需要根据级联顺序对规则进行排序,webkit先将小列表用冒泡排序,再将它们合并为一个大列表,webkit通过为规则复写“>”操作来执行排序:

    static bool operator >(CSSRuleData& r1, CSSRuleData& r2)

    {

    int spec1 = r1.selector()->specificity();

    int spec2 = r2.selector()->specificity();

    return (spec1 == spec2) : r1.position() > r2.position() : spec1 > spec2;

    }

    逐步处理 Gradual process

    webkit使用一个标志位标识所有顶层样式表都已加载,如果在attch时样式没有完全加载,则放置占位符,并在文档中标记,一旦样式表完成加载就重新进行计算。

    布局 Layout

    当渲染对象被创建并添加到树中,它们并没有位置和大小,计算这些值的过程称为layout或reflow。

    Html使用基于流的布局模型,意味着大部分时间,可以以单一的途径进行几何计算。流中靠后的元素并不会影响前面元素的几何特性,所以布局可以在文档中从右向左、自上而下的进行。也存在一些例外,比如html tables。

    坐标系统相对于根frame,使用top和left坐标。

    布局是一个递归的过程,由根渲染对象开始,它对应html文档元素,布局继续递归的通过一些或所有的frame层级,为每个需要几何信息的渲染对象进行计算。

    根渲染对象的位置是0,0,它的大小是viewport-浏览器窗口的可见部分。

    所有的渲染对象都有一个layout或reflow方法,每个渲染对象调用需要布局的children的layout方法。

    Dirty bit 系统

    为了不因为每个小变化都全部重新布局,浏览器使用一个dirty bit系统,一个渲染对象发生了变化或是被添加了,就标记它及它的children为dirty-需要layout。存在两个标识-dirty及children are dirty,children are dirty说明即使这个渲染对象可能没问题,但它至少有一个child需要layout。

    全局和增量 layout

    当layout在整棵渲染树触发时,称为全局layout,这可能在下面这些情况下发生:

    1. 一个全局的样式改变影响所有的渲染对象,比如字号的改变

    2. 窗口resize

    layout也可以是增量的,这样只有标志为dirty的渲染对象会重新布局(也将导致一些额外的布局)。增量 layout会在渲染对象dirty时异步触发,例如,当网络接收到新的内容并添加到Dom树后,新的渲染对象会添加到渲染树中。

    图20:增量 layout

    异步和同步layout

    增量layout的过程是异步的,Firefox为增量layout生成了reflow队列,以及一个调度执行这些批处理命令。Webkit也有一个计时器用来执行增量layout-遍历树,为dirty状态的渲染对象重新布局。

    另外,当脚本请求样式信息时,例如“offsetHeight”,会同步的触发增量布局。

    全局的layout一般都是同步触发。

    有些时候,layout会被作为一个初始layout之后的回调,比如滑动条的滑动。

    优化

    当一个layout因为resize或是渲染位置改变(并不是大小改变)而触发时,渲染对象的大小将会从缓存中读取,而不会重新计算。

    一般情况下,如果只有子树发生改变,则layout并不从根开始。这种情况发生在,变化发生在元素自身并且不影响它周围元素,例如,将文本插入文本域(否则,每次击键都将触发从根开始的重排)。

    layout过程

    layout一般有下面这几个部分:

    1. parent渲染对象决定它的宽度

    2. parent渲染对象读取chilidren,并:

    1. 放置child渲染对象(设置它的x和y)

    2. 在需要时(它们当前为dirty或是处于全局layout或者其他原因)调用child渲染对象的layout,这将计算child的高度

    3. parent渲染对象使用child渲染对象的累积高度,以及margin和padding的高度来设置自己的高度-这将被parent渲染对象的parent使用

    4. 将dirty标识设置为false

    Firefox使用一个“state”对象(nsHTMLReflowState)做为参数去布局(firefox称为reflow),state包含parent的宽度及其他内容。

    Firefox布局的输出是一个“metrics”对象(nsHTMLReflowMetrics)。它包括渲染对象计算出的高度。

    宽度计算

    渲染对象的宽度使用容器的宽度、渲染对象样式中的宽度及margin、border进行计算。例如,下面这个div的宽度:

    <div style=”width:30%”/>

    webkit中宽度的计算过程是(RenderBox类的calcWidth方法):

    · 容器的宽度是容器的可用宽度和0中的最大值,这里的可用宽度为:contentWidth=clientWidth()-paddingLeft()-paddingRight(),clientWidth和clientHeight代表一个对象内部的不包括border和滑动条的大小

    · 元素的宽度指样式属性width的值,它可以通过计算容器的百分比得到一个绝对值

    · 加上水平方向上的border和padding

    到这里是最佳宽度的计算过程,现在计算宽度的最大值和最小值,如果最佳宽度大于最大宽度则使用最大宽度,如果小于最小宽度则使用最小宽度。最后缓存这个值,当需要layout但宽度未改变时使用。

    Line breaking

    当一个渲染对象在布局过程中需要折行时,则暂停并告诉它的parent它需要折行,parent将创建额外的渲染对象并调用它们的layout。

    绘制 Painting

    绘制阶段,遍历渲染树并调用渲染对象的paint方法将它们的内容显示在屏幕上,绘制使用UI基础组件,这在UI的章节有更多的介绍。

    全局和增量

    和布局一样,绘制也可以是全局的-绘制完整的树-或增量的。在增量的绘制过程中,一些渲染对象以不影响整棵树的方式改变,改变的渲染对象使其在屏幕上的矩形区域失效,这将导致操作系统将其看作dirty区域,并产生一个paint事件,操作系统很巧妙的处理这个过程,并将多个区域合并为一个。Chrome中,这个过程更复杂些,因为渲染对象在不同的进程中,而不是在主进程中。Chrome在一定程度上模拟操作系统的行为,表现为监听事件并派发消息给渲染根,在树中查找到相关的渲染对象,重绘这个对象(往往还包括它的children)。

    绘制顺序

    css2定义了绘制过程的顺序-http://www.w3.org/TR/CSS21/zindex.html。这个就是元素压入堆栈的顺序,这个顺序影响着绘制,堆栈从后向前进行绘制。

    一个块渲染对象的堆栈顺序是:

    1. 背景色

    2. 背景图

    3. border

    4. children

    5. outline

    Firefox显示列表

    Firefox读取渲染树并为绘制的矩形创建一个显示列表,该列表以正确的绘制顺序包含这个矩形相关的渲染对象。

    用这样的方法,可以使重绘时只需查找一次树,而不需要多次查找——绘制所有的背景、所有的图片、所有的border等等。

    Firefox优化了这个过程,它不添加会被隐藏的元素,比如元素完全在其他不透明元素下面。

    Webkit矩形存储

    重绘前,webkit将旧的矩形保存为位图,然后只绘制新旧矩形的差集。

    动态变化

    浏览器总是试着以最小的动作响应一个变化,所以一个元素颜色的变化将只导致该元素的重绘,元素位置的变化将大致元素的布局和重绘,添加一个Dom节点,也会大致这个元素的布局和重绘。一些主要的变化,比如增加html元素的字号,将会导致缓存失效,从而引起整数的布局和重绘。

    渲染引擎的线程

    渲染引擎是单线程的,除了网络操作以外,几乎所有的事情都在单一的线程中处理,在Firefox和Safari中,这是浏览器的主线程,Chrome中这是tab的主线程。

    网络操作由几个并行线程执行,并行连接的个数是受限的(通常是2-6个)。

    事件循环

    浏览器主线程是一个事件循环,它被设计为无限循环以保持执行过程的可用,等待事件(例如layout和paint事件)并执行它们。下面是Firefox的主要事件循环代码。

    while (!mExiting)

    NS_ProcessNextEvent(thread);

    CSS2 可视模型 CSS2 visual module

    画布 The Canvas

    根据CSS2规范,术语canvas用来描述格式化的结构所渲染的空间——浏览器绘制内容的地方。画布对每个维度空间都是无限大的,但浏览器基于viewport的大小选择了一个初始宽度。

    根据http://www.w3.org/TR/CSS2/zindex.html的定义,画布如果是包含在其他画布内则是透明的,否则浏览器会指定一个颜色。

    CSS盒模型

    CSS盒模型描述了矩形盒,这些矩形盒是为文档树中的元素生成的,并根据可视的格式化模型进行布局。每个box包括内容区域(如图片、文本等)及可选的四周padding、border和margin区域。

    每个节点生成0-n个这样的box。

    所有的元素都有一个display属性,用来决定它们生成box的类型,例如:

    block-生成块状box

    inline-生成一个或多个行内box

    none-不生成box

    默认的是inline,但浏览器样式表设置了其他默认值,例如,div元素默认为block。可以访问http://www.w3.org/TR/CSS2/sample.html查看更多的默认样式表示例。

    定位策略 Position scheme

    这里有三种策略:

    1. normal-对象根据它在文档的中位置定位,这意味着它在渲染树和在Dom树中位置一致,并根据它的盒模型和大小进行布局

    2. float-对象先像普通流一样布局,然后尽可能的向左或是向右移动

    3. absolute-对象在渲染树中的位置和Dom树中位置无关

    static和relative是normal,absolute和fixed属于absolute。

    在static定位中,不定义位置而使用默认的位置。其他策略中,作者指定位置——top、bottom、left、right。

    Box布局的方式由这几项决定:box的类型、box的大小、定位策略及扩展信息(比如图片大小和屏幕尺寸)。

    Box类型

    Block box:构成一个块,即在浏览器窗口上有自己的矩形

    Inline box:并没有自己的块状区域,但包含在一个块状区域内

    block一个挨着一个垂直格式化,inline则在水平方向上格式化。

    Inline盒模型放置在行内或是line box中,每行至少和最高的box一样高,当box以baseline对齐时——即一个元素的底部和另一个box上除底部以外的某点对齐,行高可以比最高的box高。当容器宽度不够时,行内元素将被放到多行中,这在一个p元素中经常发生。

    定位 Position

    Relative

    相对定位——先按照一般的定位,然后按所要求的差值移动。

    Floats

    一个浮动的box移动到一行的最左边或是最右边,其余的box围绕在它周围。下面这段html:

    <p>

    <img style=”float:right” src=”images/image.gif” width=”100″ height=”100″>Lorem ipsum dolor sit amet, consectetuer…

    </p>

    将显示为:

    Absolute和Fixed

    这种情况下的布局完全不顾普通的文档流,元素不属于文档流的一部分,大小取决于容器。Fixed时,容器为viewport(可视区域)。

    图17:fixed

    注意-fixed即使在文档流滚动时也不会移动。

    Layered representation

    这个由CSS属性中的z-index指定,表示盒模型的第三个大小,即在z轴上的位置。Box分发到堆栈中(称为堆栈上下文),每个堆栈中靠后的元素将被较早绘制,栈顶靠前的元素离用户最近,当发生交叠时,将隐藏靠后的元素。堆栈根据z-index属性排序,拥有z-index属性的box形成了一个局部堆栈,viewport有外部堆栈,例如:

    <STYLE. type=”text/css”>

    div {

    position: absolute;

    left: 2in;

    top: 2in;

    }

    </STYLE>

    <P>

    <DIV

    style=”z-index: 3;background-color:red; width: 1in; height: 1in; “>

    </DIV>

    <DIV

    style=”z-index: 1;background-color:green;width: 2in; height: 2in;”>

    </DIV>

    </p>

    结果是:

    虽然绿色div排在红色div后面,可能在正常流中也已经被绘制在后面,但z-index有更高优先级,所以在根box的堆栈中更靠前。

    国外也有网友根据浏览器的工作原理绘制了几张工作流程图,方便大家通过简易的图片来了解这个辛苦的过程:

    浏览器工作原理

    原文:http://taligarsiel.com/Projects/howbrowserswork1.htm
    编译:zzzaquarius

Open Toolbar