nFact

n!

OpenJDKで遊んでいたらバグを見つけたのでBug Reportを出した話

概要

OpenJDK 11(11-ea+15)で、 java -XX: とするとセグメンテーション違反で落ちるエラーに遭遇しました。 既に修正が入った最新のEA版が公開されていてもう大丈夫かなという雰囲気なのでバグ発見から報告、修正までの流れ等を記事にします。*1

報告したバグレポートのURL

Java Bug System: [JDK-8204055] SIGSEGV in java -XX: - Java Bug System
Java Bug Database: Bug ID: JDK-8204055 SIGSEGV in java -XX:

見つけたきっかけ

先日のJava Day TokyoでGraalのセッションが聞けたので試そうとしてたのですがなかなかうまく行かなくて、 その試行錯誤中にたまたまtypo

$ java -XX:

を実行してしまったのが始まりでした。

Unrecognized VM optionとまでは出るのですが、その後のセグフォがなんか変だなというところから、よくよく見てみるとどうやらOpenJDK 10では再現しないことが分かり、バグ報告に至りました。

報告方法

以前からバグ報告ページBug Reportがあることは知っていて*2、 既存バグを検索してもそれっぽいのが無かったので普通にバグ報告をしました。

Report Classificationを書くときにちょっと迷うのがComponent/Subcomponentに自分のイメージしたやつがないときなんですが、 間違った選択をして報告をしてしまっても、良い感じに修正してくれるのが良いなぁと思いました。
実際、今回のチケットではjavaコマンドだったのでtoolsのlauncherがそれっぽいかな?とか思っていたのですが、報告後にhotspot/runtimeに修正されていました。 (こういうのってどこで調べれば良いのかがわからない。。。)

バグ報告をすると、Oracleによるレビューが入った上でJDK Bug SystemとOracle Java Bug Databaseに公開されるという流れになるみたいです。

私の場合、報告してから公開されるまで1日ぐらいかかりました。 OracleかOpenJDKのサイトで見たような気がしますが、セキュリティ的な理由とかで すぐ公開しちゃまずいバグかどうか等をレビューして判断しているみたいですね。

報告してから解決に向かうまで

報告者には、バグ報告ページで入力したメールアドレスにこのようなメールが届きます。

f:id:noko_k:20180613003519p:plain

記載されているURLを見て、初めて重複バグなのか等がわかるという感じですね。 バグに関する調査や、修正作業はバグチケット上のコメントでやり取りされ、他のチケットの関連付けや修正方法の検討がどんどん進んでいきます。

ところで、「Assigneeに記載されている方の名前、どこかで見たことある気がする...」と思ってググったら、この本を書いた方でした。なんかすごい方っぽい....!

https://www.amazon.co.jp/Programming-Language-Gosling-Holmes-Arnold/dp/0321349806

私の報告したバグが、Oracleのすごいエンジニアによって徐々に紐解かれていくようのは、見ててとても楽しいものですね。

このコメントが投下されたのを見たときは思わず「おぉー!」っとなり、しばらくしてリポジトリに修正がpushされたのを確認して二度「おぉ〜!」となったのは、今まで無かった体験でした。

The SEGV was introduced with the fuzzy matching flag logic refactoring in JDK-8198554. In:

Proposed fix has three parts:

  1. Update StringUtils::similarity to assert the two strings are not NULL and not zero-length.
  2. Update Arguments::process_argument to not call fuzzy_match for a zero-length arg.
  3. Update match_jfr_option to not trip-over the zero-length arg. (Still not quite sure why it does what it does there.)

修正コミット: jdk/jdk: 01e20d8850e3

OpenJDK 11(jdk-11-ea+17) では

修正されていることが確認できました🎉

> /opt/jdk-11-ea15/bin/java -XX:
Unrecognized VM option ''
fish: '/opt/jdk-11-ea15/bin/java -XX:' terminated by signal SIGSEGV (Address boundary error)

> /opt/jdk-11-ea17/bin/java -XX:
Unrecognized VM option ''
Error: Could not create the Java Virtual Machine.
Error: A fatal exception has occurred. Program will exit.

おわりに

以上、バグの発見からその報告、解決までを体験できたのでそれを記事にしました。

バグ報告をすると今までにない体験を得られ、英語が書けなくてもコードは伝わる(もちろんちゃんと書けるならそのほうが良い)、ちゃんと修正されるというのが一番の収穫でした。 修正のスピード感も想像よりもずっと速くて、流れも全部コメントで追えることができてというのも良い体験でした。

今度はバグレポと一緒にパッチを送信できるようになりたいなぁという気持ちになったので、のんびり頑張っていきたいと思います。

*1:ググってもあまり記事こういう系の記事とかが無かったので大丈夫なのかな?という気持ちになりました。規約等に違反している場合は修正/削除しますのでご連絡ください

*2:今回で2度目のバグ報告でした

手動ダウンロードしたアプリケーションをGNOME 3のDockに表示させる方法

f:id:noko_k:20180505165437p:plain←アプリケーションをここに追加したい。

概要

GNOMEDesktop Entry Specificationと呼ばれる仕様に準拠している模様。
なので、その形式通りにファイルを書いてインストールしてやれば(私はここがわからなかった)、かんたんにGNOME 3に登録することができる。

1. desktopファイルの準備

任意の場所に次のような .desktop ファイルを準備する。
ファイル名は、わかりやすく IntelliJ IDEAであれば intellij.desktopFirefoxであれば firefox.desktop などの名前をつける。

[Desktop Entry]
Name=アプリ名
Exec=アプリを起動するための実行可能ファイルの場所
Icon=アプリのアイコンファイル
Type=Application
Categories=GTK;GNOME;

2. desktop-file-install する

1で作成したdesktopファイルをinstallする。

sudo desktop-file-install intellij.desktop

インストールが完了すると、Windowsキーを押して出てくる画面で「IntelliJ」などと打つと(Name=で指定した名前で)出てくるので、 アイコンをそのまま右クリックして「お気に入りに追加」をするとやりたいことができる。

他にはまったところ

desktopファイルのバリデーションをする desktop-file-validateコマンドはファイルの文法上の問題しか検出しない模様。
GNOMEで読み込めない、または読み込んでもアイコンが表示できないdesktopファイルでも、エラーや警告なしで通ったように見えてしまう。

メモ

標準のdesktopファイルの保管場所

$XDG_DATA_DIRS/applications

お気に入りの設定の格納場所

$ dconf read /org/gnome/shell/favorite-apps
['org.gnome.Nautilus.desktop', 'org.gnome.Software.desktop', 'org.gnome.Terminal.desktop', 'firefox.desktop', 'intellij.desktop']

ここにインストール済みのdesktopファイルを記述すれば、お気に入りアプリとして表示することができる。

$ dconf write /org/gnome/shell/favorite-apps "['org.gnome.Nautilus.desktop', 'org.gnome.Software.desktop', 'org.gnome.Terminal.desktop', 'firefox.desktop', 'intellij.desktop', 'foo.desktop']"

dmsetup targetsでsnapshot-merge等が足りないときに打つコマンド

$ sudo modprobe dm-snapshot

これで、 snapshotsnapshot-merge 、 snapshot-origin が使えるようになる。

全体

$ sudo dmsetup targets
striped          v1.6.0
linear           v1.4.0
error            v1.5.0
$ sudo modprobe dm-snapshot
$ sudo dmsetup targets
snapshot-merge   v1.4.0
snapshot-origin  v1.9.0
snapshot         v1.15.0
striped          v1.6.0
linear           v1.4.0
error            v1.5.0