XがDebianマシンの特定のTTYで実行されているかどうかを確認し、その場合は表示番号(DISPLAYの値)を取得するにはどうすればよいですか?
編集:TTYは非アクティブなコンソールである可能性があり、必ずしもアクティブなコンソールである必要はありません。関数を実装しようとしています
Display()
{
local tty="$1"
...
}
プロセス名で検索できます。次に、プロセスによって開かれているUNIXドメインソケット(おそらく抽象)を調べて、表示番号を決定します。
pid=$(pgrep -xt "$tty" Xorg) &&
lsof -aUp "$pid" | sed '\|.*X11-unix/X\([0-9]\{1,\}\) .*|!d;s//\1/;q'
そのlsof
はrootとして実行する必要があります。
または、表示番号が常に存在する場合は、コマンドライン引数から表示番号を抽出できます。
pgrep -axt "$tty" Xorg | sed -n 's/.*:\([0-9]\{1,\}\).*/\1/p'
/dev/ttyNN
から$DISPLAY
へのマッピングを解決する簡単な方法がわかりません。ただし、それは可能です。私のDebianベースのシステムでは、これは:0
で実行されているXセッションのローカルDISPLAY
値/dev/tty7
を返します。
xtty=/dev/tty7
xpid=$(lsof "$xtty" 2>/dev/null | awk '$1 == "Xorg" {print $2}')
test -n "$xpid" && ps -fp "$xpid" | awk '$2 == xpid {print $9}' xpid="$xpid" # → :0
中間段階は以下のとおりです。
lsof
は、指定されたtty端末で開いているすべてのプロセスを返します。 awk
は、Xorg
という名前のプロセスのプロセスIDを選択します。その特定のXディスプレイサーバーを実行していない場合はYMMV。
lsof /dev/tty7 2>/dev/null
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
Xorg 695 root 8u CHR 4,7 0t0 1059 /dev/tty7
ps | awk
の組み合わせは、一致したXorg
プロセスの十分な詳細を提供して、DISPLAY
名を配信します。
ps -fp 695
UID PID PPID C STIME TTY TIME CMD
root 695 639 0 Jan23 tty7 00:01:44 /usr/bin/X :0 -seat seat0 -auth /var/run/lightdm
LinuxマシンとGNUツールを想定すると、これは機能するはずです:
#!/bin/bash
## Get Xorg's tty
xorgTTY="$(ps -o tty= "$(pgrep Xorg)")"
## Get the DISPLAY from a process running on that tty
while read pid; do
display="$(grep -aoP 'DISPLAY=\K[^\0]+' /proc/"$pid"/environ)" && break
done < <(pgrep -t "$xorgTTY")
echo "$display"
bash
がシェルであると仮定すると、このようなものが機能する可能性があります。
TTY="pts/20"
BASH_PID="$(ps -t $TTY|awk '$4 == "bash" {print $1;exit}')"
TTY_DISPLAY=$(tr '\000' '\n' < /proc/$BASH_PID/environ|awk -F'=' '$1 == "DISPLAY" {print $2}')
TTYを指定し、最初に見つかったbash pidを取得してから、/proc/pid/environ
からDISPLAY
varを抽出します。
Systemd-logind(Debian 8を含む必要があります)を使用するマシンでは、次のようにlogindを照会できます。
DisplayName()
{
local ttynr="$1"
declare -A property
for session in $(loginctl --no-legend list-sessions | awk '{ print $1 }' ); do
while IFS="=" read key value ; do
property[$key]="$value"
done < <(loginctl show-session $session)
if [ "${property[VTNr]}" = "$ttynr" ] && [ -n "${property[Display]}" ]; then
echo "${property[Display]}"
return 0
fi
done
return 1
}
私のDebian8システムでは、すべてのXプロセスが仮想端末を受け取ります(例:vt1
)と表示名(例::0
)引数として。ただし、Xセッションがディスプレイマネージャによって開始されたか、コンソールから開始されたかによって、引数の位置は異なります。 roaimaの答えに触発されて、私は次のシェル関数を作成しました。
DisplayName()
{
local ttyNr="$1"
ps -ef | awk -v ttyNr="$ttyNr" \
'$8 == "/usr/bin/X" {
for (i = 9; i <= NF; i++) {
if ($i == "vt" ttyNr) {
isMatch = 1
} else if ($i ~ "^:[0-9]+$") {
display = $i
}
}
if (isMatch) {
print display
exit
}
}'
}
さて、最短の答えは一文字かもしれないと思います:
$ w
USER TTY FROM LOGIN@ IDLE JCPU PCPU WHAT
arnie97 tty1 - 21:50 2:11 9.94s 8.88s -bash
arnie97 tty7 :0 20:56 1:09m 45.68s 0.02s /bin/sh /etc/xdg/xfce4/xinitrc -- /etc/X11/xinit/xserverrc
arnie97 pts/0 192.168.0.1 22:31 0.00s 0.44s 0.30s vi
スクリプトに関して:
$ w -h | awk '$3 ~ /^:/ { if ($2 == "tty7") print $3 }'
:0