目次
こんにちは、ともです。
この記事ではセッション固定攻撃とセッションハイジャックについて、駆け出しエンジニアである僕が理解をまとめます。
駆け出しエンジニアではありますが、基本的な脆弱性は理解したいと思い勉強中です。PHPでセッション固定攻撃をしてみて、セッションハイジャックしてみます。
セッションとクッキーとセッションハイジャック
そもそもセッションとクッキーとはどのようなものなのでしょうか?
下の図で説明いたします。

ブラウザ側にはクッキーという名のデータを格納する場所があります。またサーバにもセッションというなのデータを格納する場所があります。
あなたのWebブラウザからのアクセスかどうかはセッションIDによって識別する事ができます。
上の図ではexample.comにはsess2というセッションIDが格納されています。この状態でexample.comにアクセスするとsess2に対応した情報(user-idが2でnameがtomo2)であることを特定する事ができます。
ログイン済みかどうかをセッションに格納しておけば、ログイン済みユーザが判定できますね。
- Chromeをお使いの場合は、設定 > 詳細設定 > コンテンツの設定 > クッキーでブラウザに格納されているクッキーを確認する事ができます。
セッションハイジャックとは、セッションIDが漏洩ぢし、勝手にログインされてしまい乗っとられることです。
セッションIDが漏洩する1つ原因にセッション固定攻撃というものが存在します。
セッション固定攻撃
セッションIDがバレるには
- あなたが利用しているセッションIDが漏れる
- あなたが利用しているセッションIDを攻撃者が指定する
の2つあり得ますが、セッション固定攻撃とは2つ目の、攻撃者がある脆弱性を突いてセッションIDを指定してくる攻撃方法です。
セッションIDとは他者が特定できないランダムな文字列が生成されるはずですが、セッション生成時にセッションIDを固定する方法があります。
// example.com
<?php
session_start();
echo session_id();
?>
<a href="example.com?PHPSESSID=abcd">攻撃用のリンク</a>
このように、『?PHPSESSID=abcd』とURLの後ろにつけると、生成されたセッションIDは『abcd』となります。
これはセッションアダプションという脆弱性です。
しかし、この脆弱性は基本的に発生し得ません。
なぜなら、php.iniのsession.use_trans_sidがデフォルトで『0』、session.use_only_cookiesがデフォルトで『On』であり、固定する事ができないからです。
session.use_cookies | セッションIDの管理にクッキー利用する(デフォルト1) |
---|---|
session.use_only_cookies | セッションIDの管理にクッキーのみをしよう(PHP5.3.0からは1) |
session.use_trans_sid | クッキーが利用できない場合にはGET変数・POST変数によるセッション管理を行うか(デフォルト0) |

上記のように設定した場合、URLパラメータでセッションIDを固定できてしまいます。
この脆弱性がある場合、セッションIDを固定した上で被攻撃者にログインさせることで、攻撃者はセッションIDを知ることができます。
セッションハイジャックの対処方法
- ログイン後にセッションIDを再発行し、セッション固定攻撃を回避する
- セッションIDの管理をクッキーでのみ扱う
- 認証にはセッションIDだけでなくパスワードなどの多重チェックを
- エスケープ処理をする(XSS対策)
セッションIDの更新
セッションIDの更新にはsession_regenerate_id(true);
が利用できます。引数にtrueをセットした場合、サーバのセッションファイルを破棄した上でセッションIDを更新します。
セッションIDの管理をクッキーでのみ扱う
セッションIDの管理は
- クッキー
- GET・POSTパラメータ
で管理する事ができますが、php.iniの設定によってクッキーのみでセッションIDを管理するようにできます。
session.use_only_cookies = 1;
と設定する事でセッションIDの管理をクッキーでのみ行うようにできます。
認証にはセッションID以外の多重チェックを行う
セッションIDでのみ認証を判定していては、セッションIDが盗まれた場合に全てバレてしまいます。
パスワード等やユーザIDなどの多重チェックを行う事で乗っ取りの対策をする事ができます。
エスケープ処理をする
ユーザからの入力をエスケープ(安全な形に変換)することを怠たらないようにします。
ユーザ入力があるSQL文に対しては、プリペアドステートメントを利用することで、適切にエスケープする事ができます。
また、ブラウザで描画する場合はhtmlspecialcharsメソッドでエスケープし、スクリプトを実行されないように対処できます。
まとめ
セッション固定攻撃は攻撃者の指定したセッションを利用しログインさせられ、攻撃者にセッションIDがバレてしまう攻撃だという事が分かりました。
- セッション固定攻撃とは、攻撃者がセッションIDを指定してくる攻撃である
- セッション固定攻撃の原因は、PHPの設定によってはURLにパラメータを仕込むとランダムな文字列として生成されるセッションIDを指定する事ができるから
- 対処方法としては、ログイン後にセッションIDを更新することで対処可能
- セッションハイジャックとはセッションIDを利用して、正規ユーザがログインしたとなりすますこと
駆け出しエンジニアであっても、しっかりと脆弱性と対処方法について理解しWebアプリケーションを開発したいです。