12

GNU Screenセッションをデーモンとして開始した場合、プログラムでそのPIDを取得するにはどうすればよいですか?の出力がどれほど一貫しているかわからない ので、bashの定数の1つ、またはより良い代替手段を使用screen -lsしてこれを行う方法を知りたいです。$$$!

画面をで開始していますscreen -dmS screenname

スクリーンセッションを開始する直前または直後にスクリーンのPIDを取得するにはどうすればよいですか?

4

8 に答える 8

17

これは、次の名前の画面のpidを示していますnameofscreen

$ screen -ls
There are screens on:
    19898.otherscreen   (07/03/2012 05:50:45 PM)    (Detached)
    19841.nameofscreen  (07/03/2012 05:50:23 PM)    (Detached)
2 Sockets in /var/run/screen/S-sarnold.

$ screen -ls | awk '/\.nameofscreen\t/ {print strtonum($1)}'
19841
$ 
于 2012-07-04T00:58:52.543 に答える
5

使用できます:

screen -DmS nameofscreen

これはデーモンプロセスをフォークせず、pidを知ることができます。

同じ名前で2つの画面セッションが開始されている場合、screen-lsの出力の解析は信頼できない可能性があります。もう1つのアプローチは、スクリーンセッションでプロセスをフォークせず、自分でバックグラウンドに配置することです。

たとえば、既存の初期画面セッションの場合:

fess@hostname-1065% screen -ls
There is a screen on:
        19180.nameofscreen    (01/15/2013 10:11:02 AM)        (Detached)

新しいプロセスをフォークしない-d-mの代わりに-D-mを使用して画面を作成します。それをバックグラウンドに置いて、それをpidにします。(posixシェルセマンティクスを使用)

fess@hostname-1066% screen -DmS nameofscreen & 
[3] 19431
fess@hostname-1067% pid=$! 

これで、2つの画面が同じ名前になりました。

fess@hostname-1068% screen -ls
There are screens on:
        19431.nameofscreen    (01/15/2013 10:53:31 AM)        (Detached)
        19180.nameofscreen    (01/15/2013 10:11:02 AM)        (Detached)

しかし、私たちは違いを知っています:

fess@hostname-1069% echo $pid
19431

そして、私たちはそれを正確にやめるように頼むことができます:

fess@hostname-1070% screen -S $pid.nameofscreen -X quit
[3]  - done       screen -DmS nameofscreen

今、元のものだけが再びあります:

fess@hostname-1071% screen -ls 
There is a screen on:
        19180.nameofscreen    (01/15/2013 10:11:02 AM)        (Detached)
于 2013-01-15T19:12:38.447 に答える
3

ここで、次のようにスクリーンセッションのPIDを取得できます。

$ screen -ls
There are screens on:
        1934.foo_Server         (01/25/15 15:26:01)     (Detached)
        1876.foo_Webserver      (01/25/15 15:25:37)     (Detached)
        1814.foo_Monitor        (01/25/15 15:25:13)     (Detached)
3 Sockets in /var/run/screen/S-ubuntu.

foo_MonitorスクリーンセッションでBashで実行されているプログラムのPIDが必要だとします。画面セッションのPIDを使用して、PPID(親PID)で既知のPIDを検索することにより、foo_Monitor画面セッションで実行されているセッションのPIDを取得します。bash

$ ps -el | grep 1814 | grep bash
F S   UID   PID  PPID  C PRI  NI ADDR SZ WCHAN  TTY          TIME CMD
0 S  1000  1815  1814  0  80   0 -  5520 wait   pts/1    00:00:00 bash

bash次に、セッションのPIDだけを取得します。

$ ps -el | grep 1814 | grep bash | awk '{print $4}'
1815

次に、そのPIDを使用したプロセスが必要です。コマンドをネストするだけで、今回は-vフラグをオンにして、 bashではないgrep bashプロセスを取得します。

echo $(ps -el | grep $(ps -el | grep 1814 | grep bash | awk '{print $4}') | grep -v bash | awk '{print $4}')
23869

1814をスクリーンセッションの実際のPIDに置き換えるだけです。

echo $(ps -el | grep $(ps -el | grep SCREEN_SESSION_PID | grep bash | awk '{print $4}') | grep -v bash | awk '{print $4}')
于 2015-02-08T14:47:00.533 に答える
2

プログラムのPIDを画面内で実行したいのではないかと思いますが、これは簡単には入手できないようです。(1つの画面プロセスで複数の子を管理できるため、明確に定義された質問ではありません。これは、画面の優れた点の1つです!)

pgrepを使用して、PPIDが画面PIDであるプロセスを見つけることができます。または、次のようにします。

rm mypidfile
screen -dmS blah sh -c 'echo $$ > mypidfile ; exec sh'
# the write to mypidfile is happening in the background, so wait it to show up
while [ ! -s mypidfile ]; do sleep 1; done
pid=`cat mypidfile`
# $pid is now the PID of the shell that was exec'ed inside screen
于 2012-07-04T01:31:50.287 に答える
2

この答えは@sarnoldに触発されています。

すべての画面PIDを取得する方法を追加しましょう。

screen -ls | awk '/[0-9]{1,}\./ {print strtonum($1)}'

0-299は古いカーネルのデーモンのPIDであるため、{1、}を{3、}に変更できます。

各プロセスは、終了するなど、次の方法で操作できます。

pidList=(screen -ls | awk '/[0-9]{3,}\./ {print strtonum($1)}')
for pid in ${pidList[@]};
do
    screen -X -S $pid quit
done

で他のこともできますscreen -X -S $pid stuff 'command\n'

于 2019-03-09T10:13:31.377 に答える
0

もう1つの方法は、screenの-Qパラメーターを使用してセッションを照会することです。

screen -S nameofscreen -Q echo '$PID'

これにより、画面セッション内のPIDも通知として表示されることに注意してください。

于 2017-11-17T00:40:46.150 に答える
0

サーノルドの答えを完成させるには:

$ screen -ls
There are screens on:
    19898.otherscreen   (07/03/2012 05:50:45 PM)    (Detached)
    19841.nameofscreen  (07/03/2012 05:50:23 PM)    (Detached)
2 Sockets in /var/run/screen/S-sarnold.

$ screen -ls | awk '/\.nameofscreen\t/ {print strtonum($1)}'
19841

...次のように、このPIDをPPIDとして持つプロセスのPIDを取得します。

$ ps --ppid 19841 -o pid=
19842
于 2018-02-08T04:03:00.593 に答える
0

最初の答えは私にはうまくいきませんでした。代わりに、私はこれを使用しました:

screen -ls | grep -oE "[0-9]+\.screen_name" | sed -e "s/\..*$//g"

grep -oE少なくとも1つの数値、リテラルドット、そして。に一致する正規表現に一致するもののみを返しますscreen_name。たとえば、これは出力される可能性があります784.screen_name(pidが784の場合)。次に、sedを使用して、文字列の最初のドットから最後までのすべてを削除します。

于 2020-08-09T16:52:34.940 に答える