recpt1で実行中の録画のプロセスIDを取得したい(録画停止に使う)。
こんな感じのプロセスがある状態で
こういう結果が返る
のを、PHPで作る。
ーーー
まず、プロセスの取り出しを行う。ここまではシェルを使う。awk素晴らしい。
recpt1のプロセスをgrep。
$ ps aux | grep recpt1
grepコマンド自体が邪魔なので消す。
$ ps aux | grep recpt1 | grep -v grep
2列目(PID)と12列目(デバイス名)だけあればいい。awkで切り出す。
$ ps aux | grep recpt1 | grep -v grep | awk '{print $2,$12}'
ーーー
次はhtmlでformを作る。
至ってシンプル。chkPID.htmlから、chkPID.phpを呼び出すようにする。
vim chkPID.html
ーーー
chkPID.phpを書いていく。
全体はこう。
ーーー
chkPID.htmlのformからは、「pidchk」という変数名にYESかNOが入ってくる(正確には、配列$_GETのpidchkフィールドか)。
pidchk=YES ならチェック実行する。
関数の中で、シェルにプロセスIDを取得させる。
シェルのコマンドを変数 $command に入れる。
コマンドの実行結果(へのポインタ)を、変数 $handle に入れる。
$handle = popen($command , "r");
うまく $handle に入ったかチェック。入っていなければ処理しない。
うまくいくと、例えばこんなバイト列が $command に入ってたとして
7705 --device=/dev/pt3video7
29739 --device=/dev/pt3video6
そこに、ポインタ $handle がつながる。
ーーー
この $handle を、fgets() で読み込む。
読み込みは、バイト列の終わり(feof)になるまで続ける。
while文で、feofにならない間はfgets($handle)し続ける。
ーーー
preg_match()を使って、文字列を切り出す。
$command 文字列
7705 --device=/dev/pt3video7
とあるうちの、
PID(プロセス名):7705
実行デバイス名:video7
を取り出せればよい。
preg_match();
preg_match('');
preg_match('//');
preg_match('/正規表現/');
preg_match('/正規表現/' , 文字列$buffer);
preg_match('/正規表現/' , 文字列$buffer , 切り出した文字を入れる配列$m);
最高のサイトがあった。リアルタイムに、配列の格納状況を確認できる。
さっそく確認。
配列m[1]に値が入れば成功。
/(¥s*¥d+)/
¥sはスペース。先頭にスペースがあった場合を想定。
* はそのスペースの「0回」以上の繰り返し(スペースがない場合もある)。
¥dは数字。[0-9]と同じ。
+ はその数字の「1回」以上の繰り返し(数字の繰り返し)。
/(video.)/
「video」で始まって、その後に1文字(ドット1つ)ある
ーーー
これらを合わせる。
/(¥s*¥d+).*(video.)/
よし。
配列 $m[1] と $m[2] に正規表現キャプチャ(文字列の切り出し)できた。
ーーー
これで、
$m[1] には プロセスIDが入り、
$m[2] には デバイス名が入る。
これを
$value = $m[1];
$key = $m[2];
として変数に入れて、別の配列$ret(←returnのこと)に入れていく。
$ret = array();
はソースの初めで宣言済み。
$ret ($key) => $value
$ret (デバイス名) => プロセスID
として、デバイス名とプロセスIDをひも付けて、関数の返り値として配列$retを返す。
ーーー
結果、$command 文字列から配列$retまでの切り出し全体はこうなる。
関数はこれで終わり。
ーーー
あとは実行。その関数を呼ぶ。
関数の戻り値を、配列変数 $pid に入れる。
配列 $pid をwhile文で読み出す。
ーーー
テスト実行。
末尾2行で、pid を表示できてた。
これで完成。
ーーー
次回以降で、pidを指定してkillする処理を作る(録画停止)。