TLS 接続
このページでは、TLS 接続を有効にした xrdp をセットアップする方法について解説します。
対象バージョン
2017年12月現在、最新リリースの xrdp v0.9.5 で TLS が正式サポートされています。
インストールされている xrdp のバージョンがわからない場合は /etc/xrdp/xrdp.ini に以下のような記述があるか確認することでも、TLS 対応しているかの目安になります。
# security layer can be 'tls', 'rdp' or 'negotiate' # for client compatible layer security_layer=tls # X.509 certificate and private key # openssl req -x509 -newkey rsa:2048 -nodes -keyout key.pem -out cert.pem -days 365 certificate= key_file=
対象環境
本ページの内容は以下の環境でテストしましたが、他の環境でもほぼ同様です。
- CentOS 7
xrdp v0.9.5
設定方法
TLS 証明書の作成
まず最初に xrdp で使用する秘密鍵と証明書を作成する必要があります。Let's Encrypt や他の認証局に署名してもらった証明書がある場合は、それを使用することができます。 正式な証明書を使用しない場合は、自己署名証明書(オレオレ証明書)を作成して使用することになります。
詳しい作成方法は本ページでは説明しないので、以下のページなどを参照して作成してください。
とりあえずお手軽に作成したい場合は、以下のコマンドで作成することができます。
$ openssl req -x509 -newkey rsa:4096 -keyout key.pem -sha256 -nodes -out cert.pem -days 365 -subj "/CN=$(hostname)"
上手くいくと cert.pem と key.pem という2つのファイルができます。書き込み先のディレクトリのパーミッションに応じて sudo 経由で実行するなり、適切に実行してください。
TLS 証明書の配置
前のステップで作成した cert.pem と key.pem を /etc/xrdp に置きます。正式な証明書を持っている場合は、ファイル名は必ずしもこの通りになっていなくても大丈夫ですが、秘密鍵が key.pem 証明書が cert.pem というファイル名になっている前提で説明します。
コマンド実行例:
$ sudo cp cert.pem key.pem /etc/xrdp
次に、配置した証明書の場所を xrdp.ini 内の certificate, key_file に設定します。sudoedit コマンドなどを使用して xrdp.ini を書き換えます。
$ sudoedit /etc/xrdp/xrdp.ini
差分はこんな感じです。certificate, key_file のデフォルト値はそれぞれ /etc/xrdp/cert.pem, /etc/xrdp/key.pem なので空欄にしたままでも同じなのですが、説明のために明示的に書いています。証明書と秘密鍵のファイル名が異なる場合は、実際の環境に合ったものを指定してください。また、SSLv3 を使用しない設定もここで追加しています。
--- xrdp.ini.sample 2016-12-27 09:21:37.616647000 +0900 +++ xrdp.ini.new 2016-12-27 09:27:18.484140000 +0900 @@ -23,12 +23,12 @@ crypt_level=high ; X.509 certificate and private key ; openssl req -x509 -newkey rsa:2048 -nodes -keyout key.pem -out cert.pem -days 365 -certificate= -key_file= +certificate=/usr/local/etc/dehydrated/certs/icepick.vmeta.jp/cert.pem +key_file=/usr/local/etc/dehydrated/certs/icepick.vmeta.jp/privkey.pem ; specify whether SSLv3 should be disabled -#disableSSLv3=true +disableSSLv3=true ; set TLS cipher suites -#tls_ciphers=HIGH +tls_ciphers=HIGH ; Section name to use for automatic login if the client sends username ; and password. If empty, the domain name sent by the client is used.
セキュリティレイヤの設定
xrdp v0.9.5 ではデフォルトで TLS 接続が有効な設定になっていますが、もし security_layer=rdp という設定になっている場合は negotiate もしくは tls に書き換えます。
これは RDP 接続の暗号化方法の指定で、rdp を指定した場合は従来の RC4 による暗号化、tls を指定した場合は TLS による暗号化、negociate を指定した場合は、クライアントが対応している方法を自動的に判別します。
今回はより安全な接続をセットアップするため、従来の RC4 を使用せず TLS のみを使用するよう security_layer=tls としておきます。
動作確認
設定が終わったら、xrdp を再起動してクライアントから接続してみます。
$ sudo systemctl restart xrdp
TLS 接続がうまく行っている場合 Windows のクライアントから接続すると、以下の様なエラーが出ます(自己署名証明書の場合)。
証明書の内容を確認して、問題なければ続行してください。
Linux などから rdesktop や FreeRDP で接続する場合は、以下の様にターミナルに表示され、TLS で接続されていることが確認できます。
FreeRDP は接続時に証明書の検証ができますが、rdesktop ではできないようです。
$ rdesktop 192.168.24.207 Connection established using SSL.
$ xfreerdp /v:192.168.24.207 connected to 192.168.24.207:3389 @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ @ WARNING: CERTIFICATE NAME MISMATCH! @ @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ The hostname used for this connection (192.168.24.207) does not match the name given in the certificate: Common Name (CN): no CN found in certificate A valid certificate for the wrong name should NOT be trusted! Certificate details: Subject: C = AU, ST = Some-State, O = Internet Widgits Pty Ltd Issuer: C = AU, ST = Some-State, O = Internet Widgits Pty Ltd Thumbprint: 6f:c9:80:9a:6b:d2:6c:44:cd:ff:d3:6c:e3:c8:bb:a3:10:cf:cd:71 The above X.509 certificate could not be verified, possibly because you do not have the CA certificate in your certificate store, or the certificate has expired. Please look at the documentation on how to create local certificate store for a private CA. Do you trust the above certificate? (Y/N)
サーバ側で確認する場合、/var/log/xrdp.log に以下のようなログが記録されます。以下の例の場合は TLSv1.2 が使用されていて、暗号化スイートは AES256-GCM-SHA384 です。
[20180323-09:52:15] [INFO ] TLS connection established from ::ffff:192.168.24.201 port 61559: TLSv1.2 with cipher AES256-GCM-SHA384
以上の設定で、xrdp の暗号化に TLS を使用することができ、HTTPS などと同レベルのセキュリティを実現できました。
自己署名証明書を使用するリスクも HTTPS などと同じなので、必要に応じて認証局に署名された正式な証明書を使用することを検討してください。
高度な設定
より高度な設定として、使用する TLS のバージョンや暗号化スイートを細かく指定することもできます。
これらは、/etc/xrdp/xrdp.ini の中の ssl_protocols と tls_ciphers で制御できます。デフォルトでは以下のようになっています。
; set SSL protocols ; can be comma separated list of 'SSLv3', 'TLSv1', 'TLSv1.1', 'TLSv1.2' ssl_protocols=TLSv1, TLSv1.1, TLSv1.2 ; set TLS cipher suites #tls_ciphers=HIGH
TLSv1.2 以上を強制したい場合は、ssl_protocols を以下のように書き換えます。
ssl_protocols=TLSv1.2
暗号化スイートの指定は tls_ciphers で行います。指定したパラメータがそのまま openssl ciphers (1) コマンドの引数となります。
OpenSSL や OS などのシステム要件によって異なりますが、例えば HIGH を指定した場合には HIGH は以下の暗号化スイートに展開されます。すなわち HIGH を指定するとの、以下の長い文字列を指定するのは同じ効果です。
$ openssl ciphers HIGH ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA:ECDHE-ECDSA-AES256-SHA:SRP-DSS-AES-256-CBC-SHA:SRP-RSA-AES-256-CBC-SHA:SRP-AES-256-CBC-SHA:DH-DSS-AES256-GCM-SHA384:DHE-DSS-AES256-GCM-SHA384:DH-RSA-AES256-GCM-SHA384:DHE-RSA-AES256-GCM-SHA384:DHE-RSA-AES256-SHA256:DHE-DSS-AES256-SHA256:DH-RSA-AES256-SHA256:DH-DSS-AES256-SHA256:DHE-RSA-AES256-SHA:DHE-DSS-AES256-SHA:DH-RSA-AES256-SHA:DH-DSS-AES256-SHA:DHE-RSA-CAMELLIA256-SHA:DHE-DSS-CAMELLIA256-SHA:DH-RSA-CAMELLIA256-SHA:DH-DSS-CAMELLIA256-SHA:AECDH-AES256-SHA:ADH-AES256-GCM-SHA384:ADH-AES256-SHA256:ADH-AES256-SHA:ADH-CAMELLIA256-SHA:ECDH-RSA-AES256-GCM-SHA384:ECDH-ECDSA-AES256-GCM-SHA384:ECDH-RSA-AES256-SHA384:ECDH-ECDSA-AES256-SHA384:ECDH-RSA-AES256-SHA:ECDH-ECDSA-AES256-SHA:AES256-GCM-SHA384:AES256-SHA256:AES256-SHA:CAMELLIA256-SHA:PSK-AES256-CBC-SHA:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-SHA256:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA:ECDHE-ECDSA-AES128-SHA:SRP-DSS-AES-128-CBC-SHA:SRP-RSA-AES-128-CBC-SHA:SRP-AES-128-CBC-SHA:DH-DSS-AES128-GCM-SHA256:DHE-DSS-AES128-GCM-SHA256:DH-RSA-AES128-GCM-SHA256:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES128-SHA256:DHE-DSS-AES128-SHA256:DH-RSA-AES128-SHA256:DH-DSS-AES128-SHA256:DHE-RSA-AES128-SHA:DHE-DSS-AES128-SHA:DH-RSA-AES128-SHA:DH-DSS-AES128-SHA:DHE-RSA-CAMELLIA128-SHA:DHE-DSS-CAMELLIA128-SHA:DH-RSA-CAMELLIA128-SHA:DH-DSS-CAMELLIA128-SHA:AECDH-AES128-SHA:ADH-AES128-GCM-SHA256:ADH-AES128-SHA256:ADH-AES128-SHA:ADH-CAMELLIA128-SHA:ECDH-RSA-AES128-GCM-SHA256:ECDH-ECDSA-AES128-GCM-SHA256:ECDH-RSA-AES128-SHA256:ECDH-ECDSA-AES128-SHA256:ECDH-RSA-AES128-SHA:ECDH-ECDSA-AES128-SHA:AES128-GCM-SHA256:AES128-SHA256:AES128-SHA:CAMELLIA128-SHA:PSK-AES128-CBC-SHA
Mozilla SSL Configuration Generator などを使って生成した暗号化スイートの設定をそのまま使うことができます。Apache を選んで、SSLCipherSuite の部分に出力された内容をそのまま tls_ciphers に設定してください。
tls_ciphers=ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256
xrdp.ini を書き換えた後のデーモンの再起動は必要ありません。変更した直後の新しい接続から新しい設定が適用されます。
これらの設定を変更すると、使用するクライアントやクライアント側のOpenSSLのバージョン、Windowsのバージョンによっては接続できなくなる場合がありますので十分に検証を行うことをおすすめします。