V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
AnjingJingan
V2EX  ›  程序员

Linux 进程挂起问题

  •  
  •   AnjingJingan · 2022-05-17 16:44:03 +08:00 · 1137 次点击
    这是一个创建于 681 天前的主题,其中的信息可能已经有所发展或是发生改变。

    线上生产环境用 shell 脚本并发执行 php ,时间长了几乎每个脚本都有大量睡眠状态的进程一直挂在后台,像这样

    O4qhsU.png

    8 号唤起的进程还挂在后台

    以 994032 为例,用 strace 查看状态返回:

    strace -p 994032
    strace: Process 994032 attached
    futex(0x563cb97ec830, FUTEX_WAIT_PRIVATE, 2, NUL
    

    Google 了 FUTEX_WAIT_PRIVATE 说是等待唤醒,但是如果不 kill 的话永远不会唤醒

    查看运行时间:

    ps -p 994032 -p etime
        ELAPSED
     8-21:56:58
    

    shell 脚本长这样
    #!/bin/bash  
    
    pid=$$
    name=`basename $0`
    ps -ef|awk -v p=$pid -v n=$name '$2!=p && $NF~n{system("kill "p)}'  #禁止重复运行
    
    ids=$(/usr/bin/php /www/wwwroot/index_cli.php UploadImag/get_id)  #获取 id ,一般会返回几万个 ID ,格式是这样的 (1 2 3 5 6 7) 
    
    temp_fifo_file=$$.info        #以当前进程号,为临时管道取名
    mkfifo $temp_fifo_file        #创建临时管道
    exec 6<>$temp_fifo_file       #创建标识为 6 ,可以对管道进行读写
    rm $temp_fifo_file            #清空管道内容
    
    
    temp_thread=80                 #进程数
    
    for ((i=0;i<temp_thread;i++)) #为进程创建相应的占位
    do
      echo                        #每个 echo 输出一个回车,为每个进程创建一个占位
    done >&6                      #将占位信息写入标识为 6 的管道
    
    for loop in $ids
    do
      read                        #获取标识为 6 的占位
      {
    
    	/usr/bin/php /www/wwwroot/index_cli.php UploadImag/upload_img/id/$loop  #后台执行抓取程序
    
        echo >&6                  #>>>>>当任务执行完后,会释放管道占位,所以补充一个占位
      }&                          #>>>>>在后台执行{}中的任务
    done <&6                      #将标识为 6 的管道作为标准输入
    
    wait                          #等待所有任务完成
    exec 6>&-                     #关闭标识为 6 的管道
    
    

    定时任务调度方式
    */5 * * * * /bin/sh /www/wwwroot/cron/UploadImag.sh
    

    项目用 thinkphp3.1 写的历史老项目,脚本也是前人留下来的,要并发执行的时候就复制一下这个 shell 脚本模板,改一下里面的参数

    发展到现在已经有几百个这样的 shell 脚本,几乎全部存在进程卡住的情况

    系统是 centos7

    php5.4 版本

    请教这种进程卡住的情况应该怎么解决?

    8 条回复    2022-11-25 21:26:50 +08:00
    zhoudaiyu
        1
    zhoudaiyu  
       2022-05-17 23:59:41 +08:00 via iPhone
    strace -fp 994032 看看
    xyjincan
        2
    xyjincan  
       2022-05-18 05:31:51 +08:00 via Android
    有些系统资源可能默认有限,不够了,ulimit -a
    AnjingJingan
        3
    AnjingJingan  
    OP
       2022-05-18 09:17:24 +08:00
    @xyjincan ulimit -a
    core file size (blocks, -c) 0
    data seg size (kbytes, -d) unlimited
    scheduling priority (-e) 0
    file size (blocks, -f) unlimited
    pending signals (-i) 513912
    max locked memory (kbytes, -l) 64
    max memory size (kbytes, -m) unlimited
    open files (-n) 1024
    pipe size (512 bytes, -p) 8
    POSIX message queues (bytes, -q) 819200
    real-time priority (-r) 0
    stack size (kbytes, -s) 8192
    cpu time (seconds, -t) unlimited
    max user processes (-u) 513912
    virtual memory (kbytes, -v) unlimited
    file locks (-x) unlimited
    AnjingJingan
        4
    AnjingJingan  
    OP
       2022-05-18 09:26:42 +08:00
    @zhoudaiyu 994032 kill 了,换了个同样情况的 pid
    strace: Process 911015 attached
    futex(0x56260c3e7af0, FUTEX_WAIT_PRIVATE, 2, NULL
    zhoudaiyu
        5
    zhoudaiyu  
       2022-05-18 10:14:02 +08:00
    @AnjingJingan #4 我的意思是追踪的时候加上参数 f ,这样可以跟踪子进程 /线程的系统调用
    AnjingJingan
        6
    AnjingJingan  
    OP
       2022-05-18 11:34:55 +08:00
    @zhoudaiyu 加了 f 也是返回这个,4 楼回复就是加了 f 的
    strace -fp 911015
    strace: Process 911015 attached
    futex(0x56260c3e7af0, FUTEX_WAIT_PRIVATE, 2, NULL
    julyclyde
        7
    julyclyde  
       2022-05-18 12:40:10 +08:00
    @xyjincan 肯定不是 rlmit 的问题啊;而且你用 ulimit 看的是自己 shell 的 rlimit ,并不是这个后台进程的 rlimit
    AnjingJingan
        8
    AnjingJingan  
    OP
       2022-11-25 21:26:50 +08:00
    shell 脚本换了个执行用户,只要使用非 root 用户执行,就不会出现这种现象
    不清楚原理,记录一下。。。
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   我们的愿景   ·   实用小工具   ·   1737 人在线   最高记录 6543   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 26ms · UTC 16:38 · PVG 00:38 · LAX 09:38 · JFK 12:38
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.