徳丸本読書会Sql csrf

1,291 views

Published on

0 Comments
2 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total views
1,291
On SlideShare
0
From Embeds
0
Number of Embeds
3
Actions
Shares
0
Downloads
7
Comments
0
Likes
2
Embeds 0
No embeds

No notes for slide

徳丸本読書会Sql csrf

  1. 1. SQLインジェクション  &  CSRF   原理とその対策(for  Perl) 徳丸本勉強会  2013.11.17   @addsict github.com/addsict/TokumarubonDokusyokai  
  2. 2. hIps://github.com/addsict/TokumarubonDokusyokai github.com/addsict/TokumarubonDokusyokai  
  3. 3. SQLインジェクション github.com/addsict/TokumarubonDokusyokai  
  4. 4. SQLインジェクションとは •  Webサイトの脆弱性攻撃の定番中の定番   •  SQL文の構文を「破壊」し悪意のあるSQLに変 え,  テーブルの削除やパスワードの漏洩など を導く攻撃   •  今日は文字列連結ではない安全なSQLの組 み立て方を見ていく   –  あまり深堀りはしません…   github.com/addsict/TokumarubonDokusyokai  
  5. 5. どんな風にSQL文が壊されるの? •  WebアプリケーションなどではSQL文のリテラル 部分がパラメータされていることが一般的   –  リテラル:  文字列リテラル,  数値リテラルなど   •  パラメータに含めた変数が展開されると,  意図し ないSQLに変わる危険性   –  リテラル以外のものが注入される   my  $sql  =  “SELECT  *  FROM  users  WHERE  userid=‘$userid’”;   $userid  =  “’;DELETE  FROM  users;-­‐-­‐”;  を注入  ⇒   “SELECT  *  FROM  users  WHERE  userid=‘’;  DELETE  FROM  users;-­‐-­‐’”;  #  -­‐-­‐  以降はコメントアウト   github.com/addsict/TokumarubonDokusyokai  
  6. 6. Exercise:  SQLインジェクション •  SQLインジェクションを実際にやってみましょう   –  レポジトリのsql-­‐injec`on/  内のREADME参照   •  補足   –  DBD::mysqlの場合,  複数SQL文を一度に実行する mysql_mul(_statementsがデフォルトではoffなの で,  DBI-­‐>connect時にonにしてある github.com/addsict/TokumarubonDokusyokai  
  7. 7. SQLインジェクション対策 •  プレースホルダを使用するのが一番安全   –  静的プレースホルダ   –  動的プレースホルダ   github.com/addsict/TokumarubonDokusyokai  
  8. 8. 静的プレースホルダとは? •  SQLの実行方法に基づいた安全なSQLの組み立て方   –  SQLの実行の流れ:  SQLパース ⇒  構文解析  ⇒  …  ⇒  実行   •  値が未定のパラメータを含んだSQLを構文解析まで済ませておき,   後にパラメータをバインド   –  構文解析が完了したことでバインド値によらず構文が「破壊」されるこ とはない  ⇒  原理的に安全   –  DBIではprepareで構文解析を行い,  bind_paramでパラメータをバイン ドし,  executeで実行   •  *execute時にパラメータをバインドできるが,    パラメータ値が常にVARCHAR型 とみなされSQLの実行時に文字列型から実際の型への変換が行われる   •  Prepared  Statementと呼ばれる   my  $sth  =  $dbh-­‐>pepare(“SELECT  *  FROM  users  WHERE  userid  =  ?”);  #  ?がプレースホルダ   $sth-­‐>bind_param(1,  “addsict”,  SQL_VARCHAR);  #  パラメータをバインド   $sth-­‐>execute(); github.com/addsict/TokumarubonDokusyokai  
  9. 9. 動的プレースホルダはどう違うの? •  やっていることは文字列連結と変わりない   –  アプリケーション側で文字列連結するのではなく,   ライブラリ・ドライバ側で文字列連結を行う   –  DBに応じて適切なエスケープ処理やリテラルの 型をチェックし安全性を担保   •  DBD::mysqlの場合動的プレースホルダがデ フォルトの挙動   –  静的プレースホルダを使うにはDBI-­‐>connectで mysql_server_prepareオプションをONにする github.com/addsict/TokumarubonDokusyokai  
  10. 10. ORM内でのSQLの組み立て方 •  普段使用しているORMが実際にどのように SQLを組み立てているか見てみましょう   –  プレースホルダは使われていますか?   •  Tengの場合   –  SQL生成はSQL::Makerという別のモジュール   –  SQL::Maker::_make_where_condi`on  ⇒   SQL::Maker::Condi`on::add  ⇒   SQL::Maker::Condi`on::_make_tern   github.com/addsict/TokumarubonDokusyokai  
  11. 11. Exercise:  SQLインジェクション対策 •  先ほどの脆弱性を含むサイトを,  SQLインジェ クション対策するように改変してください   github.com/addsict/TokumarubonDokusyokai  
  12. 12. 合わせて読みたい •  「安全なSQLの呼び出し方」  IPA   –  hIp://www.ipa.go.jp/files/000017320.pdf   •  「SQLインジェクションゴルフ」 徳丸浩の日記   –  hIp://blog.tokumaru.org/2013/06/sql-­‐injec`on-­‐ golf.html   •  「mysql  の server  side  prepared  statement  っ て速いの?」 tokuhirom’s  blog   –  hIp://blog.64p.org/entry/20080807/1218080835   github.com/addsict/TokumarubonDokusyokai  
  13. 13. CSRF github.com/addsict/TokumarubonDokusyokai  
  14. 14. CSRFの概要 •  Cross  Site  Request  Forgeriesの略   –  Forgeryって?  →  (文書などの)偽造の意   •  Webアプリケーションの「重要な処理」を行うリクエスト を偽装して実行する(なりすまし)攻撃   –  重要な処理:  パスワード変更,  ブログ投稿など   冪等性を持たない処理   •  できることはWebアプリにHTTPリクエストを送るだけな ので,  サーバサイドのロジックのみ悪用できる   –  この点でXSSとは異なる   •  有名な事例   –  mixiのはまちちゃん事件   github.com/addsict/TokumarubonDokusyokai  
  15. 15. CSRF攻撃成立までの流れ •  ユーザがターゲットサイトAにログインする   •  ユーザが悪質なサイトBにアクセスする   –  サイトBでは(非表示に設定された)iframe内で攻 撃用ページB’にアクセスする   •  iframeを使うのはユーザに攻撃がばれないようにする ため   –  ページB’ではサイトAの「重要な処理」を行うリクエ ストを発行することで攻撃完了   この2つの条件が満たされただけで攻撃されてしまう!! github.com/addsict/TokumarubonDokusyokai  
  16. 16. Exercise:  CSRF •  CSRF攻撃を体験してみましょう   –  レポジトリのcsrf/  内のREADME参照 github.com/addsict/TokumarubonDokusyokai  
  17. 17. CSRF攻撃が生まれる原因 •  ブラウザ(の仕様)が悪い!   –  form要素のac`on属性にどのドメインのURLでも指定 可能   •  同一生成元ポリシーは適用されない   –  クッキーは自動的にリクエスト先のサイトに送信され る   •  ログイン済みであればセッション情報がクッキー上に   •  正規リクエストと偽造リクエストの違いはReferer の違いだけ   –  ログを見てリクエストヘッダを確認してみよう github.com/addsict/TokumarubonDokusyokai  
  18. 18. CSRFの対策は? •  まずCSRF対策が必要なページを区別   –  全てのページにCSRF対策が必要なわけではない   •  CSRF対策されると困るケースもある(他のサイトからの リクエストが重要なページなど)   •  対策手法   –  Refererをチェックする   –  第三者が知りえないトークンを埋め込む   github.com/addsict/TokumarubonDokusyokai  
  19. 19. 対策手法 -­‐  Refererのチェック -­‐   •  正規リクエストと偽造リクエストはRefererが異 なる   –  render_403  if  header-­‐>{referer}  ne  proper_referer;   •  注意点   –  Refererを送信しないように設定する利用者もいる   –  Refererチェックの漏れが起こりうる •  hIp://tokumaru.jp/  からのリクエストを許す場合以下の 正規表現で大丈夫?  xxxxにURLを入れて試してみよう   perl  -­‐e  ”$referer  =  xxxx;  if  ($referer  =~  m#^hIp://tokumaru.jp#)  {print  'ok';}" github.com/addsict/TokumarubonDokusyokai  
  20. 20. 対策手法  -­‐  トークンの埋め込み  -­‐ •  攻撃者が事前に知りえない情報をリクエストに含めて渡す   –  POSTの場合,  リクエストbodyにトークンを含める   –  トークンとしてセッションIDを使うのが簡易な方法   •  <input  type=“hidden”  name=“token”  value=“<:  $sid  :>”>   •  CSRFではターゲットサイトのCookieには触れないことに注意   •  twiIerもこの対策を取っている   –  Chromeの開発者ツールを開いた状態でツイートしてみよう.   ツイート内容と共に何がPOSTされてますか?   •  実装めんどい?   –  それCPANにあるよ Plack::Middleware::CSRFBlock   •  POSTメソッドを使用するformタグを探し,  トークンを自動で埋め込む   •  既存アプリのコードに手を入れないでok   github.com/addsict/TokumarubonDokusyokai  
  21. 21. Exercise:  CSRF対策 •  先ほどの脆弱性を含むサイトを,  CSRF対策す るように改変してください   –  Refererチェックで対策する例   •  csrf/refererブランチ   –  トークンで対策する例   •  csrf/tokenブランチ github.com/addsict/TokumarubonDokusyokai  

×