0

使用されている端末の種類を名前だけで表示するようにしています。たとえば、konsole を使用していた場合、konsole が表示されます。これまで、私はこのコマンドを使用してきました。

pstree -A -s $$

それはこれを出力します。

systemd---konsole---bash---pstree

その行から konsole を抽出できる次のものがあります

pstree -A -s $$ | sed 's/systemd---//g;s/---.*//g' | head -1

コンソールを適切に出力します。しかし、pstree コマンドだけで次のような出力が得られる人もいます。

systemd---kdeinit4---terminator---bash---pstree

またはこれ

systemd---kdeinit4---lxterminal---bash---pstree

sed コマンドを追加すると、ターミネータの代わりに kdeinit4 が抽出されます。端末のタイプを抽出するシナリオはいくつか考えられますが、特定のタイプの端末をチェックするための条件文を含まないシナリオはありません。私が抱えている問題は、端末名の前または後ろにある非相対または非相対的なものの数、またはそれらが何であるかを正確に予測できないこと、および端末名が何であるかを正確に予測できないことです。誰かがこれに対する解決策について何か考えを持っていますか?

4

4 に答える 4

1

あなたが使用することができます

ps -p "$PPID" -o comm=

または

ps -p "$PPID" -o fname=

シェルに PPID 変数が設定されていない場合は、次のコマンドで取得できます

ps -p "$(ps -p "$$" -o ppid= | sed 's|\s\+||')" -o fname=

もう 1 つの理論は、シェルと同じ tty に属していない現在のシェルの親プロセスが、実際には仮想端末を生成するプロセスである可能性があるため、次のようにも見つけることができるというものです。

#!/bin/bash

shopt -s extglob

SHELLTTY=$(exec ps -p "$$" -o tty=)
P=$$

while read P < <(exec ps -p "$P" -o ppid=) && [[ $P == +([[:digit:]]) ]]; do
    if read T < <(exec ps -p "$P" -o tty=) && [[ $T != "$SHELLTTY" ]]; then
        ps -p "$P" -o comm=
        break
    fi
done
于 2013-08-26T21:39:58.873 に答える
0

システムの端末名を分離する方法はわかりませんが、解析の演習として、端末が bash を直接実行していると仮定すると、pstree 出力を次のようにパイプできます。

 awk -F"---bash---" ' NF == 2 { count = split( $1, arr, "---" ); print arr [count]; }'

これにより、「---bash---」の前の単語が見つかります。例では

konsole
terminator
lxterminal

異なるシェルタイプが必要な場合は、フィールドセパレーターを拡張して、次のように含めることができます。

awk -F"---(bash|csh)---" ' NF == 2 { count = split( $1, arr, "---" ); print arr[count]; }'

次のような架空の線を考えてみます。

systemd---imaginary---monkey---csh---pstree

awk は、ターミナル名として "monkey" を見つけ、テスト セットから何かを見つけます。

于 2013-08-26T21:59:42.887 に答える
0

ここでの保証はありませんが、Linux ではほとんどの場合、これでうまくいくと思います:

ps -ocomm= $(lsof -tl /proc/$$/fd/0 | grep -Fxf <(lsof -t /dev/ptmx))

少し説明が必要かもしれませんが、情報についてはman psman lsofおよび (特に)man ptsを参照してください。

/dev/ptmx疑似 tty マスターです (最新の Linux システム、およびその他の UNIX(-like) システム上)。ターミナル エミュレータ、telnet/ssh デーモン、またはキャプティブ ターミナルを必要とするその他のプログラム (screenなど) の場合、プログラムはこれらのいずれかを開きます。エミュレータは、「タイプ」したいものを疑似 tty マスターに書き込み、疑似 tty スレーブから結果を読み取ります。

/proc/$$/fd/0$$プロセス(つまり、コマンドが実行されるシェル) のstdin です。stdin がリダイレクトされていない場合、これはスレーブ疑似端末 /dev/pts/# へのシンボリック リンクになります。これは /dev/ptmx デバイスの反対側であり、その結果、開いている上記のすべてのプログラムは、/dev/ptmxいくつかの/dev/pts/#スレーブも開いています。(の代わりに/dev/stdinorを使用できると思うかもしれませんが、それらはそれ自体で開かれ、その結果、その stdin になります。方法が実装されているため、機能しません。)シンボリックリンクをたどらせるオプション。そのため、現在のシェルと同じポイントが開いているプロセスが表示されます。/dev/fd/0/proc/$$/fd/0lsoflsof-llsof

1 行に 1 つのpid のみで構成される「簡潔な」出力を生成する-tオプション。正規表現ではなく文字列と一致させ、全行一致を強制するlsofオプション-Fxgrepこの-f FILEオプションにより、一致する文字列FILE(この場合はプロセス置換) を 1 行に 1 つずつ受け入れるようになります。

最後にps -ocomm=、pid に対応する「コマンド」 (デフォルトでは 8 文字に切り捨てられます) を出力します。

要するに、このコマンドは、マスター疑似 tty を持つ端末エミュレーターおよびその他のマスター類似プログラムのリストと、疑似 tty スレーブを使用するプロセスのリストを見つけます。2 つの共通点を見つけ、コマンド名を検索して結果を求めます。

于 2013-08-26T23:52:05.337 に答える
0
curTerm=$(update-alternatives --query x-terminal-emulator | grep '^Best:')
curTerm=${curTerm##*/}

printf "%s\n" "$curTerm"

そして結果は

terminator

もちろん違うかもしれません。これで、sed コマンドで variable を
使用できるようになりました。$curTerm

しかし、これがシンボリックリンクで適切に機能するかどうかはわかりません。

于 2013-08-26T21:39:04.840 に答える