美文网首页
服务器load average异常

服务器load average异常

作者: 陈兄 | 来源:发表于2021-08-20 08:57 被阅读0次

    4核16G的设备,正常load average不大于4,表示系统一直处在负载状态,程序有异常。

    每日服务器性能邮件告警

    4核16G的服务器,load率达到了 6.97, 6.70, 4.87.

    信息总览:
    
    CPU 内核:4核
    
    CPU load率: 6.97, 6.70, 4.87
    
    总内存:15.3 GiB    使用内存:4.7 GiB    剩余内存:10.600000000000001GiB
    
    TOP前5:
         PID         %CPU    %MEM    VSZ          RSS             Name
        2805176      59.9      6.3       7.6 GiB     986.2 MiB     java
        2901828      13.1      5.4       4.1 GiB     847.4 MiB     java
        3532650       4.5      4.7       3.9 GiB     740.9 MiB     java
        3769112       3.0      4.2       5.5 GiB     657.7 MiB     java
        1619371       0.7      1.3       6.6 GiB     204.8 MiB     java
    

    注意:CPU load率: 6.97, 6.70, 4.87。load的平均值通过3个时间间隔来展示,就是我们看到的1分钟、5分钟、15分钟,load值和cpu核数有关,单核cpu的load=1表示系统一直处在负载状态,但是4核cpu的load=1表示系统有75%的空闲。

    load高可能的一些原因

    系统load高通常都是由于某段发布的代码有bug或者引入某些第三方jar而又使用不合理导致的,因此注意首先区分load高,是由于cpu高导致的还是io高导致的,根据不同的场景采取不同定位问题的方式。

    • 死循环或者不合理的大量循环操作,如果不是循环操作,按照现代cpu的处理速度来说处理一大段代码也就一会会儿的事,基本对能力无消耗
    • 频繁的YoungGC
    • 频繁的FullGC
    • 高磁盘IO
    • 高网络IO

    当束手无策时,jmap打印堆栈文件多分析分析吧,或许能灵光一现能找到错误原因。

    发现YongGC块,FullGC也快,注定有问题

    jstat gcutil pid 100
    
    image

    可以看出行O也一直在增加,几乎99,速度很快,老年代一下就满了,立马执行了YongGC,然后进入FGC的速度也快,2天就525了。

    进一步排查获取dump文件

    通过命令抓取dump文件,进行分析。

    jmap -dump:format=b,file=1.hprof pid
    

    分析dump文件

    通过JProfiler分析1.hprof文件

    image
    image
    image

    上述分析结果可以直观的看出,创建的对象线程非常多,并且一直在加,释放很慢。

    代码分析

    发现程序确实有类似代码

    
        /**
         * Provide a new ScheduledExecutorService instance.
         *
         * <p>A shutdown hook is created to terminate the thread pool on application termination.
         *
         * @return new ScheduledExecutorService
         */
        public static ScheduledExecutorService defaultExecutorService() {
            ScheduledExecutorService scheduledExecutorService =
                    Executors.newScheduledThreadPool(getCpuCount());
    
            Runtime.getRuntime().addShutdownHook(new Thread(() -> shutdown(scheduledExecutorService)));
    
            return scheduledExecutorService;
        }
    

    因为此方法是通过一个业务定时器在轮序,2秒一次,每次都去执行了一次,所以造成了内存不足,load值增加,系统负载增加。

    解决方法

    代码解决

    程序改用单例模式,静态方法,执行一次就行。

    jvm调优优化

    • -XX:MaxTenuringThreshold
    • -XX:+ UseConcMarkSweepGC
    • -XX:CMSFullGCsBeforeCompaction
      具体参数详情请参考[性能调优参数]

    调优案例

    -XX:MaxTenuringThreshold=0 -XX:+UseConcMarkSweepGC -XX:CMSFullGCsBeforeCompaction=0
    

    相关文章

      网友评论

          本文标题:服务器load average异常

          本文链接:https://www.haomeiwen.com/subject/oucabltx.html