僕と技術とセキュリティ

セキュリティエンジニアの備忘録

sshの認証鍵のパーミッションを適当にしたら怒られた話

掲題の通り

Vagrantのprivate_keyを使って外部からssh接続しようとしたらパーミッションが違うよと怒られた。

$ssh -i private_key -l vagrant 192.168.1.8
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
@         WARNING: UNPROTECTED PRIVATE KEY FILE!          @
@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@
Permissions 0755 for 'private_key' are too open.
It is required that your private key files are NOT accessible by others.
This private key will be ignored.
Load key "private_key": bad permissions

よくみないであーハイハイpermissionね、と考えてchmod 755 private_keyとか雑なことしていたら通らず。

よくよくエラーメッセージを見てみると適切なpermissionにしていないせいで怒られていることに気がつく。
適切なpermissionを設定してやると無事接続できた。
このあたりはawsのEC2に接続する際にもよく怒られていたので、permissionは777みたいなガバセキュリティな物で運用している人はもういないのだろうな...

下記のコマンドを実行すれば動く。(private_keyはご自身のファイルに置き換えて)
$chmod 400 private_key
$ssh -i private_key -l vagrant 192.168.1.8

$chmod 400 private_key
$ssh -i private_key -l vagrant 192.168.1.8
Welcome to Ubuntu 16.04.6 LTS (GNU/Linux 4.4.0-146-generic x86_64)

 * Documentation:  https://help.ubuntu.com
 * Management:     https://landscape.canonical.com
 * Support:        https://ubuntu.com/advantage

0 packages can be updated.
0 updates are security updates.

New release '18.04.2 LTS' available.
Run 'do-release-upgrade' to upgrade to it.


*** System restart required ***
Last login: Tue Aug 13 14:04:48 2019 from 10.0.2.2

mac-cli
cli

いつもローカルのVagrant適当に設定していたはずなのにいつからこうなったのだろう...?

Slackのリンクプレビューは

掲題の通り、自分のメモ書きとして残す。

やったこと

firebaseに対して以下の様なアプリを立てた

const functions = require('firebase-functions');
const express = require('express');

const app = express();
app.get('/redirect', (req, res) => {
  res.location('https://requestbin.fullcontact.com/******61?from=redirect')
  res.send(301, null);
})
app.get('/href', (req, res) => {
  res.setHeader('Content-type', 'text/html')
  res.write(
    `<h1>Location.href</h1>
     <script>location.href="https://requestbin.fullcontact.com/******61?from=href"</script>`
  )
  res.send(200);
})

exports.app = functions.https.onRequest(app);
  • /redirectにアクセスがあれば Location:https://requestbin.fullcontact.com/******61?from=redirectを付与してリダイレクト

  • /hrefにアクセスがあれば location.href="https://requestbin.fullcontact.com/******61?from=href"でリダイレクト

Slackにリンクを貼り付けてリンクプレビューを取得させた。

結果

Location:ヘッダの方はリダイレクトした。

f:id:halkichi-web:20190709231429p:plain
redirect

令和になった今、Content-TypeヘッダのCharset付与によるクロスサイトスクリプティングについて考えてみる

経緯

なぜ今このContent-TypeヘッダのCharsetでのXSSに言及しているかというと IPAで公開されている安全なウェブサイトの作り方による資料でこの項目が今だにフォローされているからだ。

この項目が令和となった現在もフォローが必要なのか検証していきたい。


TL;DR

もう指摘基準から除外しても良いのではなかろうか
被害の恐れがある場合はIE11以前のブラウザでかつ、限定的なので。


Content-TypeヘッダのXSS??

こちらはどういうことかというかと、
ブラウザの文字コードの解釈によって実行されるクロスサイトスクリプティングの対策についての項目なのである。

通常、何も対策をしていないWebアプリケーションであれば
ユーザの入力値をサニタイズせずに画面に出力してしまう場合にXSS(クロスサイトスクリプティング)の危険性がある。

ようこそ、TESTさん!

ようこそ、<script>alert(1)</script>さん!

しかし、UTF-7 という文字コードを利用した場合にもXSSの可能性が存在した。(はてなのリンクからも情報が拾えるぞ!)

ようこそ、+ADw-script+AD4-alert(1)+ADw-/script+AD4-さん!


この+ADwから始まる文字列はUTF-7では <script>alert(1)</script>となる。
このHTMLをブラウザがUTF-7と解釈した場合にJSが実行される


なので、ブラウザによりUTF-7と解釈されない様に、 レスポンスのContent-TypeヘッダのCharset付与をしてXSSを防止しましょうということなのである。 今回はこのUTF-7で実行可能なXSS脆弱性について考えていきたい。



そもそもの経緯はIEContent-Type無視にもあったと思う。
今でこそIEは提供元のMicrosoftでさえ、使用を推奨していないということなのでもうこの手法も大分レガシーになったのではないか。

どのパターンでXSS脆弱性が存在するのか

セキュリティチェックリストでは以下の様に言及されている。

全てのウェブアプリケーションに共通の対策:
(根本的対策として)
HTTPレスポンスヘッダのContent-Typeフィールドに文字コード(charset)の指定を行う。

では文字コード(charset)の指定を行わなかった場合にどうなるのか
実際に試してみた。

  • 想定される環境
    UTF-8やShift-JIS等で動作しているサイトでHTMLでcharsetを指定し忘れて
    レスポンスヘッダのContent-Typeフィールドにcharsetを付与していない場合の挙動を確認する。

    HTML
<html>
  <body>
  +ADw-script+AD4-alert(1)+ADw-/script+AD4-
  </body>
</html>


レスポンスヘッダ(共通)

HTTP/1.1 200 OK
Content-type: text/html

脆弱性が存在しない場合は、以下の様に記号がそのまま画面に表示されるだけになる。
(以下はChrome)

Chrome_no_xss
Chromeで検証した画面

以下は、検証したブラウザとその結果である。

検証HTMLをそのまま読み込んだ場合

ブラウザ 結果
IE8 問題なし
IE11 問題なし
Edge 問題なし
Chrome 問題なし
Safari 問題なし
Firefox 問題なし


IE8はContent-Type無視問題も存在するのでそのままXSSを実行してくれると思っていた。が実際にはXSSは対策されていた。

IE8_no_xss
IE8で検証した画面

iframeで読み込んだ場合

iframeを利用して読み込んだ場合、charsetの指定がされていない時は親HTMLの文字コードが利用されるため、
このHTMLを利用して同じページを読み込んでみる。

<html>
  <head>
    <meta charset="UTF-7">
  </head>
  <body>
    <iframe src="http://example.com/charset-xss.html"></iframe>
  </body>
</html>


iframeの親HTMLのレスポンスヘッダ

HTTP/1.1 200 OK
Content-type: text/html; utf-7

以下はiframeから実行した場合の画面

iframe_otherOrigin
iframeが外部ドメインの場合

iframe_sameOrigin
iframeが同一ドメインの場合

iframeで読み込んだ場合の結果


ブラウザ 結果
IE8 ※親HTMLとドメインが同じならXSSが実行できる
IE11 ※親HTMLとドメインが同じならXSSが実行できる
Edge 問題なし
Chrome 問題なし
Safari 問題なし
Firefox 問題なし

※親HTMLはiframeの呼び出し元となったHTML
という結果であった。

結論

検証時に用意した環境ではIEのみiframeで読み込んだHTMLとXSS脆弱性のあるページが同じドメインであれば実行可能であった。
このiframeで読み込んだHTMLしか利用できないのであれば、悪意のある攻撃者は別ドメインしか用意することができないため
現実的にはCharsetが付与されていないことを利用したクロスサイトスクリプティングは攻撃できないということになる。
(同じドメイン内にcharsetが付いていないサイトとiframeを自由に指定できるというサイトは別)

所感

Edgeは既に問題の対策がされており、
IE11でさえiframeの対策がされているのであればこのContent-TypeヘッダのCharset付与のクロスサイトスクリプティング脆弱性についての項目は
現場でセキュリティ担当者が複数のサービスに対してチェックする上で負担になる代物になっているのであれば
個人的にはフォローを外しても良い様な気がする。

令和CTF Writeup

自分の地域ではネットワーク障害があったため2時間だけ開催されたが、1問だけ解くことができました。
力技のWriteupが多かったので解説を自分も書くことに。

bREInWAck (Misc)

Brainfuck問題
以下は問題とヒント

元号が変わる。記号も変わる。
参考: https://ja.wikipedia.org/wiki/Brainfuck

令和和和和和和和和和和和和和和和和「令和
和和和和令和和和和令和和和和和和和令和和
和和和和令和和平平平平平成」令和和和。令
和和和和和。成成。。平成成成成。成。令令
和和和和和和和和和和和。令和和。平平平和
和和和。令和和。和和和和。令令和和和和和
和和和和和和和。平平平和和和和和和和和和
和和和和。成成成成成成成成。令成成成成成
成成成。令令。成成成成成。成成成成成成。
令和。平平和和。令令令和和和和和和和和和
和。

Wikiよりbrainfuck問題であることがわかる。
以下のサイト二つが特に参考になった。

http://www.kmonos.net/alang/etc/brainfuck.php
https://fatiherikli.github.io/brainfuck-visualizer/

Brainfuckについて

プログラムの実行中に一つの配列を扱い、数値を格納できる。
また、その配列上を移動できるポインタを持つ。

配列のイメージ

数値を格納できる
[72, 101, 108, 108, 111]

また、命令は8つしかない

命令 意味(C言語での意味)
> ++ptr;
< --ptr;
+ ++(*ptr);
- --(*ptr);
. putchar(*ptr);
, *ptr = getchar();
[ while(*ptr) {
] }

使い方
「H」を画面に出力するのであれば上記の配列の1番目の要素にポインタを合わせて「.」を使う。
出力はASCⅡコードで考えれば良い。

命令  //C言語の対応
. //putchar(*ptr);...①
> //++ptr;        ...②
. //putchar(*ptr);...③
[72, 101, 108, 108, 111]
 ^
>H  //配列の1番目の要素72を出力...①
[72, 101, 108, 108, 111]
      ^  //配列の2番目の要素に移動...②
>H  
[72, 101, 108, 108, 111]
      ^ 
>He  //配列の2番目の要素101を出力...③

本命のWriteup

与えられた問題文より令和平成「」。7文字><+-.,[]に置き換えれば実行できそうなことがわかる。

パッと見た感じ
配列の要素をインクリメントする手段が1つしかないため
一番出現頻度の高い+に置き換わりそう。
また、[]で配列の要素をインクリメントしながら文字コードを調整するので[の直前の文字は+で間違いなさそう
和 -> +

次に、文中にそれぞれ一箇所しか出現しない「」はwhileを意味する[]に置き換えることができそう。(FlagのSECCON{~~}より出現頻度の少ない文字が+.に置き換わることはない)

「 -> [
」 -> ]

続いてここインタプリタを実行してみてwhileのループを行う配列の要素は[の直前の値を参照し、]がくると参照した要素をデクリメントして0になった場合に]の次の命令を実行することがわかったので
]の後の要素には-.が使われないことがわかる。
ポインタの概念的には配列の左から始まり、><で移動することからも以下のことが推測できた。

令 -> >

そして、<の出現頻度は>より多くなることはないため、
平 -> <
問題分の末尾にputchar(*ptr);の意味をもつ.が来ていることから
。 -> .

残った-,に置き換わると考えられるが、
ここまでの推察から残りは2パターンしか考えられないので以下の様に置換してみて、インタプリタに実行させると、一発目でFlagにたどり着けた。

この問題はかなり頭の体操になった。
他にも楽しそうな問題が多かったが(特にWeb!!)、時間的な都合がなかったため断念...

OWASP CheatSheetを参考にやられアプリ作ってみた

今頃の更新ですが、先日OWASP Connect#2に参加して登壇してきました。
その際に作った資料と環境のまとめです。

OWASP Connectとは

>OWASP Connectは、OWASPという名前は聞いたことあるけれどもどのようなものか全くわからない、どのように活用すべきかわからないといった方々を対象にしたOWASPとの接点がこれまであまりなかった方々向けの勉強会です。
(Connpassの紹介欄より)

owaspprteam.connpass.com

登壇した内容

掲題の通りやられアプリを作りました。
なお、スライドの中でやられアプリ(サイト)となっているのは、セキュリティ界隈の方は皆さんやられ'アプリ'という呼称を使っていたからです。なお、私は今まは今までやられサイトと呼んでいたので、自分のようなマイノリティにも配慮し()を付けています。笑

やられアプリについて


今回作った環境です。
こちらについての紹介はまた別の記事で詳しく取り上げようと思います。
https://github.com/halkichi0308/rails_broken_app

こちら、ソースを編集して脆弱性の修正も試せるようようになっているのですが、一度も失敗した事のないデモが動かず…魅力をお伝えしきることができなかったです…。
よく、新サービスの発表とかで登壇された際にデモされている方がいますが、あれも様々な要因で動かなかったりするのを見ます。(e,g [TSURUGI Linux])
スピーカー - AVTOKYO JP
この事から今回私が得た教訓は、「デモは動かない。」

個人的に面白かった内容

先にお断りしておくと全部興味深い内容でした。ただ話す前の緊張とデモが動かなかったがっかり感でメモを残す事が出来なかった内容がちらほら…。

関西発信!繋ぐ・学ぶ・育てる セキュリティの輪

オワスプカンサイからいらした方。
こちらは内容に興味を持ったというよりは、登壇者の方に衝撃を受けた。エンジニアではなく裁判官の方でまず導入のインパクトが凄かった。
そして喋りが面白く、登壇レベルの違いを感じた内容でした。登壇時の参考になる方がいて嬉しい反面、1発目でこのレベルの発表されたら私の後半のお通夜LTは皆さん聞いてくれるだろうか…😇という焦りも。

OWASP Dependency checkとvulsで可視化

@hogehugaさん

これは知らなかった。どうも使っているライブラリなんかの脆弱性を検出してくれるみたい。普通に脆弱性スキャンツールとして利用できるそう。
これとGCPとかののスキャンツール戦わせてみても面白そう。
https://www.owasp.org/index.php/OWASP_Dependency_Check

【LT】OWASP Snakes and Laddersやってみたよ

@芝雑種さん

この方Twitterでよく見かけて気になっていた。どうも僕と同じフリーランスでセキュリティに携わっているそう。どの分野だろう…?
会場の時間の都合で少ししか発表されていなかったけどOWASPの遊べる脆弱性ボードゲームみたいなやつをやってみたという発表をされていた。僕も人集めてやってみたいぜ。

所感

規模が大きい勉強会で登壇すると勉強になる事が多い。人の話し方、資料の作り方とか。
そしてアウトプットの影響力が凄い、Twitterのフォロワーさんが前日比120%↑ とある診断員さんにフォローされたのも٩( 'ω' )و
月イチ登壇生活始めてから今のところ半年ちょいきたけど、人数は多い方が良いと感じた。やはりフィードバックが濃い。また参加してどんどん発信しよう。

脆弱性診断ええんやでを聴講してきた その2

今回のテーマ「CSRF完全に理解した」

https://security-testing.doorkeeper.jp/events/85711

なんともタイトル詐欺っぽい笑
CSRF、、、これ診断員でも攻撃ができるできないでよく話に上がるんですよねぇ。
結局ここに 書いてある事が全てだったりそうでなかったりするのだけれど。

普段説明する相手にしっかり理解してもらうための伝え方を学ぶために参加!<( 'ω')/

CSRFとは

被害者ユーザのブラウザから自動で更新処理をさせるような攻撃。被害者ユーザのアカウントで勝手に商品を購入されてしまう、など。

  1. 攻撃者はCSRF攻撃用罠サイトを用意
  2. 適当なところに罠サイトのURLを貼る
  3. 攻撃対象サイトに利用者がログイン
  4. 別タブで罠サイトにうっかりアクセス
  5. 罠サイトのフォームが送信されてパスワードが変更させられる。。。

(↑スライドまま)
罠サイトを踏んだユーザのアカウントで処理がされてしまう理由としては、被害者側のブラウザから送信されるCookieを更新処理のあるページに送信している。Cookieは接続先のドメインを見てブラウザが勝手に送信するので自動で被害者側のブラウザのセッションとして利用されているCookieが送信され、正規のユーザからのリクエストを受け取ったとして、サーバが処理してしまう。
ということはログイン処理があるようなアプリケーションに限られる。(ユーザの道程ができないため)

そしてCSRFの流れの説明はホワイトボードをふんだんに使う!どうやってあのややこしい遷移を説明されるのかと思えば...!

対策が必要な処理

  • パスワード変更
  • 購入、決済
  • その他更新が走る処理。

対策

  1. TOKENを使う
    根本的対策として、そのページにアクセスをした際にのみ発行されるTOKENを付与するというやり方がある。
    更新が走る処理には正しいTOKENを持っているかどうかをチェックし、正しい値でなければ処理を行わない。
  2. パスワードを再入力させる
    本人しか知り得ない情報を入力させることは、攻撃者が罠サイトに埋め込めない値を使っているため、罠サイトを作ることができない。
  3. Rereferチェック
    罠サイト=正規のサイトからのRefererではないため、ここが正しいかチェックすることで罠サイトからのリクエストを防ぐ事ができる。

(でも実際はRefererによる対策で防げていた対象はあまり見ない...よく抜ける。) 個人的には独自ヘッダ付与するのが結構強い対策だったりと思う。

Docker環境で行う脆弱性診断(LT枠)

dh_meganeさん
Sier6年目だそう。
Docker環境を使って脆弱性診断を試した結果を発表されていた! localhostの環境に対してZAPを使ったリクエストのを拾い方や簡単なXSSを確認してみたよといった事も。
セキュリティとかいう分野外のことを始めたばかりなのに色々実践してみていてえらいです...!

スライドの以下の部分に共感...!

「Dockerイメージを配布して診断を実施してもらうのもあり?」

ありあり! 全然あり!

むしろコードを我々診断員が見ても良いなら断然Dockerイメージで欲しい。 手元で自由にできる環境の方が制限なく文字列を試せるから脆弱性も見つかりやすいしこういう方が増えてくれれば予定した診断日に突然動かないとかいう案件も一気に解決する予感。

なんと私のセミナーに参加された事があり…終わった後の懇親会で向こうから声をかけて頂いた。話しかけられるまですっかり、忘れていた…申し訳ありませんです🙇人の顔覚えるの苦手なの、どうにかならないかな…。

所感

やはり皆さんCSRFの理解には苦戦されている様子。 そして松本さんは今回もOWASP ZAPを使用して説明をされていた。そして今回も親切にOWASP ZAPのセットアップもレクチャーされていた。
QWASP ZAPの機能たまにしか使わない物もあるから助かります...!

DockerでRuby on Railsを使う話

掲題の通り。

まず目的としてはセミナーの受講者に配布&実行してもらう環境でRails使いたかった。

なんか探しても良い感じの環境がなかったから作った
github.com

使い方
git cloneしてdocker-compose.ymlがあるディレクトリで

docker-compose up -d

そのあとブラウザで以下のディレクトリにアクセス

localhost:3000

Railsが使えるようになる。
docker-compose内でvolumesを指定しているのでローカルを編集すればコンテナ内にも変更が反映される


もう少し説明
アプリケーションのルートディレクトリは.envに記載。
アプリケーションの名前もここから引っ張ってくるので
.envを変更してdocker-compose up しなおせば任意のプロジェクトで始められる。

肝心のDBとの接続は未だ未着手
mysqlと接続出来るように変更。起動時に勝手に接続される。従来通りSQLiteも利用可能


参考にさせていただいた所
RailsアプリをDockerで開発するための手順 - Qiita