ひとこと

― 今日のひとこと ―
気付けば前回更新してから2年以上経ってた
(2023.10.25)

2013年1月28日月曜日

Hackme攻略 Lv2

今回はHackme Lv2の攻略。


以下、Hackmeの攻略に関するネタバレを多大に含みます。自力で攻略したいなら見ちゃだめです。





[Lv2]




1.ヒントを探す

今回もまた、ページを眺めてみてもこれといった発見はない。右クリックもできる。
ソースコードにもアカウント情報は記載されていない(当然といえば当然だが)
物は試しとLv1と同じ情報を入力してみると・・・

「ユーザ名またはパスワードが違います」というエラーメッセージが表示された。

そういえば、たまにパスワードだけが間違っているって表示しちゃうサイトがあるが、
それって結構危ないんだよな。IDはデータベース上に存在してるって自分で証明してるわけだから。
Lv2さんはそんなに甘くないってことだな。流石や!


2.考える

さて、どうやらユーザが見ることができる範囲にヒントになるような情報はなさそうだ。
仕方がないので少し専門的な知識を使おう。

Q.Webサイトのログインフォームを作る際に注意しなければならない攻撃は?
A.SQLインジェクションです。

Q.SQLインジェクション対策として有効なのは?
A.サニタイジング処理またはバインド機構です。

という具合に、データベースとWebセキュリティの基本を知ってれば誰もが考える。
では早速検証してみよう。


3.検証する

要は、SQLにおいて意味を持つ特殊文字がどう扱われているかを調べればいいわけだ。
代表的なのはアポストロフィ(')だな。

というわけでIDをてきとーに入力し、パスワードにただ1文字 ' と入力してみる。


結果は・・・


pg_queryとかいういかにもデータベース扱ってますよと云わんばかりに命名されたメソッドでエラーが!
アポストロフィ付近で文法エラーが起きてクエリが発行できなかったと書いてある。

さっきまでクラッカーにヒントを与えない完璧なエラーメッセージを発し続けていたLv2さんが
こんな明瞭なヒントを出すなんて・・・妙に変だなぁ・・・

プログラムでサニタイジングやプレースホルダが使われているなら、
はじめのように「ユーザ名またはパスワードが違います」と表示されるはず。
しかしSQL文法エラーが起きているという事は、入力された特殊文字がSQL文中で意味を持っているということ!
SQLインジェクションが有効だと考えられるね。


4.Hackyou!

SQLインジェクションというのは、簡単に言えばフォームにSQL文を打ち込んで実行させる手法だ。
ログインフォームでは、認証に用いられるクエリの実行結果が「true」になるようにSQL文を入力すればいい。

たとえば、↓のようなSQL文でパスワードの認証を行っているとする。
  SELECT user_password FROM user_info WHERE user_password = '<入力された値>';
この一文の内、WHERE句の条件に注目する。
素直に「password = ?」の形でクラッキングを試みたところで勝算はない。
このままでは本当に存在するパスワードを入力する以外ではクエリの結果を「true」にできないからだ。

上記クエリの実行結果を「true」にするには、SQL文を↓のように書き換えて実行させればいい。
  # xxxは任意の文字列
  SELECT user_password FROM user_info WHERE user_password = 'xxx' OR 絶対にtrueになる式 --';

条件式にある「A OR B」という形は、「最低限AかBのどちらかがtrueなら結果もtrue」っていう意味。
だからxxxが間違っていても、後に書いた<絶対にtrueになる式>によって実行結果はtrueになる。

そして、「--」は「それ以降をコメント化(無視)する」という意味。
これをつけないと末尾に残るアポストロフィによって文法エラーになってしまう。


説明が長くなったが、そんなこんなの理由から僕が入力したのは以下の通りだ。
ID :まろ最高
Pass:a' or 1=1 --


結果は・・・

Lv2クリア!



次回はLv3の攻略。

12 件のコメント:

  1. このような、ハッキング技術やコンピューターに関しては全く分からないのでこれから色々勉強させていただきます。

    返信削除
    返信
    1. 私もまだまだ勉強中です。お互いレベルアップしていきましょう!

      削除
  2. 僕は今日初めてこういうことをしています。僕ももっとプログラミングが得意になれるように、頑張ります!

    返信削除
    返信
    1. コメントありがとうございます。忙しくても、少しずつでも新しいことを覚えていけるといいですね。
      自分もOSCP頑張らねば。。

      削除
  3. このような知識を身に着けるにはまず初めにどのようなことをすればいいのでしょうか

    返信削除
    返信
    1. HackmeはWebサイトをハッキングしようというゲームですので、それを攻略するにあたって必要なのはWebセキュリティの知識になります。
      サイバーセキュリティには色んな分野がありますが、その中でWebをターゲットにしたもの、ということですね。

      で、WebセキュリティはWebセキュリティで覚えるべき知識や技術が多々ありますが、その前に「守るべきもの(=Webシステム)」の内側を知っておくことをお勧めします。

      Webシステムの内側では何がどう処理されるかを知っている、または推測できるようになることで、Webセキュリティを効果的に学んでいくことができると思います。

      本文中にある下記の部分、これも
      -----------
      Q.Webサイトのログインフォームを作る際に注意しなければならない攻撃は?
      A.SQLインジェクションです。
      -----------
      ログインフォームがあるWebサイト→会員情報は一般的にデータベースに保存する→データベースを操作するにはSQLを使う→Webページの処理でサニタイジングしていなければ任意のSQLを入力し実行(SQLインジェクション)できてしまう

      という考え方が先にあるわけですね。
      この考え方の中でも、最後こそWebセキュリティの領域ですが、そこに辿り着くまではWebシステムの一般的なセオリーです。

      長くなってしまいましたが、Webセキュリティを学ぶなら、大まかにこんな順番で勉強するのがいいのかなと思います↓

      1.Webプログラミング
      Hackmeと同じ程度の簡単なページでいいので1つ作ってみる。

      2.データベース(SQL)
      DBを作り、tableを作り、データをinsertし、データをselectするという一連の操作を実践してデータベースやSQLの基本を覚える。

      3.Webセキュリティ
      全部を理解しなくてもいいのでOWASP TOP 10の日本語版を読んでみる。
      Webシステムには主にどんな脆弱性があって、それによってどんなリスクがあるか、どう対策すればいいかが書かれている。
      環境構築して1と2までやっていれば3~5割くらいはぼんやり理解できるはず。
      あとはDVWAをやってみるとか、徳丸本を読んでみるとか。

      という感じでいかがでしょうか。
      もし時間と興味とネットに繋がるPCがあれば、徳丸本以外は無料でできますよ!

      削除
  4. 解説がとても分かりやすかった!ありがとう

    返信削除
    返信
    1. お役に立てたならよかったです!

      削除
  5. 初歩的な質問ですみません。回答が xxx' OR 1=1 --とのことですが
    アポストロフィをxxxの片側にだけ記述するのは何故でしょうか?

    返信削除
    返信
    1. 文字列を表すデータは「'」で囲む(=左右に「'」を付ける)必要があるためですね。

      これがない場合、つまり入力値が「xxx or 1=1--」の場合、
      ↓のようなクエリになるため、入力値がそのままパスワード文字列として検索されます。
      SELECT user_password FROM user_info WHERE user_password = 'xxx OR 1=1 --';
      (当然、そんなパスワードは設定されていないので結果は偽=認証NGとなります)

      入力値が「xxx' or 1=1--」の場合、↓のようなクエリになります。
      SELECT user_password FROM user_info WHERE user_password = 'xxx' OR 1=1 --';
      この場合、パスワード文字列は「xxx」、ただし「OR 1=1」によって検索結果は必ず真となり、「--」によって右側の「'」はコメント扱いとなるため文法エラーも発生しないという理屈です。

      つまり、「'」を入力しない場合は単純なパスワード検索となり、
      入力する場合はクエリを改竄することで検索結果を自由に変更できてしまう、ということですね。
      SQLインジェクションを悪用すると、場合によっては、クエリの結果を単に操作できるだけでなく、任意のファイルを生成してWebサーバ上でコマンドを実行したり、パスワードそのものやパスワードをリセットするために必要な情報を盗んだりすることもできます。
      年々対策が進んでいる脆弱性ではありますが、かなりのインパクトがある非常に危険な問題です。。

      SQLの理解を深めるにはデータベースを実際いじってみるのが一番効率がいいと思います!
      「SQLインジェクション 仕組み」とかでWeb検索すればもっとわかりやすい解説記事がたくさんあると思いますので、そちらも参考になさってください。

      削除
  6. 以前8946という似たようなハッキング事例サイトがあってレベルがかなりあっていつか挑戦しようとブクマしていたところ消えてしまい、新たに見つけたhackmeは難易度が高くこちらのおかげで解けました。ありがとうございます。
    手法そのものだけでなく、起こりうる問題とその解決を記してくださっているため勉強になります。

    返信削除
    返信
    1. 8946ありましたね。自分もブックマークしてちょこちょこ解いていたのですが、いつの間にか消えていました。
      運営会社がハッキングされて話題にもなってましたが、その後の対応があまりにも恰好悪かったので印象に残っています。

      「Root me」というサイトが8946の完全上位互換なので、ご興味あればそちらにチャレンジしてみるのもいいかもしれません。

      削除