Remote X Apps mini-HOWTO (zweije@xs4all.nl) 11 July 2000 The Linux Japanese FAQ Project (JF@linux.or.jp) v0.6.3j1, 29 March 2001 この mini-HOWTO はリモート X アプリケーションを実行する方法について 説明します。つまり、X のプログラムを実行しているコンピュータとは 異なるところに表示をさせる方法です。逆にいいますと、X のプログラムを あなたが対面しているコンピュータではないところで実行させる方法、となります。 この mini-HOWTO の焦点はセキュリティです。さらに X アプリケーションを ローカルで、ただし異なったユーザ ID で、実行させる情報も含んでいます。 はじめに

この mini-HOWTO はリモート X アプリケーションを扱うためのガイドです。これを 書いた理由はたくさんあります。 「リモート X アプリケーションを実行するには?」という質問が usenet で 多い。 X 接続の許可に「 xhost 以外のもっとよい方法を記述した簡単な文書を知らない。 もし、他の簡単な文書を知っているなら著者 zweije@xs4all.nl に教えてください。 このドキュメントは UNIX ライクなシステムを対象に書かれています。ローカル かリモートのどちらかのオペレーティングシステムが UNIX 系でなくても、 この文書で動作の仕組みを見つけられるかもしれません。しかしながら、例として 書いたことは各自のシステムに合わせて変更しなければならないでしょう。 このドキュメントの最新版は で入手できます。また「Remote X Apps mini-HOWTO」として で入手できます。Linux (mini-)HOWTO は から http か ftp で入手できます。 このバージョンは 0.6.3 です。善意により公開されており、無保証です。提案、 アイディア、追加、役立つポインタ、(打ち間違い等の)訂正などを募集しています。 でも、この文書は簡単で読み易い文書に保っておきたいと思っています。 最もよい意味での HOWTO 形式ですね。いちゃもんは /dev/null へ。 内容の最終更新は 2000年06月11日 に が行いました。 関連した読み物

&dquot;What to do when Tk says that your display is insecure&dquot; という 関連ドキュメントが WWW 上の () にあります。 氏によって書かれたものです。このドキュメント (xauth) では X 認証について この文書と同じような解決方法を提案しています。しかし Kevin は xauth の制御に xdm を用いることの方を中心にしているようです。 の The X System Window System Vol. 8 X &dquot;Window System Administrator's Guide&dquot; もまたよい情報源なので注意を惹かれます。あいにく著者はチェック できていません。 さらにもう一つのドキュメントは &dquot;Securing X Windows&dquot; という タイトルですぐにでも読めるものです。 から入手できます。 The Scene --> 想定する状況

2台のコンピュータを使っています。1台目で、入力と表示のために X ウィンドウシステムを使っています。2台目をいくつかの重要なグラフィックの 仕事に使っています。1台目のディスプレイに2台目の出力を表示させたい。 X ウィンドウシステムはこれができます。 もちろんネットワーク接続が必要です。X プロトコルはネットワークを大食いする ので、なるべく速いものが必要です。ですがちょっとの我慢と適切なプロトコル圧縮を 使えば、モデム経由でアプリケーションを実行することもできます。 X プロトコル圧縮については dxpc か LBX (またの名を という) をチェックしてください。 1台目のディスプレイに2台目の出力を表示するには、以下の2つのことを しなければなりません。 リモートコンピュータからの接続を受け付けるよう、ローカルディスプレイ (サーバ) に指定する。 ローカルディスプレイにその出力を行うよう、リモートアプリケーション (クライアント) に指定する。 ちょっとした理論

マジックワードは ディスプレイは名前で表されます。例えば: ディスプレイの表記はホスト名 (例示した light.uni.verse や localhost)、 コロン(:)、番号 (例示した 0 や 4 ) から成ります。ディスプレイの表記の ホスト名は X サーバを実行しているコンピュータの名前です。ホスト名を省略すると、 ローカルホストを示すことになります。 番号は普通 0 です――1台のコンピュータに複数のディスプレイが接続されて いるのなら、別の値になるかもしれません。 上記のディスプレイ表記に 他の host/unix:D.S means screen /tmp/.X11-unix/XD (so it's only reachable from host/unix:D.S, where --> 技術的な興味のために: host/unix:D.S はホスト /tmp/.X11-unix/XD をリッスン します (なので host/unix:D.S と等価です。ここで クライアントに指定する

クライアントプログラム (例としてグラフィックアプリケーション) は 私たちのコンピュータは外部からホスト名 light として見えており、 ドメイン uni.verse に所属しているとします。 普通に X サーバを実行しているなら、ディスプレイは すでにリモートコンピュータ リモートコンピュータで csh を使っているなら dark% setenv DISPLAY light.uni.verse:0 dark% xfig & とするか、あるいは dark% xfig -display light.uni.verse:0 & とします。 リモートコンピュータで sh を使っているなら dark$ DISPLAY=light.uni.verse:0 dark$ export DISPLAY dark$ xfig & とするか、あるいは dark$ DISPLAY=light.uni.verse:0 xfig & とします。もちろん dark$ xfig -display light.uni.verse:0 & でもいいです。

(訳注; dark$ env DISPLAY=light.uni.verse:0 xfig& なら csh でも sh でも使えますね :) ) telnet の種類によっては、自動的にリモートホストへ 代用するのと同様の考え方で、次のような数行のスクリプトで実現できます。 telnet する前に、 サーバに指定する

サーバはどこからの接続でも受け付けるわけではありません。あなたのスクリーンに すべての人がウィンドウを表示できるなんて、嬉しくないですよね。 あなたの入力を読まれたくもないでしょう――キーボードはディスプレイの 一部であるということを忘れないで下さい。 ディスプレイへのアクセス許可が、セキュリティリスクの原因になる ことを理解している人はほとんどいません。あなたのディスプレイに アクセスできる人は、スクリーンを読み書きでき、あなたのキーストロークを 読むことやマウスの動きを読むこともできます。 ほとんどのサーバは接続の認証方法が2つあります――host リスト機構 (xhost) と マジッククッキー機構 (xauth) です。また ssh(secure shell) は X 接続を転送する ことができます。 xhost

xhost は host 名にもとづいてアクセスを許します。サーバは、接続を許された host のリストを管理します。host のチェックを完全に無効にすることもできます。 注意してください――無効にするとチェックをしなくなるので全ての host が 接続できます! xhost プログラムを用いるとサーバの host リストを制御できます。 前述の例でこの機構を使うには light$ xhost +dark.matt.er とします。 これはホスト dark.matt.er からの接続をすべて許します。X クライアントが接続され ウィンドウが表示されたら、すぐに安全のため接続許可を取り消します。それには light$ xhost -dark.matt.er とします。 host のチェックを無効にするには light$ xhost + とします。 これは host のアクセスチェックを無効にしているので、すべての人に接続を 許しています。信用できないユーザーがいるネットワーク (例えばインターネット) 上では決してアクセスチェックを無効にしないでください。host のチェックを 再度有効にするには light$ xhost - でできます。 &dquot;xhost -&dquot; は、アクセスリストから全部のホストを削除するわけでは ありません (もしそうなら、不便極まりません――どこから も、ローカルホストさえからも接続できなくなります)。 xhost はとても危なっかしい機構です。xhost はリモートホスト上のユーザを 区別できませんし、 host 名 (実際にはアドレス) も偽ることができます。もし信用できないユーザがいる ネットワーク (例えばインターネットにダイアルアップ PPP アクセス) にいるなら、 これは良くないことです。

(訳注:アドレスを偽れる理由。xhost において X サーバが維持するリストは数値が 登録されています。host 名を使って登録した場合でも gethostbyname 関数により その IP アドレスが数値となります。ですので、4バイトの数値になります。 X サーバがアクセスチェックをする時に使用するのは、X クライアントが送出した IP パケットのソース IP アドレスを使用するのではありません。データ部に X クライアントが乗せた任意の数値です。X クライアントのプログラムの作りにより 何でも乗せることができます。 訳者が以前使用したことのあるメーカ製ワークステーションは、hostid の値を乗せて いました。hostid の既定値は inittab の中で、プライマリの IP アドレスを 定義してるだけでした。この場合は、クラッキングプログラムを書かずとも、数行の スクリプトを書くだけで、ブルドーザアタックが行えます。) xauth

xauth は正しい機密を知っている人にアクセスを許します。そのような機密は 認証レコードあるいはマジッククッキーと呼ばれます。この認証スキームの正式な 呼称は MIT-MAGIC-COOKIE-1 です。 異なるディスプレイに対するそれぞれクッキーは、˜/.Xauthority にまとめて 格納されます。˜/.Xauthority はグループユーザおよび他ユーザには アクセスできないようにしなければなりません (訳注:˜/.Xauthority changes, セッションを始める際、サーバは ˜/.Xauthority のクッキーが 変更されてもサーバはこの変更を取り出しません。 最近のサーバは照会したクライアント用のクッキーをすぐに作ることができます。 しかし、クッキーはサーバ内に保存されたままです――クライアントが ˜/.Xauthority にクッキーを追加しない限り ˜/.Xauthority には入りません。David Wiggins氏によると あなたが興味を示すような名案が X11R6.3 で追加されました。 新しいセキュリティ拡張を通して、X サーバはすぐに新しいクッキーを 作って返すことができます。さらにクッキーを「信用しない」ように指定できるので、 そのようなクッキーで接続を行ったアプリケーションは次のように操作を制限され ます。例えば他の信用できるクライアントのキーボード/マウスの入力やウィンドウに 表示されている内容を盗めなくなります。簡単でないにしても、少なくともこの機能を 使うことができる新しいサブコマンド &dquot;generate&dquot; が xauth にあります。 xauth は xhost に比べてセキュリティに優れています。また特定のコンピュータの 特定のユーザだけにアクセスを制限することができます。xhost のように偽った アドレスからの接続はできません。必要なら xauth の後で接続を許すために xhost を 使うこともできます。 クッキーを作る

xauth を使いたいのなら、/usr/X11R6/bin/startx: --> /usr/X11R6/bin/startxからの引用: mcookie|sed -e 's/^/add :0 . /'|xauth -q xinit -- -auth "$HOME/.Xauthority" mcookie は util-linux パッケージにある小さなプログラムで、 から入手できます。あるいは、 md5sum を用いて 無作為データ (例えば /dev/urandom dd if=/dev/urandom count=1|md5sum|sed -e 's/^/add :0 . /'|xauth -q xinit -- -auth "$HOME/.Xauthority" root になれず startx スクリプトを編集できないのなら、システム管理者に statx スクリプトを適切に設定してもらうか、あるいは xdm を設定して もらってください。管理者ができないもしくはしないなら、 ˜/.xserverrc スクリプトで実現できます。このスクリプトがあると、 xinit は実際の X サーバの代わりにこのファイルを実行します。 したがって、このスクリプトから実際の X サーバを適切な引数で起動できます。 こうするには、 ˜/.xserverrc に上記のマジッククッキーの行を書いて クッキーを作らせ、次いで X サーバを起動する行を書きます。 #!/bin/sh mcookie|sed -e 's/^/add :0 . /'|xauth -q exec /usr/X11R6/bin/X "$@" -auth "$HOME/.Xauthority" X セッションの管理に xdm を使うなら、xauth を簡単に使用できます。 /etc/X11/xdm/xdm-config の中に DisplayManager.authDir リソースを 定義してください。xdm は X サーバが起動する時に -auth 引数を渡すように なります。xdm のもとでログインした時、xdm は ˜/.Xauthority に クッキーを置きます。詳しくは xdm(1) の man ページを参照して下さい。例えば 著者の /etc/X11/xdm/xdm-config では以下の行が書かれています。 DisplayManager.authDir: /var/lib/xdm クッキーの転送

サーバホスト ˜/.Xauthority の中にクッキーを持ちました。 次はクライアントホスト Shared Home Directories --> ホームディレクトリの共有

light と dark 上のあなたのホームディレクトリが共有されていれば 一番簡単です。両方の ˜/.Xauthority ファイルは同じなので、即座に クッキーは転送されます。 しかし落とし穴があります――˜/.Xauthority #!/bin/sh mcookie|sed -e 's/^/add :0 . /' -e p -e "s/:/$HOST&/"|xauth -q exec /usr/X11R6/bin/X "$@" -auth "$HOME/.Xauthority" リモートシェル ホームディレクトリが共有されていないのなら、リモートシェル rsh による方法で クッキーを転送できます。 light$ xauth nlist "${HOST}:0" | rsh dark.matt.er xauth nmerge - とします。これは ローカルの ˜/.Xauthority からクッキーを抽出する (xauth nlist :0)。 dark.matt.er に転送する (| rsh dark.matt.er)。 転送先の ˜/.Xauthority に置く (xauth nmerge -)。 を行います。

Manually, by Telnet --> Telnet を使い手動で行う

rsh が動作しないこともあります。また rsh はセキュリティ上の欠点もあります (著者の記憶が正しいなら、これも host 名を偽れます)。 rsh を使えないか使わないなら以下のように手動でクッキーを転送できます。 light$ echo $DISPLAY :0 light$ xauth list $DISPLAY light/unix:0 MIT-MAGIC-COOKIE-1 076aaecfd370fd2af6bb9f5550b26926 light$ rlogin dark.matt.er Password: dark% setenv DISPLAY light.uni.verse:0 dark% xauth Using authority file /home/zweije/.Xauthority xauth> add light.uni.verse:0 . 076aaecfd370fd2af6bb9f5550b26926 xauth> exit Writing authority file /home/zweije/.Xauthority dark% xfig & [15332] dark% logout light$ 詳しくは rsh(1)、xauth(1x) を参照して下さい。 Telnet で自動に行う方法

リモートホストへ telnet する時に、」 を参照してください。 これについては異論のある方もいらっしゃるでしょう。この方法で本当にうまく いくのかどうか、あるいは駄目なのか、という点を知りたいので、もし実際に 検証できた人がいれば結果を著者まで送っていただけたら幸いです。

(訳注:クッキーは元々ネットワーク透過です。 しかし、X はマルチプラットフォーム環境なので、充分なテストが必要 であるということだと思われます。) でも注意、他の UNIX では、別のユーザからでも環境変数を見ることができることも あります。そんな場合、 $TERM の中に入れたクッキーを他人に 見えないようにするすべはありません。 クッキーを使う

dark.matt.er 上の (前述の xfig のような) X アプリケーションは、 認証に使うクッキーを自動的に ˜/.Xauthority から読みます。

host/unix:D と解釈します。実際には、˜/.Xauthority 考えてみれば、単に論理に従っているに過ぎないことがわかるでしょう。 SSH

認証レコードは暗号化されずにネットワークを経由して送信されます。誰かが接続を のぞく心配があるなら、ssh(secure shell) を使ってください。これは暗号化された 接続を経由して X を転送します。それにまた、ほかにもすばらしいことがあります。 それはシステムの構造改善です。ssh ホームページ を見てください。 誰か認証スキームや暗号化 X 接続について他に何か知っていませんか? kerberosかな?

訳注: Kerberosについて、うえやま るいさん、岡本さんからのコメントをまとめました:

ケルベロスはギリシャ神話に出てくる冥界の支配者ハデスの飼い犬で3つの 頭をもち冥界の門を守る番犬です。"Kerberos" は MIT の "Athena" 計画の一貫 として研究開発されました。RFC 1510 が 1993 年に発行されてます。

Kerberos は信頼できないネットワークで安全な認証・通信を行うために、信頼でき る第三者を使うシステムです。内部の暗号は 対称鍵暗号DESを使います。DESなので あまり強くはありません。しかし、チケットという仕組で認証を行うので運用が簡単 で、安全な認証と通信ができます。鍵配布センターを階層化して、大規模なシステム にも対応することもできるようです。

ふつうの方法だと、クライアントがサーバを利用するときは相手が本当に本物であ るか互いに分かりません。そこで、お互いが信頼している第三者に身元保証しても らえばよいという考えに基づいています。その第三者が鍵配布センターというもの で、その鍵配布センターにサーバを利用するためのチケットを発行してもらいます。 だれでもチケットを発行してもらえるわけはなくクライアントとサーバの鍵を登録 しておく必要があります。 鍵配布センターに発行してもらったチケットは、クライアント(発行してもらう側) の鍵で暗号化されているので、これを復号できるということは、クライアントは確かに 本人であることがわかります( チケットは復号化した中に入っていて、このチケットはサーバの鍵で暗号化されて います。そこで「サーバがチケットを復号化できる = サーバも確かに本人である」 ということになります( この欠点は、チケットの再利用ができてしまうところです。攻撃者はチケットの内容 を見れませんが、流れているチケットを拾ってそのままもう一回サーバに送れば本人 のふりをできます。そのために、タイムスタンプを暗号化して一緒に送ります。 古いタイムスタンプ付きのチケットは使えません。それに、サーバはタイムスタンプ を記録しているので、まったく同じスタンプを持つチケットは無効です。

システム全体での欠点は、鍵配布センターが存在することです。 鍵すべてを登録しているので、ここを破られると安全もなにもありません。

XFree86 のマニュアルの翻訳(岡本さん)が JF にあります。 X の認証関係の参考にしてください。また、国内では OPEN DESIGN No.14 CQ 出版社 ポインタ:

FreeBSDハンドブックのページ:

Jun Kuwamuraさんのページ: 別のユーザ ID からの X アプリケーション

root 特権の必要な、グラフィカルな設定ツールを実行したいとしましょう。しかし、 X セッションは普通のアカウントで実行しています。始めは奇妙に思うかも しれませんが、X サーバはツールがディスプレイにアクセスすることを許しません。 root で普通に何かしたい時に、どうすれば可能ですか? そしてどうすればこの問題を回避できますか?

ユーザ ID ˜clientuser/.Xauthority はディスプレイにアクセスするための 正しいマジッククッキーを含んでいません。正しいクッキーは ˜serveruser/.Xauthority にあります。 同一ホスト上の異なるユーザ

もちろん、リモート X で動作するものは、異なるユーザ ID の X でも同じように 動作します (端的には ユーザ ID の切り替えに su - clientuser -c "env DISPLAY=$DISPLAY clientprogram &"

これだけでは動作しません。さらにクッキーの転送を行う必要があります。 クッキーの取得は 当然パイプでクッキーを渡したいところです。残念ながら、 #!/bin/sh if [ $# -lt 2 ] then echo "usage: `basename $0` clientuser command" >&2 exit 2 fi CLIENTUSER="$1" shift # FD 4 becomes stdin too exec 4>&0 xauth list "$DISPLAY" | sed -e 's/^/add /' | { # FD 3 becomes xauth output # FD 0 becomes stdin again # FD 4 is closed exec 3>&0 0>&4 4>&- exec su - "$CLIENTUSER" -c \ "xauth -q <&3 exec env DISPLAY='$DISPLAY' "'"$SHELL"'" -c '$*' 3>&-" } ほとんどの状況で、移植性と動作に十分だと考えます。 現在著者が考えうる欠点は、'$*' を使っているため、 '$*') が壊れてしまうことです。 もし他にもなにか深刻な間違いがあったら、著者に email を書き送って ください。

スクリプトを /usr/local/bin/xsu とすれば xsu clientuser 'command &' とできます。

パスワードを使う限り、これ以上そう簡単にはできません。 ええ、( Client User Is Root --> クライアントユーザが root

当然、root ではないクライアントユーザが root で動作することも同様にできます。 しかし、root はすべての人の ˜/.Xauthority ファイルを読むことが できるので、root の場合はより簡単です。クッキーを送る必要がありません。 ˜serveruser/.Xauthority を見るように設定するだけです。つまり: su - -c "exec env DISPLAY='$DISPLAY' \ XAUTHORITY='${XAUTHORITY-$HOME/.Xauthority}' \ command"

これをスクリプト中に書くと以下のようになるでしょう。 #!/bin/sh if [ $# -lt 1 ] then echo "usage: `basename $0` command" >&2 exit 2 fi su - -c "exec env DISPLAY='$DISPLAY' \ XAUTHORITY='${XAUTHORITY-$HOME/.Xauthority}' \ "'"$SHELL"'" -c '$*'"

スクリプトを /usr/local/bin/xroot とすれば xroot 'control-panel &' とできます。

でも、もし Running a Remote Window Manager --> リモートウィンドウマネージャの実行

ウィンドウマネージャ ( ほとんどの場合うまくいきます。最高で一つのウィンドウマネージャをいつでも ディスプレイで実行できます。すでにローカルウィンドウマネージャが実行され ているのなら、リモートウィンドウマネージャを起動することは できません (それは不平を言い終了するでしょう)。最初に ローカルウィンドウマネージャを kill(または単に quit) しなければなりません。

残念ながら、多くの X セッションスクリプトはこの1行で終わります。 exec window-manager-of-choice そして、これは (ローカルの)ウィンドウマネージャが終了した時に、 セッションが終了することを意味します。 X システム (xdm か xinit) にセッションが終了したとみなされると、 実際にはログアウトさせられてしまいます。

いくつか特別なことを行わなければなりませんが、実行は可能でそんなに 難しくありません。あなたが欲するとおりに、セッションスクリプト (普通は ˜/.xsession˜/.xinitrc) をちょっと いじるだけです。

多くの場合、ウィンドウマネージャは新しいプログラムの実行方法を提供しますが、 それで実行したプログラムはローカルマシン上で実行されることに注意してください。 ここで言うローカルとはウィンドウマネージャが起動しているマシンを指します。 リモートでウィンドウマネージャを実行した場合は、リモートのアプリケーションが 起動されます。これはあなたの希望とは異なるかもしれません。もちろん、リモートで 起動したプログムは、依然として手元のディスプレイに表示を行います。 トラブルシューティング

初めてリモート X アプリケーションを実行しようとしても、 大抵はそのままでは動作しません。 以下2〜3のエラーメッセージ、原因、解決方法を挙げます。 xterm Xt error: Can't open display: _X11TransSocketINETConnect: Can't connect: errno = 101 xterm Xt error: Can't open display: love.dial.xs4all.nl:0 エラー 101 は &dquot;Network is unreachable&dquot; です。アプリケーションは サーバにネットワーク接続できません。 _X11TransSocketINETConnect: Can't connect: errno = 111 xterm Xt error: Can't open display: love.dial.xs4all.nl:0 エラー 111 は &dquot;Connection refused&dquot; です。接続しようと しているサーバマシンには到達しますが、指定したサーバがありません。 ホスト名とディスプレイ番号を正しく使っているか確認してください。 Xlib: connection to ":0.0" refused by server Xlib: Client is not authorized to connect to Server xterm Xt error: Can't open display: love.dial.xs4all.nl:0.0 クライアントはサーバに接続を作れましたが、サーバは (認証されていない) クライアントがディスプレイを使うことを許しません。 正しいマジッククッキーをクライアントに転送し、その期限が切れていないか (新しいセッションを開始する時、サーバは新しいクッキーを使います) 確認してください。 日本語訳について

日本語訳は Linux Japanese FAQ Project が行いました。 翻訳に関するご意見は JF プロジェクト <JF@linux.or.jp> 宛に連絡してください。 改訂履歴を以下に示します。 v0.3.1 翻訳: Tetsu Isaji <isaji@mxu.mesh.ne.jp> Kerberosについて: うえやま るいさん 、 岡本 一幸さん 、 Jun Kuwamuraさん v0.6.3 翻訳: 野本浩一 <hng@ps.ksky.ne.jp> 校正: 藤原 輝嘉さん 、 加藤 大典さん 、 高城 正平さん 、 Toshimi Horie さん 、 武井 伸光さん 、 中谷 千絵さん 、 中野 武雄さん 、 森本 淳さん 、 Hiro YAMAZAKI さん 、 Tsutomu Kawashima さん 、 後藤 雅晴さん 、 佐野 武俊さん 、 岡本 一幸さん