盗み聞きしてみた(コンテナ上のnginxプロセスと、ホスト間の通信パケットをtcpdumpでキャプチャしてみた〜CoreOS toolboxを使ってみる〜)
パケットキャプチャとは
サーバさんたちがどんなおはなしをしているのか、
ぬすみぎきすることだよ(白目)
いきさつ
ホスト間とコンテナ上のnginxがどういう通信をしているのか気になった。
普通のサーバへの通信と変わらないのかな。
こういうときは実験だ。
盗み聞きまでの手順
nginxコンテナを起動
$ docker pull nginx:latest $ docker run --name nginx_test -d -p 8080:80 nginx:latest
CoreOSにtcpdumpを入れる
CoreOS toolboxを使用すると、tcpdumpが使えるみたい。
盗み聞きする
Docker上で走っているコンテナとホスト間は、
docker0という仮想ブリッジでつながっている。
(ホスト上でifconfigをするとdocker0があることがわかるよ)
なのでdocker0を盗みぎきするNICに設定。
$ tcpdump -i docker0
結果
14:06:21.082183 IP 172.17.8.1.55248 > 172.18.0.6.http: Flags [S], seq 584948487, win 65535, options [mss 1460,nop,wscale 5,nop,nop,TS val 1315360133 ecr 0,sackOK,eol], length 0 14:06:21.082237 IP 172.18.0.6.http > 172.17.8.1.55248: Flags [S.], seq 636172623, ack 584948488, win 28960, options [mss 1460,sackOK,TS val 3302158741 ecr 1315360133,nop,wscale 7], length 0 14:06:21.083531 IP 172.17.8.1.55248 > 172.18.0.6.http: Flags [.], ack 1, win 4117, options [nop,nop,TS val 1315360133 ecr 3302158741], length 0 14:06:21.083662 IP 172.17.8.1.55248 > 172.18.0.6.http: Flags [P.], seq 1:587, ack 1, win 4117, options [nop,nop,TS val 1315360134 ecr 3302158741], length 586: HTTP: GET / HTTP/1.1 14:06:21.083677 IP 172.18.0.6.http > 172.17.8.1.55248: Flags [.], ack 587, win 236, options [nop,nop,TS val 3302158743 ecr 1315360134], length 0 14:06:21.083835 IP 172.18.0.6.http > 172.17.8.1.55248: Flags [P.], seq 1:181, ack 587, win 236, options [nop,nop,TS val 3302158743 ecr 1315360134], length 180: HTTP: HTTP/1.1 304 Not Modified 14:06:21.084186 IP 172.17.8.1.55248 > 172.18.0.6.http: Flags [.], ack 181, win 4112, options [nop,nop,TS val 1315360134 ecr 3302158743], length 0
ちょっと見てみる。
パケット解析
3 way hand shake
サーバ同士でお話するときはいきなり話しかけない。
「ちょっとお話しませんか?」
「いいですよ。こっちもちょっと話していいですか?」
「いいですよ」
という紳士的なやり取りをして、はじめてお話が始まる。
それを
3 way hand shake
という。
↓ その痕跡がこれ
(1)IP 172.17.8.1.55248 > 172.18.0.6.http: Flags [S] (2)IP 172.18.0.6.http > 172.17.8.1.55248: Flags [S.], ack (3)IP 172.17.8.1.55248 > 172.18.0.6.http: Flags [.], ack
ここで大事なのはFlags[S]とack。
(1)接続元が接続先に対して「ちょっとお話しませんか?」と聞いている
Flags [S]は、
SYN(コネクション確立要求)の先頭文字。
相手に対して、
「ちょっとお話しませんか?」と聞いてる感じ。
(2)接続先が接続元へ「いいですよ。私も話していいですか?」と聞いている
ack が「いいですよ」
S が「私も話していいですか?」
(3)接続元が接続先へ「いいですよ」いってる。
ack が「いいですよ」
この3つの過程を経て、ようやく通信ができるようになる。
GETリクエスト
IP 172.17.8.1.55248 > 172.18.0.6.http: (省略) HTTP: GET / HTTP/1.1
/ ディレクトリへアクセス。
確認応答
IP 172.18.0.6.http > 172.17.8.1.55248: Flags [.], ack 587
ここは勉強不足で、どこらへんが確認応答なのかわかっていない…
レスポンス
172.18.0.6.http > 172.17.8.1.55248: (省略) HTTP: HTTP/1.1 304 Not Modified
何度か通信していたので、取得したコンテンツが更新されていないことが確認できた。
まとめ
コンテナ - ホスト間の通信は、
普通のhttp通信と同じようにみえる。
違うのは、docker0という仮想ブリッジを通した通信だ、ということくらいかな。
CoreOS toolboxに入れない〜Failed to allocate scope: Unit core-fedora-latest.scope already exists.〜
CoreOS toolbox使ってたらこんなエラーがでた
CoreOSでtoolboxコンテナを使い、
Ctrl-wで無理やりコンテナを抜けた。
そしていつものようにtoolboxを起動したら、
$ /usr/bin/toolbox
らこんなエラーがでた。
Failed to allocate scope: Unit core-fedora-latest.scope already exists.
困ったぞ。
stack overflowの記事
Fedra25だと起こる問題みたい。
対処
dockerホスト上で、以下のコマンド実行。
$ echo "TOOLBOX_DOCKER_TAG=24" >>$HOME/.toolboxrc
その上でもいちど
$ /usr/bin/toolbox
いつものtoolboxコンテナに入れた。
Dockerでたてたコンテナにtelnet-serverを入れて、telnetでコンテナ間通信ができるようにしてみた
いきさつ
networkやセキュリティ、telnetデーモンを叩き起こすxintedの勉強がてらやってみた。
手順
0. 準備
0-1. telnet-server用のコンテナを走らせる
$ docker pull centos:centos7 $ docker run --privileged -d --name centos_test centos:centos7 /sbin/init
なお、telnet-serverコンテナでは、
後程systemdを用いてサービスを走らせるので、
--privilegedと/sbin/initが必要になってくる。
0-2 telnet-client用のコンテナを走らせる
$ docker run -d --name telnet-client centos:centos7
1. telnet-serverコンテナの設定
1-1. telnet-serverのinstall
$ docker exec -it telnet-server /bin/bash # yum -y install telnet-server
1-2. リモートホストからのアクセス制御の設定をする
他のサーバからのアクセスを制御します。
すべてのhost/すべてのサービスからのアクセスを拒否します。
# echo 'ALL: ALL' >> /etc/hosts.deny
特定のサービス/特定のホストからのアクセスを許可します。
# echo 'in.telnetd: 172.18.0.5' >> /etc/hosts.allow
telnetデーモンに対して、172.18.0.5からアクセスがあった場合は許可します。
なお、172.18.0.5はtelnet-clientコンテナのipアドレス。
1-3. xinetdの設定
# vi /etc/xinetd.d/telnet
以下を追記します。
service telnet { flags = REUSE socket_type = stream wait = no user = root server = /usr/sbin/in.telnetd log_on_failure += USERID disable = no }
2. telnet-serverの起動
# systemctl status telnet.socket
3. telnet接続用のuserを作成する
# useradd telnet-user # passwd telnet-user Changing password for user telnet-user. New password: Retype new password:
4. telnet-clinentコンテナの設定
4-1. telnet-clinentのinstallをする
$ docker exec -it telnet-client /bin/bash # yum install -y telnet
4-2. 接続
いちおう、サーバ側のポートが空いていることを確認してみる。
$ nmap -sV -PE -p 23 172.18.0.4 Starting Nmap 6.40 ( http://nmap.org ) at 2018-01-09 16:00 UTC Nmap scan report for 172.18.0.4 Host is up (0.000039s latency). PORT STATE SERVICE VERSION 23/tcp open telnet Linux telnetd
あいてた。
$ telnet 172.18.0.4 23 Trying 172.18.0.4... Connected to 172.18.0.4. Escape character is '^]'. Kernel 4.14.11-coreos on an x86_64 f71734bf26ca login: telnet-user Password: Last login: Tue Jan 9 16:07:51 from 172.18.0.5
入れた!
感想
コンテナからコンテナにtelnetログインするだけでそれなりの作業量となる。
色々勉強になった。
参考
apt-get updateは何を行っているのか調べてみた〜パッケージインデックスファイルとは何か〜
結論
$ apt-get update
は、パッケージリストの更新を行う。
具体的に言うと、
/etc/apt/sources.list
にかかれているURLから、
パッケージインデックスファイルを引っ張ってきて、
$ cd /var/lib/apt/lists
に格納している。
いきさつ
1. Dockerで構築したubuntuにてfileコマンドが使えない
$ file bash: file: command not found
2. fileコマンドをinstallしてみる
$ apt-get install file Reading package lists... Done Building dependency tree Reading state information... Done E: Unable to locate package file
まじか。。 installできない。
3. fileコマンドがないことをdpkgコマンドで確かめる
$ dpkg -K file dpkg-query: package 'file' is not installed
やっぱりないね。
なんでや
apt-getについて調べてみると、
以下の記事が見つかった。
つまり、
apt-get install package_name
を実行した際には、
$ cd /var/lib/apt/lists
にある
パッケージインデックスファイルを参照して、
その中に含まれるパッケージがinstallされる。
対処
1. パッケージインデックスファイルがあるかどうか確認
$ cd /var/lib/apt/lists $ ls
パッケージインデックスファイルが、空。
参照されるインデックスファイルがないので、
このままではinstallできない。
2. パッケージインデックスファイルのダウンロード
つまり、パッケージリストの更新を行う。
$ apt-get update
/etc/apt/sources.list
に指定されているリストにもとづいて、
パッケージインデックスファイルがダウンロードされる。
3. パッケージインデックスファイルを確認
$ ls archive.ubuntu.com_ubuntu_dists_xenial-backports_InRelease archive.ubuntu.com_ubuntu_dists_xenial-backports_main_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial-backports_universe_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial-updates_InRelease archive.ubuntu.com_ubuntu_dists_xenial-updates_main_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial-updates_multiverse_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial-updates_restricted_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial-updates_universe_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial-updates_universe_source_Sources.lz4 archive.ubuntu.com_ubuntu_dists_xenial_InRelease archive.ubuntu.com_ubuntu_dists_xenial_main_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial_multiverse_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial_restricted_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial_universe_binary-amd64_Packages.lz4 archive.ubuntu.com_ubuntu_dists_xenial_universe_source_Sources.lz4 lock partial security.ubuntu.com_ubuntu_dists_xenial-security_InRelease security.ubuntu.com_ubuntu_dists_xenial-security_main_binary-amd64_Packages.lz4 security.ubuntu.com_ubuntu_dists_xenial-security_multiverse_binary-amd64_Packages.lz4 security.ubuntu.com_ubuntu_dists_xenial-security_restricted_binary-amd64_Packages.lz4 security.ubuntu.com_ubuntu_dists_xenial-security_universe_binary-amd64_Packages.lz4 security.ubuntu.com_ubuntu_dists_xenial-security_universe_source_Sources.lz4
たしかにパッケージインデックスファイルがダウンロードされた。
4. fileコマンドをinstall
$ apt-get install file
今度はinstallできた。
5. fileコマンドを実行
$ file Usage: file [-bcEhikLlNnprsvzZ0] [--apple] [--extension] [--mime-encoding] [--mime-type] [-e testname] [-F separator] [-f namefile] [-m magicfiles] file ... file -C [-m magicfiles] file [--help]
fileコマンドが入った。
まとめ
installしたばかりのubuntuには、
パッケージをinstallする際に参照するインデックスファイルが存在しない。
なので、パッケージをinstallすることができない。
よって、
はじめにインデックスファイルをダウンロード(更新)する必要がある。
そのために用いられるのが
$ apt-get update
であり、
その結果
$ cd /var/lib/apt/lists
にあるパッケージインデックスファイルが更新される。
間違えてリモートにpushしたcommitを元に戻す
手順
1
$ git log
して、取り消したいコミットのハッシュをコピー
2
$ git revert ハッシュ
して、
コミットを取り消すコミットをする(ややこしい)
3
$ git push origin master
remoteにpush
まとめ
自分のブランチならいいけど、
他の人も使っているブランチならやらないほうが良いよね。
pushするまえならgit resetを使用すること。
【ホワイトハッカー入門】サーバの開いているポートとサービスをnmapで特定する。ついでにOS情報も拾ってくる
ホワイトハッカーとは
ハッキングの手法を熟知し、それを防御のために使ういいハッカー。
対義語はブラックハットハッカーとかクラッカーとか言われる。
ハッカーの攻撃手法
ハッカーの攻撃手法は、だいたい以下の用な手順になる。
偵察
スキャニング
アクセス権の取得
アクセスの維持
痕跡の消去
今回はこのスキャニングにチャレンジしてみる。
※ くれぐれも公開されているサーバに対してこれを行わないように
はじめてのポートスキャン
立ち上げているVMにたいしてポートスキャンを行う。
nmap -sV -O -PE 192.168.33.0/24
-sVオプション
バナー情報(サービスのバージョンなど)を収集する。
-Oオプション
OSの種類とバージョンを教えてくれる。
結果
Starting Nmap 7.60 ( https://nmap.org ) at 2018-01-08 11:28 JST Nmap scan report for 192.168.33.50 Host is up (0.00051s latency). Not shown: 998 closed ports PORT STATE SERVICE VERSION 22/tcp open ssh OpenSSH 6.6.1p1 Ubuntu 2ubuntu2.8 (Ubuntu Linux; protocol 2.0) 111/tcp open rpcbind 2-4 (RPC #100000) MAC Address: 08:00:27:7F:5E:D0 (Oracle VirtualBox virtual NIC) Device type: general purpose Running: Linux 3.X|4.X OS CPE: cpe:/o:linux:linux_kernel:3 cpe:/o:linux:linux_kernel:4 OS details: Linux 3.2 - 4.8 Network Distance: 1 hop Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel Nmap scan report for 192.168.33.91 Host is up (0.00037s latency). Not shown: 996 closed ports PORT STATE SERVICE VERSION 22/tcp open ssh OpenSSH 5.3 (protocol 2.0) 80/tcp open http Apache httpd 2.2.15 ((CentOS)) 111/tcp open rpcbind 2-4 (RPC #100000) 3306/tcp open mysql MySQL (unauthorized) MAC Address: 08:00:27:F4:E4:AA (Oracle VirtualBox virtual NIC) Device type: general purpose Running: Linux 2.6.X|3.X OS CPE: cpe:/o:linux:linux_kernel:2.6 cpe:/o:linux:linux_kernel:3 OS details: Linux 2.6.32 - 3.10
攻撃者にとって何が嬉しいか
ポートで動いているサービスがわかるので、
バージョンなどから脆弱性が判明する。
そうすると攻撃ができる。
防御するためにはどうしたらよいか
nmapはICMPプロトコルを使用しているので、
ICMPプロトコルを拒否するような設定を
サーバにしてやれば良いと思う(まだやったことないので後々調べます)
ハッキングがテーマのノベルゲーム「CyberRebeat」に触発されて、CTFの練習問題「Basic is secure?」を解くためにパケットキャプチャを使ってみた【CTF入門】
CyberRebeatとは
ハッキングを題材したノベルゲーム。
CyberRebeat -The Fifth Domain of Warfare-
作中、とあるハッカーはこう言います。
"僕らにとって、世界は不安なほどに穴だらけだ"、と。
ボタン一つでネットに繋がっているOA機器が検索でき、
10ドル出せばハッキングツールが説明書付きで手に入るこの時代。
本作では"CTF"と呼ばれる、現実に存在しているハッキング競技を皮切りに、
彼らの世界、その一端を描き出します。
CTFとは
コンピュータ・セキュリティ技術を用いた競技。
すごく簡単に言うと、ハッキング大会。
最近少し興味が湧いてきた。
CTF競技内容
主に2つある。
- attack/defense style
攻防戦形式(英語:attack/defense style)では、 各チームに守るべきコンピュータ(または小規模なネットワーク)が割り当てられ、 自チームのコンピュータに対する相手からの攻撃の防御成功、 及び相手のコンピュータに対する攻撃の成功に対し得点が与えられる。 個々のCTFのルールによって、 相手のコンピュータに侵入して情報を奪う(相手の旗を奪う)又は情報を書き込む(自分の旗を立てる)ことを企図する。
- jeopardy style
クイズ形式。出題された問題に隠されたFlagを手に入れ、
提出してポイントを貰う。
※「Capture The Flag」の略がCTF
入門として
以下のサイトに練習用の問題がある。
今回チャレンジした問題
手順
リンクからq8.pcapをダウンロード
wiresharkで読み込む
パケットがいっぱい出てきた(小並感)
気になるところを読む
この問題はBasic認証。
レスポンスヘッダに200 OKとでていることから、
Basic認証が成功したことがわかる。
4(レスポンス)をみてみる
実際のパケットのHTTPレイヤを見てみるとこんな感じ。
成功してるっぽい。
「The flag is q8's password.」とある。
3(リクエスト)を見てみる
あ。。あった。
感想
パケットキャプチャとBasic認証の知識があれば何となくいける問題だった。
この調子で他の問題も解いていこうと思う(networkとかwebを中心に)