カテゴリー: PHP Security

HMACを利用した安全なAPIキーの送受信

Webアプリケーションの機能をサービスとして提供する場合、ランダムな値の秘密のAPIキーを鍵とすることが多いです。

// 何らかのAPIを呼び出す
http://example.com/api/v2/get_something?api_key=qwertyuiop

シンプルな方法で使いやすいですが、鍵となるAPIキーをそのまま使っているので鍵が漏洩する可能性があります。HMACやHKDFを使うと鍵となるAPIキーを直接使わないでAPIへのアクセスを認証できます。

もっと読む

hash_hmac()の使い方

HMACの応用的な使い方をここ数本のブログで書いてきましたが、HMACの基本的な使い方を紹介していませんでした。リクエストパラメーターを安全に検証/バリデーションする方法を例に紹介します。unserialize()を安全に利用する利用例にもなります。

参考:

HMACハッシュの使い方のまとめ

もっと読む

パスワードのハッシュ化

HMACを使った鍵の生成(導出)方法を書いているので、念の為にパスワードのハッシュ化方法について書いておきます。一般にユーザー入力のパスワードをアプリケーションデータベース等に保存する場合、HMACやHKDFを使わずに、password_hash()を使うべきです。

参考:

もっと読む

ハッシュ(HMAC)を使って弱い鍵を強い鍵に変える方法

既存の鍵から別の鍵を導出する方式としてはHKDF(RFC 5869)があります。AES用に弱い鍵から強い鍵を作るにはHKDFでなくてもHMACで十分です。実際、HKDFはHMACを組み合わせて鍵を導出しているだけなので、ここで紹介するHMACのみの鍵導出と同等です。

※ PHP 7.2からHKDFを実装したhash_hkdf()を使えます。hash_hkdf()が利用できる場合はシンプルにhash_hkdf()を使うと良いです。

もっと読む

PHPのmt_rand()/rand()問題

PHPのmt_rand()とrand()には状態の初期化/再初期化に問題があります。話しを簡単にするためにrand()をmt_rand()のエイリアスにする提案

https://wiki.php.net/rfc/rng_fixes

が適用された状態を前提にMT rand問題として解説します。しかし、基本的には古いPHPでrand()を使う場合も同じ(かそれ以上)の問題があります。

そもそもMT randは暗号理論的に安全な乱数生成器ではありません。安全な乱数の取得に使ってはなりませんが、MT rand以前の乱数に比べ予測が困難、ということで不適切な箇所で利用しているケースが散見されます。

結論から言うと、MT randで生成された乱数値は安全ではなく非常に危険1、です。

もっと読む

ISO 27000の入力データ妥当性確認

セキュリティ標準では入力データの妥当性確認(入力バリデーション)が要求されています。具体的な方法はBS 7799(英国のJIS規格のような物、2000年に国際標準化)が作られた時(90年代後半)から記載されており、前の版までのISO 270001にも記載されています。2013年版のISO 27000ではセキュアプログラミングが普及したので具体的な方法などは省略しています。(日本では普及していないような。。)

セキュアプログラミングの基本中の基本がセキュリティ対策ではない、というような意味が全く解らない議論もあるのが現状です。

かなり昔に似たようなことを書いたようにも思いますが、記憶が定かではありません。今でも有効なので改めて(?)ブログにします。

もっと読む

ホワイトリストの作り方

ホワイトリストの考え方/作り方は難しくありません。しかし、間違えていることが少なくないようです。

GoogleがCSP(Content Security Policy – ホワイトリスト型のJavaScriptインジェクション対策)の利用状況を調べたところ以下のような結果が得られました。

we take a closer look at the practical benefits of adopting CSP and identify significant flaws in real-world deployments that result in bypasses in 94.72% of all distinct policies.

なんと、約95%のCSP利用サイトがCSPの保護が無効になるような設定になっていた、としています。

もっと読む

プライベートサイトを作るならPHPのURL Rewriterを使う

クロスサイト・リクエスト(他のWebサイトから自分のサイトへURLリンクやPOSTでアクセスする)を制限したいWebアプリケーションは結構あります。例えば、ホームルーターの管理ページを作る場合、クロスサイト・リクエストは有用などころか有害です。ホームルーターの管理ページにはクロスサイト・リクエストによる脆弱性が多数報告されています。

PHPの基本機能を使えば、クロスサイト・リクエストを簡単かつ丸ごと拒否することができます。CSRFやXSS1を完全かつ簡単に拒否する仕組みを作れます。

もっと読む

完全なSQLインジェクション対策

不完全なSQLインジェクション対策だけで、SQLインジェクション対策は万全、と誤解しているケースが少なくないです。

  • プリペアードクエリ/プレイスホルダを使ったSQLインジェクション対策でOK

は誤りです。「とにかくプレイスホルダを使おう」では脆弱性は無くなりません。

簡単な証明:プリペアードクエリ”だけ”では、識別子(カラム/テーブル等)を使うソートクエリ、特定カラム抽出クエリを”原理的”に無害化できない。識別子のエスケープ/バリデーションが必須。(問題はコレだけはありません)

似たような間違いに「出力対策をするのがセキュリティ対策」だとする考え方があります。こういう考え方になる原因はセキュリティ設計や原則を理解していないことにあると思われます。

出力対策”のみ”のセキュリティはアンチプラクティス

アンチプラクティスであっても正しく動作するならまだ良い方です。しかし、論理的・原理的に出力対策”だけ”では正しく動作するアプリケーションは作れません

参考:

もっと読む