x 秒間に x 回実行された場合に bash ループを強制的に終了させるにはどうすればよいですか?

x 秒間に x 回実行された場合に bash ループを強制的に終了させるにはどうすればよいですか?

私は SSH 経由でリモート パイプから入力のバッチを取得しようとしています。以下のスクリプトは問題なく動作しますが、スクリプトが暴走し始めたときに何か問題が発生したりループが中断したりした場合に終了するように、何らかのチェックを追加したいと思います。

ループが 3 秒間に 5 回実行されたかどうかをチェックし、その後スクリプトがループを中断して自動的に終了するコンポーネントを追加するにはどうすればよいでしょうか。

#!/bin/sh
if [ -z "$1" ]
    then
    echo " usage: user@host"
    echo
    exit
fi


while [ 1 ]
    do
    CB=`ssh $1 cat clipboardpipe`
    if [ -n "$CB" ]
        then
        echo $CB | /usr/bin/pbcopy
        echo $CB | /usr/local/bin/growlnotify
    fi
    sleep 1
done

追伸: 次のようなものの使用を検討しましたtail -fが、他のプログラムがバッチでの入力を期待している場合は機能しないようです。アドバイスをお待ちしています。

pss: は、clipboardpipeリモート システムのホーム ディレクトリ内の名前付きパイプです。

答え1

GNU はdateを介し​​てナノ秒の精度を実現します%N

every=3     # test every n'th itteration 
bsecs=0.95  # break at secs (float)
bnano=$(printf '%0.9f' "$bsecs"); bnano=${bnano/./};  
# avoid lead '0' octal clash when time slice < 1 sec
shopt -s extglob; bnano=${bnano#+(0)}  

tprev=$(date +%s%N)
for i in {1..24} ;do  # just a test loop

  if ((i%every==1)) ;then
    tnow=$(date +%s%N)
    if ((tnow-tprev>=bnano)) ;then 
        echo "Auto Break!  $every itteratons took longer than $bsecs secs"
        break
    fi
    ((tprev=tnow))
  fi
  # do something, eg sleep for testing
  sleep 1.$i; echo $i
done

答え2

Linuxをお使いの場合は、タイムアウトcoreutils パッケージによって提供されるコマンド。

タイムアウトのドキュメント

関連情報