Bash脚本检查特定进程的CPU使用情况

问题描述:

首先,我是新手。我有一些Windows脚本和苹果脚本的经验,但没有太多与bash。我想要做的是抓住特定进程的PID和%CPU。然后将%CPU与设定的数字进行比较,如果更高,则杀死进程。我觉得我很接近,但现在我发现了以下错误:Bash脚本检查特定进程的CPU使用情况

[:0.0:语法错误:无效的算术运算符(错误标记为” .0" )

我在做什么错误?这是我到目前为止的代码:

#!/bin/bash 
declare -i app_pid 
declare -i app_cpu 
declare -i cpu_limit 
app_name="top" 
cpu_limit="50" 
app_pid=`ps aux | grep $app_name | grep -v grep | awk {'print $2'}` 
app_cpu=`ps aux | grep $app_name | grep -v grep | awk {'print $3'}` 
if [[ ! $app_cpu -gt $cpu_limit ]]; then 
    echo "crap" 
else 
    echo "we're good" 
fi 

很显然,我要替代回声中的if/then语句,但它的作用就好像不管什么样的CPU负载实际上是说法是正确的(我测试这个由改变-gt到-lt,它仍然回荡“废话”

谢谢所有帮助。呵呵,这是在OS X 10.7,如果这是非常重要的。

的问题是可以的bash处理小数,你可以乘以100,并用普通整数代替:

#!/bin/bash 
declare -i app_pid 
declare -i app_cpu 
declare -i cpu_limit 
app_name="top" 
cpu_limit="5000" 
app_pid=`ps aux | grep $app_name | grep -v grep | awk {'print $2'}` 
app_cpu=`ps aux | grep $app_name | grep -v grep | awk {'print $3*100'}` 
if [[ $app_cpu -gt $cpu_limit ]]; then 
    echo "crap" 
else 
    echo "we're good" 
fi 

请记住,CPU百分比是应用程序运行状况的次优度量。如果您有两个进程在单个核心系统上运行无限循环,那么即使他们正在垃圾周围,同样优先级的其他应用程序也不会超过33%。

+0

感谢大家的帮助! 至于CPU的百分比,我们实际上有一个过程,开始吃掉CPU,得到100-200%,然后阻止用户登录到计算机,杀死进程导致它重新启动并坐在.1%为很长时间。 我打算让这个按需运行的启动守护进程运行,所以它应该终止进程,所以用户不必在屏幕锁定时重新启动1/3-1/2。 – user2073780 2013-02-15 14:32:43

我建议看看ps的设施,以避免多重可怕的事情。

在我的系统(ps从procps的Linux上,GNU AWK)我会做到这一点:

ps -C "$app-name" -o pid=,pcpu= | 
    awk --assign maxcpu="$cpu_limit" '$2>maxcpu {print "crappy pid",$1}' 

我用top检查一些细节。它提供了更多的细节,如CPU时间。

top -l 1 | grep $app_name 

我想出了这个,使用顶部和bc。

通过传递前使用它:./script apache2 50 # max 50%

如果有很多的PID匹配你的程序的说法,只有一个会被计算的基础上,如何顶部列出。我本来可以通过抓住他们所有人并扩大比例或其他东西来扩展脚本,但这必须做到。

您也可以传入一个数字./script.sh 12345 50,这将强制它使用确切的PID。

#!/bin/bash 

# 1: ['command\ name' or PID number(,s)] 2: MAX_CPU_PERCENT 

[[ $# -ne 2 ]] && exit 1 
PID_NAMES=$1 
# get all PIDS as nn,nn,nn 
if [[ ! "$PID_NAMES" =~ ^[0-9,]+$ ]] ; then 
    PIDS=$(pgrep -d ',' -x $PID_NAMES) 
else 
    PIDS=$PID_NAMES 
fi 
# echo "$PIDS $MAX_CPU" 
MAX_CPU="$2" 
MAX_CPU="$(echo "($MAX_CPU+0.5)/1" | bc)" 
LOOP=1 
while [[ $LOOP -eq 1 ]] ; do 
    sleep 0.3s 
    # Depending on your 'top' version and OS you might have 
    # to change head and tail line-numbers 
    LINE="$(top -b -d 0 -n 1 -p $PIDS | head -n 8 \ 
     | tail -n 1 | sed -r 's/[ ]+/,/g' | \ 
     sed -r 's/^\,|\,$//')" 
    # If multiple processes in $PIDS, $LINE will only match\ 
    # the most active process 
    CURR_PID=$(echo "$LINE" | cut -d ',' -f 1) 
    # calculate cpu limits 
    CURR_CPU_FLOAT=$(echo "$LINE"| cut -d ',' -f 9) 
    CURR_CPU=$(echo "($CURR_CPU_FLOAT+0.5)/1" | bc) 
    echo "PID $CURR_PID: $CURR_CPU""%" 
    if [[ $CURR_CPU -ge $MAX_CPU ]] ; then 
     echo "PID $CURR_PID ($PID_NAMES) went over $MAX_CPU""%" 
     echo "[[ $CURR_CPU""% -ge $MAX_CPU""% ]]" 
     LOOP=0 
     break 
    fi 
done 
echo "Stopped" 

Erik,我用你的代码的修改版本来创建一个类似的新脚本。希望你不介意。

bash脚本的过程 使用,以获得CPU使用率:

nohup ./check_proc bwengine 70 & 

bwegnine是我们希望在进程正在使用CPU的70%以上,以监控70只登录进程名称。

检查日志在:/var/log/check_procs.log

输出应该是这样的:

DATE | TOTAL CPU | CPU USAGE | Process details 

例子:

03/12/14 17:11 |20.99|98| ProdPROXY-ProdProxyPA.tra 

03/12/14 17:11 |20.99|100| ProdPROXY-ProdProxyPA.tra 

链接到完整的博客: http://felipeferreira.net/?p=1453

这是也有用app_user信息可用于测试当前用户是否有权终止/修改正在运行的进程。可以通过使用read消除awk或任何其他第三方解析器的需要与必要app_pidapp_cpu获得沿着这条信息:

read app_user app_pid tmp_cpu stuff <<< \ 
$(ps aux | grep "$app_name" | grep -v "grep\|defunct\|${0##*/}") 

然后,您可以让您的app_cpu * 100有:

app_cpu=$((${tmp_cpu%.*} * 100)) 

注:包括defunct${0##*/}grep -v防止多个进程匹配$app_name

#!/bin/sh 
PROCESS="java" 
PID=`pgrep $PROCESS | tail -n 1` 
CPU=`top -b -p $PID -n 1 | tail -n 1 | awk '{print $9}'` 
echo $CPU