【发布时间】:2014-05-04 13:02:01
【问题描述】:
我有一个进程会产生一些其他进程,
我想在特定进程上使用time 命令并获得与time 命令相同的输出。
这可能吗?如何实现?
【问题讨论】:
-
如果您“在特定进程上使用
time命令”,您不会根据定义“获得与time命令相同的输出”吗? -
不是吗?肯定不是它的用户时间。
我有一个进程会产生一些其他进程,
我想在特定进程上使用time 命令并获得与time 命令相同的输出。
这可能吗?如何实现?
【问题讨论】:
time 命令”,您不会根据定义“获得与time 命令相同的输出”吗?
我想在特定进程上使用 time 命令并获得与 time 命令相同的输出。
可能只使用pidstat 来获取用户和系统时间就足够了:
$ pidstat -p 30122 1 4
Linux 2.6.32-431.el6.x86_64 (hostname) 05/15/2014 _x86_64_ (8 CPU)
04:42:28 PM PID %usr %system %guest %CPU CPU Command
04:42:29 PM 30122 706.00 16.00 0.00 722.00 3 has_serverd
04:42:30 PM 30122 714.00 12.00 0.00 726.00 3 has_serverd
04:42:31 PM 30122 714.00 14.00 0.00 728.00 3 has_serverd
04:42:32 PM 30122 708.00 16.00 0.00 724.00 3 has_serverd
Average: 30122 710.50 14.50 0.00 725.00 - has_serverd
如果不是,则根据 strace time 使用 wait4 系统调用 (http://linux.die.net/man/2/wait4) 从内核获取有关进程的信息。相同的信息返回 getrusage,但您不能根据其文档 (http://linux.die.net/man/2/getrusage) 为任意进程调用它。
所以,我不知道任何可以提供相同输出的命令。但是,创建一个 bash 脚本来获取特定进程的 PID 并输出类似 time outpus 的内容是可行的
此脚本执行以下步骤:
1) 获取每秒时钟滴答数
getconf CLK_TCK
我假设它是 100 并且 1 滴答等于 10 毫秒。
2) 然后在目录/proc/YOUR-PID存在的情况下循环执行相同的命令序列:
while [ -e "/proc/YOUR-PID" ];
do
read USER_TIME SYS_TIME REAL_TIME <<< $(cat /proc/PID/stat | awk '{print $14, $15, $22;}')
sleep 0.1
end loop
一些解释-根据man proc:
user time: ($14) - utime - Amount of time that this process has been scheduled in user mode, measured in clock ticks
sys time: ($15) - stime - Amount of time that this process has been scheduled in kernel mode, measured in clock ticks
starttime ($22) - The time in jiffies the process started after system boot.
3) 当进程完成时获取完成时间
read FINISH_TIME <<< $(cat '/proc/self/stat' | awk '{print $22;}')
然后输出:
我认为它应该给出与时间大致相同的结果。我看到的一个可能的问题是该过程是否存在很短的时间。
这是我对time的实现:
#!/bin/bash
# Uses herestrings
print_res_jeffies()
{
let "TIME_M=$2/60000"
let "TIME_S=($2-$TIME_M*60000)/1000"
let "TIME_MS=$2-$TIME_M*60000-$TIME_S*1000"
printf "%s\t%dm%d.%03dms\n" $1 $TIME_M $TIME_S $TIME_MS
}
print_res_ticks()
{
let "TIME_M=$2/6000"
let "TIME_S=($2-$TIME_M*6000)/100"
let "TIME_MS=($2-$TIME_M*6000-$TIME_S*100)*10"
printf "%s\t%dm%d.%03dms\n" $1 $TIME_M $TIME_S $TIME_MS
}
if [ $(getconf CLK_TCK) != 100 ]; then
exit 1;
fi
if [ $# != 1 ]; then
exit 1;
fi
PROC_DIR="/proc/"$1
if [ ! -e $PROC_DIR ]; then
exit 1
fi
USER_TIME=0
SYS_TIME=0
START_TIME=0
while [ -e $PROC_DIR ]; do
read TMP_USER_TIME TMP_SYS_TIME TMP_START_TIME <<< $(cat $PROC_DIR/stat | awk '{print $14, $15, $22;}')
if [ -e $PROC_DIR ]; then
USER_TIME=$TMP_USER_TIME
SYS_TIME=$TMP_SYS_TIME
START_TIME=$TMP_START_TIME
sleep 0.1
else
break
fi
done
read FINISH_TIME <<< $(cat '/proc/self/stat' | awk '{print $22;}')
let "REAL_TIME=($FINISH_TIME - $START_TIME)*10"
print_res_jeffies 'real' $REAL_TIME
print_res_ticks 'user' $USER_TIME
print_res_ticks 'sys' $SYS_TIME
这是一个比较我的time 和真实time 实现的示例:
>time ./sys_intensive > /dev/null
Alarm clock
real 0m10.004s
user 0m9.883s
sys 0m0.034s
在另一个终端窗口中,我运行 my_time.sh 并为其指定 PID:
>./my_time.sh `pidof sys_intensive`
real 0m10.010ms
user 0m9.780ms
sys 0m0.030ms
【讨论】: