追記

meta's blog - The Power To Serve

筆者について - No Unix, No Life

日本xrdpユーザ会発起人。

とある元大学院生の UNIX 系日記。FreeBSDを通じてOSSに囁かな貢献を。 FreeBSD ports contributor やってます。

For non Japanese native people:
If you are interested in my articles, please leave comments. I will do my best to give you articles in English.


2018-02-16 [長年日記]

はじめてのMacPorts: FreeRDPを2.0.0-rc1にアップデートしてマージされた

MacPortsに入っているFreeRDPが1.1系で古かったので、最新の2.0.0-rc1に更新してみました。FreeBSD portsのアップデートpatchを作るというのは日常的にやっているので、その

大体こんな流れ。

  1. GitHubのMacPortsリポジトリをforkする
  2. forkしたリポジトリをcloneする
  3. 当該portをいじる
  4. Pull Requestを作る

最初の2つは1回きりで手元にリポジトリを持っていれば省略できるので、適当に。

まずはMacPortsのチケット検索ページから、当該portのアップデートリクエスト等のチケットがないか確認します。あれば、後でコミットするときに「このチケットの作業やっといたよ」とコミットメッセージに書くためにURLを控えておきます。

次にPortfileをいじります。Portfileの書き方はFreeBSD portsのMakefileとは全然違うものの、FreeBSD portsに慣れていればなんとなく雰囲気でわかりました。ちょっと手こずったのが、FreeBSD portsの `make makesum` のような tarball のチェックサムを自動的に生成する手段がない(?)ところ。

もしかしたらあるのかもしれませんが、OpenSSLで2種類のチェックサムを生成して手でPortfileに書き込みました。

openssl dgst -rmd160 FreeRDP-2.0.0-rc1.tar.gz
openssl dgst -sha256 FreeRDP-2.0.0-rc1.tar.gz

コミットメッセージはガイドラインに沿うように。 そんなこんなで出来上がったのがこちらのコミット。とりあえず見様見真似。

そしてPull Requestを作成。

Pull Requestにテンプレートがあって、以下のコマンドでテストしたMacの環境を添えます。

echo "macOS $(sw_vers -productVersion) $(sw_vers -buildVersion)"; echo "Xcode $(xcodebuild -version | awk '{print $NF}' | tr '\n' ' ')"

他にも、

  • コミットメッセージガイドラインに沿ったか
  • 同じようなPull Requestがないことを確認したか
  • Tracチケットがある場合URLでリンクをしたか(チケット番号だけではダメ)
  • `port lint` コマンドで文法チェックをしたか
  • `sudo port test` コマンドでテストを実行したか(テストがある場合)
  • `sudo port -vst install` でインストールのテストをしたか
  • 全てのバイナリの実行テストをしたか

といった項目の確認をします。Tracチケットがなかった場合、わざわざ作る必要はないのですがうっかり作ってしまいました。うっかり作ったとはいえ、チケットを作ってしまったのでチケットのURLをコミットメッセージに含めました。

とりあえずここまで。提出したPull Requestがマージされるのか、それとも修正を求められるのか、とりあえず見守ります。野良portsとしてのビルドはご自由に。

その後

無事にマージされました。いくつか指摘があって、

  • PulseAudioのvariantを削除した理由をコミットメッセージで説明する
  • うっかりepochを削除してしまったので元に戻す

という変更が必要でしたが、大きな変更ではありませんでした。

FreeRDP 2.0系ではMacとの互換性も向上していて、以前はPulseAudioを経由しないと音が出せなかったのがMacのネイティブオーディオをサポートしたため必要なくなったというのがvariantを削除した理由です。


2018-01-31 [長年日記]

実行中のプロセスの環境変数を調べる

いつも忘れるのでメモ。

Linuxの場合

procfsを参照すればわかるが、いい感じに表示するためにodを使う。

od -S1 /proc/<pid>/environ

ref: https://qiita.com/Sheile/items/93171a2c428710700469

FreeBSDの場合

FreeBSDの場合はprocfsがないとは言わないが、procfsをマウントしても /proc/<pid> 以下に environ がなく環境変数を取得できない。

このため、baseに含まれるprocstatを使って調べる。

procstat -S1 -e <pid>

その他

macOSを含む各OS共通で ps eww <pid> でもいける。見た目が見やすいのはLinuxのprocfsに頼った方法なので、他のOSでいい感じに表示するにはどうしよう。


2017-12-31 [長年日記]

2017年に携わったOSSを振り返る

2017年もあと僅かとなりました。ここで、2017年に携わったOSSを振り返ってみます。

xrdp

自身の関わるOSSとし最大のcontributionのあるxrdpですが、2016年6月に開発者の仲間入りを果たしリリース体制の一新を訴えてきました。Pavel RoskinやDebianの手助けもあり、xrdpは2016年12月リリースのv0.9.1以降は 年に4回のTime-basedリリースを行う体制に変わりました。Time-baedリリースサイクルなので、時間が来たら重大なバグがない限り単純にリリースするだけという単純なものですが、概ね予定通りにリリースすることができました。

2017年のコミットを振り返ってみると、コミット数では私が109コミットで1位、続いてPavelが44コミットで2位、プロジェクトリーダーのJayが36コミットと続きます。コミット数だけでは語れないのですが、多くのバグ修正やリファクタリングで貢献してきたと思います。

a3yKrzfUW1bAEcdSjIy7JMUaZR3WXUVEspnX6qa9kqKjdLqLgGYNc4wONVhCFhsNoXeNg86U7YAwVhdtYYdZWADTDY-_Q2X2lLk1s8UUxlb06lgzieGNKa_gMT3OSXMEi0NzTmUvbB-Lg2zwhVvQu9ZLSEbuWAOydsgcWxu9mEnquQqF1BuQS-FjH_Ba-5neb4hCsWRQmDZ1rrHo2rbkTomUs9lSPDvLa2Uvxfvdm6fS5kd1Zu1NrBPwCcpsEm90fooJ7YZK8hoVd_KnfI70J2sMqCLBLT98s3GRLOAr_Ww56DfhwHhF5Y3qjpDX_5s0DJDAte4hjv9mXIyoKpNGzKv4Aj3sOx_3D9KKPIvmHuQA9NJEahniqvq2XBL-wpH41K2Q98xdRSUclL18jmAi4vI-HovLPztNpqDBQ5MKcoZKC236Sk21R9DK2ENceruoB2FOrGs_BZKZFqEn09vPOs0zvxAonRSYm-gQulh9OzUJLvM1SSsHwcp8fNL-x4Tnq9wJfBhCH8qk4AgxBXcrRUbqwzKwYQhHQW59F-9x2h4gwPQaWS-LIxKaKLz9SC2toDr-zd4CI9sWIGj0rDf1lIfvSswtnt0ZaQmtZVv2E4roKsCPOaT2lcbfjyU0GY7Sb8nZ6ZgfzQR_1p8rXJ6JpngeEtutFQnewQ=w750-h905-no?.jpg

10月には openSUSE.Asia Summit 2017 への登壇も果たしました。

xorgxrdp

xrdpのサブコンポーネントであるxorgxrdpですが、こちらは安定しているためそれほどコミット数は多くなく、1年間で14コミットでした。

FreeRDP

FreeRDPはオープンソースのRDPクライアント・サーバの実装として、xrdpと関係の深いプロジェクトです。

こちらには日常的に関わっているというわけではないのですが、今年は1つバグを報告して修正してもらいました。

tDiary

このブログにも使っているtDiaryですが、バージョン5系にアップデートしたところいくつかのプラグインでエラーが出るようになったため、直してPull Requestを送りました。

ところが、直し方がまずかったようで、作者のただただしさんに直してもらいました。

このバグの修正は最新リリースの v5.0.7 に含まれています。

まとめ

xrdpを中心に、その他のソフトウェアにも細々と貢献した1年でした。来年もよろしくお願いします。


2017-12-27 [長年日記]

xrdp v0.9.5 リリース

2017年12月27日、xrdp v0.9.5をリリースしました。四半期ごとのリリースに開発体制が変更になって以来、ちょうど1年、4回目のリリースです。リリースノートはGitHubのリリースページを参照ください。

今回のリリースの主なトピックはCVE-2017-16927の脆弱性修正です。xrdpチームからパッチが出ましたが、そのパッチには不備がありDebianから追加のパッチが提供されました

他には、オーディオ転送のためのPulseAudioモジュールのビルド方法が古くなっていたのをリニューアルし、最新の手順をリリースに含めています。xrdpでオーディオ転送を実現したい場合、下記ドキュメントを参照してください。

セキュリティフィックス

  • ローカルサービス拒否攻撃につながる脆弱性CVE-2017-16927修正

新機能

  • DEBUGより詳細な新たなログレベル TRACE の追加
  • RDP経由でのSSHエージェントフォワーディングのサポート(要FreeRDP)
  • 横ホイールによるスクロールを正式にサポート

バグフィックス

  • sesmanのポートがハードコードされていたのを修正
  • NeutrinoRDPモードでWindows Server 2008と接続した際、描画が乱れるのを修正
  • AACオーディオ転送で音が乱れるのを修正
  • vsockサポートを追加
  • TLS接続時にCPU使用率が100%になる問題を修正

その他の修正

  • US Dvorak キーボードサポートを追加
  • いくつかの誤解を招くログを修正
  • フィンランド語キーボードサポートを追加
  • Xorgの設定により親切なコメントを追加
  • PulseAudioモジュールのドキュメントを改定
  • その他多くのリファクタリング

既知の問題

Windowsのクライアントでオーディオ転送使用時、コーデックがMP3だと音が鳴らない不具合があります。AACを代わりに使用してください。


2017-11-28 [長年日記]

xrdp-sesman の脆弱性 CVE-2017-16927 を修正しました

各所から情報が公開されていますが、xrdp を構成する1コンポーネントである xrdp-sesman にバッファオーバーフローの脆弱性が発見されました。本脆弱性は既に修正済みですが、脆弱性のみを修正するリリースは行わず、来月2017年12月に予定している定期リリースに含む予定です。

xrdp-sesman の sesman/libscp/libscp_v0.c の scp_v0s_accept 関数内で、ネットワークから受け取った信頼できない整数値をサイズとして、固定長のバッファに書き込んでいました。これにより、xrdp-sesman プロセスのクラッシュにより DoS が発生する可能性があります。

デフォルトの設定では、xrdp-sesman は localhost:3350 を LISTEN しているため、リモートからの攻撃は受けず、ローカルユーザによる攻撃に限定されます。

パッチは下記の通り、可変長のバッファを確保することで対応しています。


2017-08-30 [長年日記]

運転免許の更新期間が「有効期間満了年の誕生日の前後1ヶ月」というデマは誰が広めたのか

「運転免許 更新 期間」などのワードで Google 検索すると、更新期間が「有効期間満了年の誕生日の前後1ヶ月」という説が多数ヒットする。 例えば unten-menkyo.com 内のページ (Web魚拓)が一例であるが、これは明らかに間違いである。

igsDvpk68UZDsPYGhHEknX056KKBqmMBwkEDpXbq4LQv4uynsJ_WCqhypGac8vve5DM2Yirk3LXar1sId3OWT1vRyJYlyYlfDGH8eU8VQZbHMEwPD5_fuJqdj-QuqeoWUIGn6kHdpKQ92-lcX39jPdxDSr4PuZJruHep1KkClLJK6RZ-XRvvg6Edz7BshZITqz7-INE5FEhwgG6ywBEOw7FEfHRysuYWEOCwvlJE_AiPAfsBYiWB3bbCYDeJkyq9cTPKGgmSV5gl0qrAj2oR4m7Xlk3ymOp9e0NVqSEplAH_59Z_5v69fTOlbLpW_vTV81lGwZXFxqdU878fbK0wVVjMQlMwl-A3kFvMqgSW2krlpa3lhSJQYtmOBy--JyKaER0eYZFv1W6F7kL_Rhwuhb9_Nusu1MaIj2PsCr9iSTS1ZQ2V2_zAgJ9kPF6n1PPRAOXo-WhTgStoxuGlzoK3S4QiS7RSYWgpeS8y7VoPn0pllCFuEVq99X7Ak2_vHAWAY583SkBGmDhlEG8D5kzsbr_v5VUDq2vYVA0qRY62XAeK4NymQEhGnFDklSFm6QMpZ5RGnycursoTJNYChfnuPCBrOKjeTrBFI03thdSTMOm1y-aODjDiN94cPhdesuyxb2sFaQ8_r1cZHn7blbwg3lB2NxZvYRUD_4_hMu1RwIjaIak=w498-h345-no?.jpg

なぜなら、運転免許の有効期限満了日は誰でも誕生日の1ヶ月後に設定されているからだ。12月生まれの場合有効期限満了日は誕生日の翌月で年を跨ぐ。「有効期限満了年」というのは文字通り有効期限満了日を含む年のことだから、「有効期間満了年の誕生日の前後1ヶ月」というのは有効期限が満了してから10ヶ月後から12ヶ月後までの2ヶ月間を指す。「更新期間が有効期間満了年の誕生日の前後1ヶ月」というデマを真に受けてしまうと、1〜11ヶ月生まれは有効期限満了前に更新を済ませなければならず、12月生まれは有効期限満了後10ヶ月経過してからようやく更新できることになる。12月31生まれの場合、有効期限満了年の2月1日から11月29日までは、有効期限が切れているのに運転免許の更新もできない空白期間が発生してしまう。

道路交通法を参照してみると、そんなことはない。運転免許を更新できる期間は

当該免許証の有効期間が満了する日の直前のその者の誕生日の1月前から当該免許証の有効期間が満了する日までの間(道交法6章5節101条)
となっていて、空白期間など存在しないし、更新期間は期限満了日の直前の誕生日の前後1ヶ月となっていて、「満了年の誕生日の前後1ヶ月」説とは丸1年ずれている。

道路交通法はコーナーケースまでしっかり考慮して設計されているのに、わざわざコーナーケースの考慮を外したものを広める輩がいることは理解に苦しむ。 「更新期間は有効期間満了年の誕生日の前後1ヶ月」とかいい出した輩が12月生まれでないことは確かであろう。

m5YftFJkZ9V-lFu9FTkjM2PplFCpZbcUWdHhcwM2-oCGImFPCViM8FVOMc9i0BYQA3z7dBuUf7yxVaDYlW4SG0DGZDg1XN2Z2sFnbotpQFFwLPyTZOjTHzH82jaxpks8Jz_C6Ot0Pe71-0FaFttAxNRv756HUTgEOV3L9iaOaK3YR5Dff44UQaLmGFoXLfzotDHGxQEtwnowyQj2gSR0_IgKOtGX9d5ISfdu2BlzDv2R1QeQT-BcDo9YEHWS1d-F4JsIKRh8YEfX2nHrXQ8dx2d8YPpDhw0YWoXhu4jL8Trq_d1xTfV3ge1WuwxKeaFHeY0YBndLbcRgXRBNrmD0hB0_VBjzaoZgNioxjcLDs6QNIDCg6KzGHzPGNAH-I3MRIcWUQ-O3CEaX06M-lw4AigKN5hu5tyqOOg-wT1AsOrsWJEQeg51fB6JWZFvyWnO2geFvKAvvk52ogXe9Hi50C8mePgulruy8-KAEhDC0UrS3miLCjPo7pDN3UsZe4HUcMGyA4Zne6p2fMfPtCoXCCyjXAGy8JNC5mwHyi7bGiebocNcgGv9GTtWV2Ek85CtAXsFZQYxda5Oy6Q-B-w7FbhNiwaq1qNz7Rr2bM-ix142sKVEdmzRyaoZ5iPBiXLouwcTHTnTNbp98Zteth9ZVl_jO6ejwSTjAuMJqiuZg0fqP4AQ=w605-h542-no?.jpg

unten-menkyo.com 内に「満了年の誕生日の前後1ヶ月」という記述があることは確かだが、これが一次出典であるという根拠はない。もっと前にいい始めた輩がいるのかもしれない。

「満了年の誕生日の前後1ヶ月」というデマがどこから生まれてどのように広まったか情報をお持ちの方は、教えていただけないでしょうか。


2017-08-29 [長年日記]

OpenSSH で全ユーザの公開鍵を1ファイルで管理する

この記事は、OpenSSH 6.6以上を使うことを前提とします。

OpenSSH ではユーザの公開鍵は通常 $HOME/.ssh/authorized_keys に置きますが、

  • 各ユーザのホームディレクトリに置くので管理者権限で鍵を追加する際にオーナー&パーミッションを意識するのが面倒
  • 置き場がホームディレクトリだと予めホームディレクトリを作成しなければならないのを避けたい (mkhomedir)
  • ホームディレクトリを持たないまたは揮発性のホームディレクトリを持つユーザにログインさせたい
  • ユーザに勝手に鍵を追加させたくない(管理者が鍵の追加・削除をコントロールしたい)

など、いくつかの理由で違う場所に置きたい場合もあります。

例えば sshd_config 内の AuthorizedKeysFile を使い、

AuthorizedKeysFile /etc/ssh/authorized_keys_%u

とすれば、ユーザごとに /etc/ssh/authorized_keys_<ユーザ名> というファイルが使われ、公開鍵ファイルを1ヶ所にまとめることができますが、ユーザごとに1ファイルとなっていて、全てを1ファイルで管理するというタイトルの要件は満たしていません。

そこで、AuthorizedKeysCommandAuthorizedKeysCommandUser を使います。これらの詳しい使い方については man ページを参照してください。仕組みを雑に説明すると AuthorizedKeysCommand を使い、特定のユーザの公開鍵を検索して、その公開鍵を認証に使うというからくりです。

まず、全ユーザの公開鍵を置くファイルのフォーマットを考えます。ただ公開鍵を並べただけでは、どの鍵がどのユーザのものかという情報がないので、それを付け加えてやるだけです。今回は以下のようなフォーマットにしました。

%ユーザ名%公開鍵

具体的にはこんな感じ。

%alice%ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQCg+hAJJvTWHD1Rv+H5RWu30QXXHRoLHdZbfUydG7...
%bob%ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQCh2o84D5La+7LnURTMJNYrNlL0v6BsTAa7Sg27BF...

このファイルからユーザごとの公開鍵を検索するためのコマンドを作成します。要件は引数にユーザ名が与えられたときに、通常の authorized_keys と同様の鍵リストを返すこと。

シェルスクリプトで実装して、こんな感じになります。/etc/ssh/authorized_keys というのは、上記のフォーマットで記述された、全ユーザの公開鍵を1つにまとめたファイルです。

#!/bin/sh

AUTHORIZED_KEY_FILE=/etc/ssh/authorized_keys
PATTERN="^%${1}%"

if [ $# -ne 1 ]; then
        exit 1
fi

grep ${PATTERN} ${AUTHORIZED_KEY_FILE} | sed -e "s|${PATTERN}||"

このスクリプトを /etc/ssh/find_authorized_keys.sh として保存して、所有者を root にし、所有者以外からは書き換えられないパーミッションにしておきます。

このスクリプトは AuthorizedKeysCommand を実行するための専用ユーザで実行することが推奨されているので、適切にパーミッションを設定します。実行するユーザは AuthorizedKeysCommandUser で指定しますが、これは必須です。また、前述の /etc/ssh/authorized_keys ファイルも当該ユーザで読めるパーミッションにする必要があります。

設定の差分を抜粋するとこんな感じ。sshd_config を書き換えたら、sshd を再起動してログインできることを確認。

AuthorizedKeysFile        none # 通常の $HOME/.ssh/authorized_keys を無効化するため
AuthorizedKeysCommand     /etc/ssh/find_authorized_keys.sh # nobody ユーザで実行できるようにしておく
AuthorizedKeysCommandUser nobody # root でない上記スクリプト実行用のユーザ