WebGaot 5 Crypto Basics

暗号文

No.2 Base64 Encoding

符号化は本当の意味での暗号ではないが、暗号機能を中心としたあらゆる規格で多く使われている。特にBase64エンコーディング

Base64エンコーディングは、あらゆる種類のバイトを特定の範囲のバイトに変換するために使われる。この特定範囲とは、ASCIIで読めるバイトのこと*1。こうすることで、秘密鍵などのバイナリデータをより簡単に転送することができる。また、エンコードは可逆的である。エンコードされたバージョンからオリジナルのバージョンを作成することができる。(デコード)

  • 元データを6ビットずつに分割。(6ビットに満たない分は0を追加して6ビットにする)

  • 各6ビットの値を変換表を使って4文字ずつ変換。(4文字に満たない分は = 記号を追加して4文字にする)

その結果、符号化されたバイトのサイズは 4/3に(約33%)増加する。

Hello ==> SGVsbG8=

Basic Authentication : ベーシック認証

Webアプリケーションではベーシック認証が使われることがある。これはBase64エンコーディングを使用する。そのため、サーバに送信されるユーザー名やパスワードを他人に読まれないようにするために、少なくともTLS・HTTPで暗号化する必要がある。(Base64エンコーディングは簡単にデコードできるから)

$echo -n "myuser:mypassword" | base64
bXl1c2VyOm15cGFzc3dvcmQ=

このとき HTTP header は次のようになる

Authorization: Basic bXl1c2VyOm15cGFzc3dvcmQ=

問題. 次のヘッダを傍受したとする。
Authorization: Basic c2hp***************taW4=

このときのユーザーネームとパスワードは?

Base64 デコード」で検索しても良いが、今回は BurpSuite のデコーダーを使う。

f:id:hirose-test:20210216224900j:plain

f:id:hirose-test:20210216225628j:plain

No.3 その他のエンコーディング

HTML エンコーディング

HTML エンコーディングは、フォームデータやリクエストパラメータをサーバに送信する際に多く使用される。URLではスペースは許可されていないので、これは%20に置き換えられる。 UUEncode

Unix-2-Unix

Unix-2-Unix エンコーディングは、メールの添付ファイルを送信するために使用されている。

XOR エンコーディング

パスワードを格納するための最初でシンプルな難読化技術として、エンコーディングが使用されることもある。IBM WebSphere Application Server などでは、XOR エンコーディングの特定の実装を使用して、構成ファイルにパスワードを格納している。IBM では、これらのファイルへのアクセスを保護し、既定の XOR エンコーディングを独自のカスタム暗号化に置き換えることを推奨している。しかし、これらの推奨事項が守られていない場合、このデフォルト設定が脆弱性になる可能性がある。

問題. XORエンコードされたデーターベースパスワード Oz4rPj0+LDovPiwsKDAtOw== を見つけた場合、実際のパスワードは何か。

WebSphere {xor} password decoder and encoder に入れてみる。

f:id:hirose-test:20210217232716j:plain

f:id:hirose-test:20210217232826j:plain

No.4 Plain Hashing

プレーンハッシュ ハッシュ化は暗号の一種であり、主に元のデータが変更されたかどうかを検出するために使用されます。ハッシュは元のデータから生成されます。これは不可逆的な暗号技術に基づいています。元のデータが1バイトでも変更された場合、結果のハッシュも異なるものになります。 そのため、ある意味では安全な技術のように見えます。しかし、パスワードに使用する場合は、決して良い解決策ではありませんし、決してそうではありません。ここでの問題は、辞書からパスワードを生成し、そのパスワードからあらゆる種類のバリエーションを計算することができるということです。各パスワードに対してハッシュ値を計算することができます。これはすべて大規模なデータベースに保存することができます。ですから、パスワードになりそうなハッシュを見つけたときはいつでも、データベースの中のハッシュを調べてパスワードを見つけることができます。 いくつかのハッシュアルゴリズムは、もう使わない方がいいでしょう。MD5SHA-1 これらのハッシュでは、ペイロードを変更しても同じハッシュが得られるようにすることができます。これには多くの計算能力が必要になりますが、それでも実現可能なオプションです。

ソルトハッシュ プレーンパスワードは、明らかにデータベースに保存されるべきではありません。そして、プレーンなハッシュについても同じことが言えます。OWASP Password Storage Cheat Sheet は、パスワードに関連する情報を安全に保存する必要がある場合に、何を使用すべきかを説明しています。 www.DeepL.com/Translator(無料版)で翻訳しました。

問題. 次の各ハッシュ値から導き出せるパスワードは何か。 E10ADC3949BA59ABBE56E057F20F883E
8F0E2F76E22B43E2855189877E7DC1E1E7D98C226C95DB247CD1D547928334A9

ヒント:ハッシュの長さからハッシュ関数の種類を推測する。

E10ADC3949BA59ABBE56E057F20F883E(32文字)→MD5
8F0E2F76E22B43E2855189877E7DC1E1E7D98C226C95DB247CD1D547928334A9(64文字)→sha256

MD5 Online | Free MD5 Decryption, MD5 Hash Decoder
→123456

https://sha256.web-max.ca/
→passw0rd

検索すると他にも多々デコードページはあるが、解析可否はそのサイトのレインボーテーブルに登録されているかどうかによる。

f:id:hirose-test:20210217234849j:plain

No.6 署名

署名とは、あるデータの妥当性を確認するために使用できるハッシュのことである。署名は、それが検証するデータとは別に提供することもできますし、CMSSOAPの場合は同じファイルに含めることもできます。(ファイルの一部がデータを含み、一部が署名を含む場合)。

署名は、整合性が重要な場合に使用されます。これは、AからBに送信されたデータが変更されていないことを保証するためのものです。したがって、Aはデータのハッシュ値を計算し、そのハッシュ値を非対称秘密鍵を使って暗号化することでデータに署名します。次にBは、データのハッシュを計算し、署名を復号化することで、両方のハッシュが同じかどうかを比較することで、データを検証することができます。
RAW署名
生の署名は通常、以下のように計算されます。
データのハッシュを作成する (例:SHA-256 ハッシュ)
非対称秘密鍵を使ってハッシュを暗号化する (RSA 2048ビット鍵など)
(オプションで) base64 エンコーディングを使用して暗号化されたバイナリハッシュをエンコードします。
Bは公開鍵付きの証明書も取得しなければなりません。これは以前にも交換されているかもしれません。つまり、データ、署名、証明書の少なくとも3つのファイルが関係しているということです。
www.DeepL.com/Translator(無料版)で翻訳しました。

問題. ここで簡単な課題です。秘密のRSA鍵が送られてきます。RSA鍵のモジュラスを16進数の文字列として決定し、その鍵を使ってその16進数の署名を計算します。

以下の秘密鍵を持っているとします。

-----BEGIN PRIVATE KEY----- MIIEvAIBADANBgk(中略)Sc3LEI2xfo+x56VutL -----END PRIVATE KEY-----

公開鍵のモジュラスは何ですか?そして、そのモジュラスに基づいて署名を提供してください。

とりあえず何も入力せずに "post the answer" をクリックしてみる。

f:id:hirose-test:20210227124235j:plain

ヒント. opensslを使って、秘密鍵から公開鍵を取得します。どうやら秘密鍵と公開鍵の両方の情報が保存されているようです。

  1. 公開鍵のモジュラスを問われているが、秘密鍵しかないため、まずは秘密鍵から公開鍵を作成する。
秘密鍵をコピペして private-key.pem という鍵ファイルを作成する。(鍵名は適当に)
hoge@fuga:~$ cat private-key.pem
-----BEGIN PRIVATE KEY-----
MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQCIITOeNuzsafFU/4u+KJR
(中略)
BZSe1N4icwGwtpzHg+UWYvXzyCapSCoDDmImbTR/aH5Q7VSpyM/uStK4XxyklDSabZcA==
-----END PRIVATE KEY-----

hoge@fuga:~$ openssl rsa -in private-key.pem -pubout -out public-key.pem
writing RSA key
hoge@fuga:~$ ls
private-key.pem  public-key.pem
hoge@fuga:~$ cat public-key.pem
-----BEGIN PUBLIC KEY-----
MIIBIDANBgkqhkiG9w0BAQEFAAOCAQ0AMIIBCAKCAQEAiCEznjbs7GnxVP+LviiU
(中略)
lQIBEQ==
-----END PUBLIC KEY-----
  1. 次に公開鍵からモジュラスを取得する。
hoge@fuga:~$ openssl rsa -in public-key.pem -pubin -modulus -noout
Modulus=8821339E36ECEC69F154FF8BBE2894758C067805D05CD4225EF26584C5891433331994792EC9D6DE8535981EED2CC68A978
(中略)
6A5DEA9C4530CD8FEBFB0BA0F172A3DF8083E8F9C68C52A80BA92ADC0D43B530769F15298D89B7E37F2C0053C295

表示されたモジュラスを回答欄にコピペする。

f:id:hirose-test:20210227124643j:plain

モジュラスは正解。次は署名欄。
先ほどのモジュラスをコピーして次のコマンドに入力する。

hoge@fuga:~$ echo -n "88C189B0626BD7C4CFEDB594F9E472E1ADD4EDE59468A70ED15C66B6F74FE0A3F9BDAF1601C0EBB7AB1057C6719EB4BB206E9A8EDAA6F3210FB7602F5CFF4E17A2CF5BFBEC9DDF813533F4DB3531DC9801E2C2CC104867E29AB0F7E4C520AAFB0332F54587FBFF28D9E708BB81BF22754E97165ED45710A17F6969EC99983C1BC5488E83C153581BC35FBF4E9BB0C7169604639114DA1D8CD64F8892D9FD890ACECB7A8E3DE341D3EE05568469B380630A71D80BB53D4C0410DB02A17CA7FF1E50CE43E2038D6E797A48044C99E0E528A552FB4B6DD23549B08944EE1E108834BDD2D4B71C1B61D11398B674D8C35A88F611B2EE11FFCBAF71BB7C966CC2823D" | openssl dgst -sign private-key.pem -sha256 -out sign.s
ha256
hoge@fuga:~$ ls
private-key.pem  public-key.pem  sign.sha256

sign.sha256 ができたがまだ答えではない。このままだと暗号化されているので読めない。

fuga@hoge:~$ cat sign.sha256
UFgҼ-Uo"
(中略)
+RM6$nD|jj8ru:eU5Ez
J-f-|-v'7ss<       7Z{uĞ\%bǏi%&'H[5l

Base64エンコーディングを使用して暗号化されたバイナリハッシュをエンコードする必要がある。

hoge@fuga:~$ openssl enc -base64 -in sign.sha256 -out sign.sha256.base64
hoge@fuga:~$ ls
private-key.pem  public-key.pem  sign.sha256  sign.sha256.base64
hoge@fuga:~$ cat sign.sha256.base64
VUZn1NK8LZCwtVVv2ejAItcKpI2k3HjpqpJ+PYcpEe71bRpgT9K1unz7BtLwZKGy
(中略)
jwDsaSUmJ0iBW881+mwTuw==

上記を回答欄にコピペする。 f:id:hirose-test:20210227154942j:plain 正解。

No.8

この演習では、docker コンテナイメージの中に誤って残された秘密を取得する必要があります。この秘密を使って、以下のメッセージを解読することができます。>U2Fsd(中略)D7as=. 実行中のコンテナ (docker exec ...) にログインし、/root にあるパスワードファイルにアクセスすることでメッセージを解読できます。その後、コンテナ内のopensslコマンドを使用します(Windows/Mac/Linux上でのopensslの移植性の問題のため)。 以下のdockerイメージの中に秘密を見つけることができます。

ヒント:dockerコンテナを起動した後、docker exec -ti dockerid /bin/bash を使ってコンテナに入ります。

PS D:\hoge> docker run -d webgoat/assignments:findthesecret
PS D:\hoge> docker exec -ti 8cd3XXX(CONTAINER ID) /bin/bash
webgoat@8cd39XXXXXXX:/$ ls
bin  boot  dev  docker-java-home  etc  home  lib  lib64  media  mnt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var
webgoat@8cd39XXXXXXX:/$ cd /root/
bash: cd: /root/: Permission denied

root 権限がない。

WebGoat之路-1-Introduction & General | riChar

ファイルの名前はまだわかっていません。明らかにroot権限がsu必要ですが、パスワードは直接必要です。したがって、rootパスワードを変更する必要があります。

  1. 最初にdockerのbashを終了し sudo docker container cp [CONTAINER ID]:/etc/shadow ./ で shadowファイルをコピーします。

  2. Linuxパスワードストレージのルールに従って、$id$salt$encrypted 私たちは自分でパスワードを生成することができます。そこで、Pythonでコードを書きました。

    import crypto,random
    passwd=input("Please input your password: ")
    salt="$6$"+"".join(random.sample('1234567890qwertyuiopasdfghjklzxcvbnmQWERTYUIOPASDFGHJKLZXCVBNM',16))
    print(crypt.crypt(str(passwd),salt))
    
    ルート行の最初の2つのコロンの間に出力文字列を書き込み(元の * を置き換えます)、保存します。

  3. sudo docker container cp ./shadow [CONTAINER ID]:/etc/shadow 変更した shadow ファイルを書き込みます。
    もう一度 sudo docker exec -ti [CONTAINER ID] /bin/bash 接続を使用し、su 設定したパスワードを入力すると、root 権限が付与されます。

  4. ls /root default_secret というファイルがあります。docker の bash から抜けます。
    sudo docker container cp [CONTAINER]:/root/default_secret ./ でコピーします。

  5. タイトルの要件に従って入力した後、
    echo "U2Fsd(中略)pD7as=" | openssl enc -aes-256-cbc -d -a -kfile default_secret
    復号化は成功します。
  6. 最終的な答えは Leaving passwords in docker images is not so secure と default_secret です。
PS D:\hoge> docker container cp 8cd3925cd393:/etc/shadow ./     
PS D:\hoge> ls
    ディレクトリ: D:\hoge
Mode                 LastWriteTime         Length Name
----                 -------------         ------ ----
(前略)
-a----        2019/11/21     16:32            530 shadow
(後略)
PS D:\hoge> python.exe .\hoge.py
Traceback (most recent call last):
  File "C:\Users\XXXXX\AppData\Local\Programs\Python\Python38\lib\crypt.py", line 6, in 
    import _crypt
ModuleNotFoundError: No module named '_crypt'

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File ".\hoge.py", line 1, in 
    import crypt,random
  File "C:\Users\XXXXX\AppData\Local\Programs\Python\Python38\lib\crypt.py", line 9, in 
    raise ImportError("The crypt module is not supported on Windows")
ImportError: The crypt module is not supported on Windows

ということで、WSL Ubuntu で。

shinkanaoka@FRGRH:~$ python hoge.py

Command 'python' not found, did you mean:

  command 'python3' from deb python3
  command 'python' from deb python-is-python3

はい。

shinkanaoka@FRGRH:~$ python3 hoge.py
Please input your password: (ここで新しいパスワードを設定する)
$6$6K(中略)Ww1O0.

Windowsに戻って

PS D:\hoge> docker container cp ./shadow 8cd3XXXXXXXX:/etc/shadow
PS D:\hoge> docker exec -ti 8cd3925cd393 /bin/bash
webgoat@8cd3925cd393:/$ su -
Password: (さっきPythonで設定したパスワード)
root@8cd3925cd393:~# ls /root/
default_secret
root@8cd3925cd393:~# cat root/default_secret
ThisIsMySecretPassw0rdF0rY0u
root@8cd3925cd393:~# echo "U2Fsd(中略)pD7as=" | openssl enc -aes-256-cbc -d -a -kfile default_secret
Leaving passwords in docker images is not so secure

答え:

  • default_secret

  • Leaving passwords in docker images is not so securer

f:id:hirose-test:20210227205246j:plain

最後に、dockerをオフにすることを忘れないでください。
sudo docker kill [名称]
スペースを節約するために、ミラーを削除してください。
sudo docker image rm webgoat/assignments:findthesecret --force
この質問は少し感じ始めます。要約すると、最終的な答えが言ったように、dockerにパスワードを残す必要はありません。外部ユーザーがdockerコンテナを操作するために使用できるコマンドは、root権限を持つことと同じです。中に保管されているものはそうではありませんそれは安全でなければなりません。

*1:データを64種類の印字可能な英数字のみを用いて、それ以外の文字を扱うことの出来ない通信環境にてマルチバイト文字やバイナリデータを扱うためのエンコード --WikiPedia

WebGaot 4 CIA Triad

CIA Triad : 情報セキュリティの三特性
Confidentiality, Integrity, Availability 機密性、完全性、可用性

No.5

1. 侵入者はどのようにして機密性のセキュリティ目標を害することができますか?
解決策1:すべてのデータベースを削除する。
解決策2:システムの一般的な設定情報が格納されているデータベースを盗む。
解決策3:名前や電子メールが格納されているデータベースを盗み、ウェブサイトにアップロードする。○
解決策4:侵入者によって機密性が損なわれないようにする。

2.侵入者はどのようにしてセキュリティの目標である完全性を害することができるでしょうか?
解決策1:データベースに保存されている 1 人以上のユーザーの名前と電子メールを変更する。○
解決策2:着信および発信のネットワークトラフィックを盗聴する。
解決策3:データベースへのアクセスを管理するために設置されている認証メカニズムを迂回する。
解決策4:完全性が損なわれるのは、侵入者がデータベースストレージへの物理的なアクセス権を持っている場合に限られる。

3.侵入者はどのようにして可用性というセキュリティ目標に害を与えることができるか。
解決策1:システムソフトウェアのバグを利用して、データベースの認証メカニズムを迂回する。
解決策2:機密データを含む電子メールを他の個人にリダイレクトする。
解決策3:ストレージデバイスの電源を抜くことによってのみ、可用性が損なわれる。
解決策4:サーバーにサービス拒否攻撃を仕掛ける。○

4.CIAのセキュリティ目標のうち、少なくとも1つが危害を受けるとどうなるのでしょうか?
解決策1:システムは、すべての目標が損なわれるまでは安全であると考えられる。一つの目標が危害を加えても、システムのセキュリティには何の影響もない。
解決策2:一つの目標だけが危害を加えられても、システムの安全性は損なわれる。○
解決策3:攻撃者がデータを読み取ったり変更したりしても、少なくとも一部のデータはまだ利用可能であるため、可用性の目標が害された場合にのみ、システムのセキュリティが損なわれる。
解決策4:攻撃者がデータを変更したり、利用できなくしたりしても問題ないが、機密性の高いデータを読み取ることは許容できない。機密性が損なわれた場合にのみ問題がある。

www.DeepL.com/Translator(無料版)で翻訳しました。

f:id:hirose-test:20210216222915j:plain

WebGaot 3 Developer Tools

Google Chrome Developer Tools

No.4 Try It! Using the console

Chromeの開発ツールを開いて javascriptの関数 webgoat.customjs.phoneHome() を実行する。

>webgoat.customjs.phoneHome()
phoneHome invoked
<-undefined
phone home said {"lessonCompleted":true,"feedback":"Congratulations. You have successfully completed the assignment.","output":"phoneHome Response is -1987324058","assignment":"DOMCrossSiteScripting","attemptWasMade":true}

phoneHome Response is の所に乱数が表示されるのでフォームにコピペしてSubmit。

f:id:hirose-test:20210216220353j:plain

No.6 Try It! Working with the Network tab

GO! ボタンをクリックするとHTTPリクエストが生成される。特定のHTTPリクエストを見つける。リクエストにはnetworkNumというフィールドが含まれている。その番号が答え。

f:id:hirose-test:20210216221447j:plain

f:id:hirose-test:20210216221147j:plain

WebGaot 2 HTTP Proxies

Owasp ZAP を使用してProxyについて学ぶ。

Lesson No.6

ZAP の Firefoxアイコンをクリックすると ZAPとブラウザを連携して使うことができる。 f:id:hirose-test:20210215211940j:plain

ZAP HUDという画面上にZAPのボタンを表示させることができる機能がある。 f:id:hirose-test:20210215211838j:plain

Configure a breakpoint filter

ZAP でリクエストを受ける前に、WebGoat フレームワークから内部リクエストを除外する必要がある。そうしないと ZAP は WebGoat の内部作業にのみ必要なすべてのリクエストを停止する。 基本的には、リクエストヘッダーにPOSTが含まれている場合にリクエストを阻止するブレークポイントが設定されている。開発ツールでネットワークタブをみると、.mvcメッセージが数秒に1回、ポーリングされていて邪魔なので除外する。

ブレークポイントを以下のように設定。 f:id:hirose-test:20210215212956j:plain

チェックボックスブレークポイントをON/OFFできる。グリーン/レッドボタンはもう使わないように。 f:id:hirose-test:20210215213205j:plain

Intercept and modify a request

リクエスト傍受後

  • メソッドをGETに変更

  • ヘッダ 'x-request-intercepted:true' を追加。

  • リクエスト本文を削除し、代わりにクエリ文字列パラメータとして 'changeMe' を送信し、値を 'Requests are tampered easily' に設定(シングルクォーテーションは抜きで)。

f:id:hirose-test:20210215214308j:plain

f:id:hirose-test:20210215214634j:plain

f:id:hirose-test:20210215214718j:plain

"Requests are tampered easily"

WebGaot 1 HTTP Basics

ログイン画面

f:id:hirose-test:20210211145730j:plain

Register new user をクリックして新規登録

f:id:hirose-test:20210211145849j:plain

このプログラムを実行している間は、あなたのマシンは攻撃に対して非常に脆弱になります。このプログラムを使用している間は、インターネットから切断する必要があります。WebGoatのデフォルト設定は、攻撃を最小限に抑えるためにlocalhostにバインドします。

このプログラムは教育目的のみを目的としています。許可なくこれらの技術を試みると、捕まる可能性が非常に高くなります。無許可のハッキングに従事しているのを発見された場合、ほとんどの企業はあなたを解雇します。セキュリティ調査をしていたと主張しても、それはすべてのハッカーが最初に主張することなので、うまくいきません。

LESSON No.3

f:id:hirose-test:20210211195600j:plain

問題. このレッスンで使われているHTTPコマンドは POSTですか、GETですか。またマジックナンバーは?

f:id:hirose-test:20210211195941j:plain

ヒント:パラメータなどを見てみてください。

マジックナンバーとは?とりあえず適当に入力してパラメータを見てみる。
入力後、GO! をクリックしたとき「Attack2」というリクエストが飛んでいることが分かる。
内容を確認してみると、Method は POST で FormData に magic_num:27 とある。これが答え。

f:id:hirose-test:20210211195812j:plain

/* -----codeの行番号----- */