46
31

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

テキトー実装だとハッカー攻撃の恰好の的になりがちなRubyライブラリopen-uri

Posted at

open-uriってちゃんと実装しないとなにかと危険な香りがしますな、という話。

Ruby 2.4.0 リファレンスマニュアル module OpenURI

例えば外部のAPIを叩く必要があって

require "open-uri"

として使っていたとする。
フォームから受け取ったパラメータを入れてopen(なんやら)とする場合、そのままなんでもopen()の中に入れるとかなり危険。

例えばこれはフォームに入れたURLにしたがって、そのウェブサイトに行ってなんか取ってくる例。

Screen Shot 2017-02-16 at 17.54.32.png

コードで言うとこんな感じ。

require "open-air"

class PagesController < ApplicationController
  def search
    @page = open(search_params[:url])
  end

  private

  def search_params
    params.permit(:url)
  end
end

おそらくこんなセキュリティー開きっぱなしな実装はしないと思うが、これをハックしてみるとこうなる。

Screen Shot 2017-02-16 at 17.54.51.png

Rubyの場合、パイプを渡せばそのまま外部コマンドが実行できる。

| ls

結果がこれ

Screen Shot 2017-02-16 at 17.55.03.png

ちゃんとlsコマンドの結果としてGemfileやらが見えてますな。ハッカー達がlsコマンドの結果を見ただけで立ち去る、なんてお行儀がいい訳ない。コマンドが実行できると分かればアレもこれもやられことは想像に難くない。

そこで対策としてparamsをチェックしましょう、と。でもそれが単に「正規表現とかでhttpを含んでいる場合だけopenを実行」だと突破はカンタン

このように||をつければOk

Screen Shot 2017-02-16 at 17.59.47.png
| cat /etc/passwd || http://son_of_a_bxxxh

A || B の意味はAを実行してエラーが出た場合にだけBを実行しなさい、という意味。言うまでもなくコマンドの意図はhttp....は単なるURL風の見せかけで/etc/passwdを見せなさい、と。

その結果がこれ。

Screen Shot 2017-02-16 at 17.59.56.png

見事に/etc/passwdが見えたりして香ばしい。

別にopen-uriがダメなライブラリと言いたい訳ではない。要はどんなライブラリでもその使い次第ということで十分気をつけましょう、と。

以前にこういうハッカー的なテクニックを使ったパズルを作ろうと考えていて、結果的にできたパズルがこれ。

ほとんどのエンジニアには解けるが、下位10%のダメなエンジニアにだけ解けないパズル?

このパズルにご登録いただいた解答者数がやっと5300を超えたあたりか。。。もっと伸ばす方法ないのかなー。

46
31
2

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
46
31

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?