Shikata Ga Nai

Private? There is no such things.

第35回:クラッシュレポートから脆弱性のヒントを探す

Hello there, ('ω')ノ

💥 クラッシュレポートとは?

アプリがエラーや例外で停止したときに、次のような情報をログやレポートに出力します:

  • クラス名・メソッド名
  • 行番号
  • スタックトレース(処理の流れ)
  • エラーの原因(NullPointerException など)
  • ローカル変数の値(設定次第で)

開発者にとっては重要なデバッグ情報ですが、この情報が外部に流出していたら? → 攻撃者は、内部構造・APIのパス・処理の分岐などを知る手がかりにします。


🧪 診断でのチェックポイント

✅ 1. エラー発生時にログが出力されていないか?

try {
  someApiCall();
} catch (Exception e) {
  e.printStackTrace();
  Log.e("Crash", e.getMessage());
}

printStackTrace()e.getMessage() を使うと、詳細なエラー情報が logcat に出力されます。 これが外部で観測可能な環境だった場合、設計や内部構造を推測されるリスクがあります。


✅ 2. クラッシュレポートサービスの内容を確認する

Firebase Crashlytics などを使っている場合、クラッシュ時に次のようなデータが送信される可能性があります:

  • 例外情報(NullPointerException, IllegalArgumentExceptionなど)
  • 呼び出しスタック(クラス名・メソッド名・ファイル名・行数)
  • ユーザーIDや端末情報(設定次第)

レポートに含まれる情報を必要最小限に絞っているか?を確認しましょう。


✅ 3. 外部公開されていないか?

  • 開発者用のクラッシュログファイルが外部ストレージに保存されていないか?
  • クラッシュレポートがWeb API経由で外部送信されていないか? 例:https://logs.example.com/crashreport?error=...

→ これらが暗号化されず送信されている場合、盗聴やなりすましのリスクがあります。


🧠 クラッシュレポートが悪用される例

脆弱性のヒント クラッシュログの内容
内部APIのパス com.example.api.AdminApi.getSecretToken()
認証エラー時の処理分岐 AccessDeniedException at AuthHandler.java:54
データ構造 java.lang.NullPointerException at UserInfo.getEmail()
バイパスできる条件 if (user.isAdmin()) { ... } else { crash } のような分岐ログ

🛡️ 診断&対策ポイント

チェック項目 対策内容
ログに詳細を出力していないか? printStackTrace() は開発中のみ使用、リリースビルドでは無効化
ユーザー情報が含まれていないか? クラッシュレポートに名前やIDなど個人情報を含めない
エラー発生時に処理を分岐していないか? 意図的なクラッシュで内部状態を調査されるのを防ぐ
クラッシュレポートを外部に保存していないか? ローカルやサーバー送信時には暗号化と認証を必須に

✅ まとめ

  • クラッシュレポートは、内部構造を探る強力な手がかりになる
  • logcatやクラッシュログを診断し、クラス名・API・条件分岐の漏洩がないかをチェックしよう
  • クラッシュログの出力範囲を最低限に抑える設計がセキュリティ的にも重要
  • ログの出力と送信を制御する仕組みを導入し、攻撃者にヒントを与えないことが大切

Best regards, (^^ゞ