$30 off During Our Annual Pro Sale. View Details »

CWEから学ぶ脆弱性

happynote3966
November 04, 2018

 CWEから学ぶ脆弱性

セキュリティ・ミニキャンプ in 北海道 2018で発表したスライド資料です

happynote3966

November 04, 2018
Tweet

More Decks by happynote3966

Other Decks in Technology

Transcript

  1. CWEから学ぶ脆弱性
    金沢工業大学 宮口誠
    @happynote3966

    View Slide

  2. この講義での目的
    2
    ソフトウェア(≒プログラム)には何かしらの脆弱性があります
    「脆弱性は塞がなければならない!」→「どうやって?」
    脆弱性を防ぐ、もしくは攻撃から守るためには
    その仕組みを知らなければなりません
    本講義では脆弱性の種類や
    それに対する攻撃手法と原理を学ぶことにより
    セキュアな(安全な)ソフトウェアを作成するための学びとします

    View Slide

  3. 講義の流れ
    3
    座学 演習
    座学 <<< 演習

    View Slide

  4. Level0 : Dreaming
    4

    View Slide

  5. まずはこの講義の
    概要をお伝えします!
    5

    View Slide

  6. CWE、脆弱性とは
    6
    脆弱性:ソフトウェア等において、コンピュータ不正アクセス、
    コンピュータウイルス等の攻撃により
    その機能や性能を損なう原因となり得る
    安全性上の問題箇所(1)
    CWE:製品の個々の脆弱性ではなく、
    ソフトウェアの弱点(脆弱性や不具合)のパターンに
    共通の呼び名を与えるプロジェクト(2)
    (1) https://www.ipa.go.jp/files/000011568.pdf より引用
    (2) https://www.ipa.go.jp/files/000059838.pdf より引用

    View Slide

  7. 今回学ぶことについて
    7
    以下のリンクにある、Cでありがちな脆弱性の種類について学びます
    https://cwe.mitre.org/data/definitions/658.html

    View Slide

  8. 配布VMについて
    8
    リンク:https://drive.google.com/file/d/1giv6ZPZGLlMFzK93uUqHYd-f3PKhoduW/view?usp=sharing
    USER:user PASS:justdoit
    :root :justdoit
    配布したVM内のディレクトリは以下のようになっています
    (~)/MiniCamp2018_Hokkaido
    + Level1
    + Level2
    + Level3
    + Level4
    + Level5
    各Levelがそれぞれフォルダ名に対応しています

    View Slide

  9. Level1 : Wake-up
    CWE-457 / CWE-478 / CWE-480 / CWE-483 / CWE-484 / CWE-783
    9

    View Slide

  10. C言語のストレッチをします
    慣れている人もそうでない人も
    クイズにチャレンジ!
    このレベルではPCを触らないよ!
    スライドの方を見てくださいね!
    10

    View Slide

  11. (前提知識)プログラムの制御構造
    11
    処理
    処理
    処理
    処理A 処理B
    制御式 制御式
    処理
    順次構造 選択構造
    (ifやswitch)
    繰り返し構造
    (forやwhile)

    View Slide

  12. Where is the BUG ? (CWE-457.c)
    12

    View Slide

  13. Where is the BUG ? (CWE-457.c)
    変数を初期化せずに使っている!
    13

    View Slide

  14. CWE-457 Use of Uninitialized Variable
    概要:初期化していない変数を使うことで、予想外の動作をしてしまうというもの
    変数は初期化してから使いましょう
    サンプル:zero_variableには0を代入すべきだったが、されていなかった
    zero_variableには何が入っているか分からないため
    ほぼ確実にlogin()を実行できない
    https://cwe.mitre.org/data/definitions/457.html 14

    View Slide

  15. Where is the BUG?? (CWE-478.c)
    15

    View Slide

  16. Where is the BUG?? (CWE-478.c)
    default文がない!
    (login_failedを呼び出していない!)
    16

    View Slide

  17. CWE-478 Missing Default Case in Switch Statement
    概要:default文が書いてないために本来の動作とは異なってしまう
    サンプル:login_failed()をdefault文の中で実行すべきだったが
    その記述がどこにも見当たらない
    passcodeにどんな値が代入されても
    login()が実行されてしまう
    17
    https://cwe.mitre.org/data/definitions/478.html

    View Slide

  18. Where is the BUG??? (CWE-480.c)
    18

    View Slide

  19. Where is the BUG??? (CWE-480.c)
    代入演算子を使っている!
    19

    View Slide

  20. CWE-480 Use of Incorrect Operator
    概要:間違った演算子を使ってしまい、セキュリティ上の問題を引き起こすこと
    サンプル:「=(代入演算子)」と「==(比較演算子のイコール)」を間違って使っていた
    本当なら「==」を使わないといけない
    passcodeが0以外であれば
    login()が実行される
    20
    https://cwe.mitre.org/data/definitions/480.html

    View Slide

  21. Where is the BUG???? (CWE-483.c)
    21

    View Slide

  22. Where is the BUG???? (CWE-483.c)
    if文の後のインデントがおかしい!
    22

    View Slide

  23. CWE-483 Incorrect Block Delimination
    概要:波カッコ「{ }」などを使ってブロックを分かりやすく分けてないせいで
    if文などのブロックの処理が複数行われてしまうこと
    サンプル:波カッコを使わずにif文を書くと、その下の一行だけがブロックになるが
    それよりも下の行がインデントをミスしている
    23
    https://cwe.mitre.org/data/definitions/483.html
    黄色の部分はif文
    緑色の部分は
    黄色のif分の結果に
    関係なく実行される

    View Slide

  24. Where is the BUG????? (CWE-484.c)
    24

    View Slide

  25. Where is the BUG????? (CWE-484.c)
    break文がない!
    25

    View Slide

  26. CWE-484 Omitted Break Statement in Switch
    概要:switch文の中に、break文をつけないと
    その下の処理も実行されてしまうということ
    サンプル:login_failed()の実行後に
    その下のcase文の中のlogin()も実行される
    26
    https://cwe.mitre.org/data/definitions/484.html
    case 1から実行すると
    login_failed()とlogin()が実行され
    case 0から実行すると
    login()が実行される

    View Slide

  27. Where is the BUG?????? (CWE-783.c)
    27

    View Slide

  28. Where is the BUG?????? (CWE-783.c)
    演算子の優先順位が間違っている!
    28

    View Slide

  29. CWE-783 Operator Precedence Logic Error
    概要:演算子の優先順位を間違ってしまい、予想外の処理をしてしまうこと
    サンプル:「=」よりも「==」のほうが優先順位が高いため
    is_loginにauth()の返り値が代入されるよりも前に0との比較が行われてしまった
    29
    https://cwe.mitre.org/data/definitions/783.html
    直感的には左から右へ実行しそうだが
    実際には「auth() == 0」が先に実行し
    その結果をis_loginに代入する

    View Slide

  30. Level2 : Stretch
    CWE-128 / CWE-134 / CWE-191 / CWE-194 / CWE-242 / CWE-476
    30

    View Slide

  31. ちょっとずつ難しくなります
    コンピュータの仕組みと照らしながら
    勉強しましょう!
    ここからは実際に
    手を動かしながら調べてみましょう!
    31

    View Slide

  32. (前提知識)CPUとレジスタについて
    32
    EAX
    EBX
    ECX
    EDX
    CPU レジスタ ビット列
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0

    View Slide

  33. Where is the BUG? (CWE-128.c)
    33

    View Slide

  34. Where is the BUG? (CWE-128.c)
    34

    View Slide

  35. What is the EVIL input?
    ? ?
    35

    View Slide

  36. What is the EVIL input?
    2147483647 1
    36

    View Slide

  37. CWE-128 Wrap-around Error
    概要:表せる範囲の最大値を超えて表そうとすると
    プラスの値がマイナスの値になってしまうこと(符号なしの場合は0に戻る)
    サンプル:sumが表せる最大範囲の2147483647を超えた足し算をしてしまった
    37
    https://cwe.mitre.org/data/definitions/128.html
    sum += input_numberが
    実行される前に
    最大値を超えないか確認すべきだった

    View Slide

  38. EX. 4bitで表した整数の足し算
    38
    0 0 0 0 0
    0 0 0 1 1
    0 0 1 0 2
    0 0 1 1 3
    0 1 0 1 5
    0 1 1 0 6
    0 1 1 1 7
    1 0 0 0 -8
    0 1 0 0 4 足し算の結果がマイナスになっている!
    +1
    +1
    +1
    +1
    +1
    +1
    +1
    +1

    View Slide

  39. Where is the BUG?? (CWE-134.c)
    39

    View Slide

  40. Where is the BUG?? (CWE-134.c)
    40

    View Slide

  41. What is the EVIL input??
    ? ?
    41

    View Slide

  42. What is the EVIL input??
    %d(%x) -889275714
    42

    View Slide

  43. CWE-134 Use of Externally-Controlled Format String
    概要:外部から入力される文字列をそのまま書式文字列として渡すこと
    サンプル:入力される文字列がprintf関数の第一引数になっているため
    書式指定子を入力するとそれに応じた結果が出力されてしまう
    43
    https://cwe.mitre.org/data/definitions/134.html
    外部からの入力を
    そのまま出力させたいのなら
    printf(“%s”,buf)にすべきだった

    View Slide

  44. 書式文字列と引数の関係(x86の場合)
    44
    printf(“%d %s %x”,integer,str,hex)
    printf(buf)
    ※bufには”%d %s %x”が入るとする
    “%d(1) %s(2) %x(3)”へのポインタ
    (1) integer(何かの整数)
    (2) str(何かの文字列へのポインタ )
    (3) hex(何かの整数)
    スタック(後述)
    “%d(1) %s(2) %x(3)”へのポインタ
    ??????????????????????????
    ??????????????????????????
    ??????????????????????????
    参照 参照
    スタック

    View Slide

  45. Where is the BUG??? (CWE-191.c)
    45

    View Slide

  46. Where is the BUG??? (CWE-191.c)
    46

    View Slide

  47. What is the EVIL input???
    ? ?
    47

    View Slide

  48. What is the EVIL input???
    2147483647 2
    48

    View Slide

  49. CWE-191 Integer Underflow (Wrap or
    Wraparound)
    概要:表せる範囲の最小値より小さい値を表そうとすると
    マイナスの値がプラスの値になってしまうこと(符号なしの場合は最大値になる)
    サンプル:sub_sumが表せる最小範囲の-2147483647を下回る引き算をしてしまった
    49
    https://cwe.mitre.org/data/definitions/191.html
    sub_sum -= input_numberが
    実行される前に
    最小値を下回らないか
    確認すべきだった

    View Slide

  50. EX. 4bitで表した整数の引き算
    50
    1 1 1 1 -1
    1 1 1 0 -2
    1 1 0 1 -3
    1 1 0 0 -4
    1 0 1 0 -6
    1 0 0 1 -7
    1 0 0 0 -8
    0 1 1 1 7
    1 0 1 1 -5 引き算の結果がプラスになっている!
    -1
    -1
    -1
    -1
    -1
    -1
    -1
    -1

    View Slide

  51. Where is the BUG???? (CWE-194.c)
    51

    View Slide

  52. Where is the BUG???? (CWE-194.c)
    52

    View Slide

  53. What is the EVIL input????
    ?
    53

    View Slide

  54. What is the EVIL input????
    65535
    54

    View Slide

  55. CWE-194 Unexpected Sign Extension
    概要:大きいデータ型から小さいデータ型へデータを移動する時に
    意図せず符号(プラスやマイナス)が付加してしまうこと
    サンプル
    55
    https://cwe.mitre.org/data/definitions/194.html
    number = tmp_numberをする際に
    2つのデータタイプを
    しっかりと確認すべきだった

    View Slide

  56. 2byteから1byteへの整数値のキャスト
    56
    0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1
    1 1 1 1 1 1 1 1
    無視される
    255
    -1
    2byteで(11111111)の時は255という扱いになるが
    1byteで(11111111)の時は-1という扱いになる

    View Slide

  57. Where is the BUG????? (CWE-242.c)
    57

    View Slide

  58. Where is the BUG????? (CWE-242.c)
    58

    View Slide

  59. What is the EVIL input?????
    ?
    59

    View Slide

  60. What is the EVIL input?????
    ‘A’ * 31~
    60

    View Slide

  61. CWE-242 Use of Inherently Dangerous Function
    概要:安全に動作する保証のない関数を使うこと
    サンプル:gets関数はユーザ側が任意の長さの入力をすることが可能
    61
    https://cwe.mitre.org/data/definitions/242.html
    getsを使うことがそもそも危険
    (後で解説するBOFにつながる)
    ※他にも危険な関数は存在する

    View Slide

  62. Where is the BUG?????? (CWE-476.c)
    62

    View Slide

  63. Where is the BUG?????? (CWE-476.c)
    63

    View Slide

  64. What is the EVIL input??????
    ?
    64

    View Slide

  65. What is the EVIL input??????
    [a-z]
    65

    View Slide

  66. CWE-476 NULL Pointer Dereference
    概要:NULLポインタを参照すると大抵の場合クラッシュしてしまうというもの
    サンプル:pointerに代入されるstrchrの返り値がNULLであるかをチェックしていない
    66
    https://cwe.mitre.org/data/definitions/476.html
    *pointer = ‘!’を実行する前に
    pointerの値がNULLかどうかを
    チェックしなければならなかった

    View Slide

  67. C言語における文字列
    67
    A B C D E F G H I J K L ...
    0x80486b4
    文字列本体
    0x80486b4
    alphabetの値
    変数(または定数)は
    文字列の「アドレス」を保存している
    ? ? ? ? ? ? ? ? ? ? ? ? ...
    0x0(NULL)
    ????????
    0x0
    小文字入力時の
    pointerの値
    アドレスが0の場所には
    何もない(アクセス禁止)

    View Slide

  68. Level3 : Running
    CWE-121 / CWE-124 / CWE-126 / CWE-127 / CWE-170
    68

    View Slide

  69. いよいよ本格的になります
    あの有名な脆弱性もでてくるよ!
    わからないことがあれば
    近くの人と話したり
    チューターに質問してみよう!
    69

    View Slide

  70. ASCII文字について
    70
    文字は全て文字コードに従って「数値」の表現を変えたものです
    詳しくは http://www3.nit.ac.jp/~tamura/ex2/ascii.html を参照
    0x31 = ‘1’
    0x40 = ‘@’
    0x41 = ‘A’

    View Slide

  71. メモリについて
    71
    0x01番地
    0x02番地
    0x03番地
    0x04番地
    CPU メモリ ビット列
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0
    0 0 0 0
    データ

    View Slide

  72. メモリについて
    72
    コード領域
    (実行するプログラムの場所)
    データ領域
    (実行のためのデータの場所)
    ヒープ領域
    (動的に確保するメモリの場所)
    スタック領域
    (一時変数などに使用するメモリの場所)
    0x00000000
    0xFFFFFFFF

    View Slide

  73. メモリについて
    73
    コード領域
    (実行するプログラムの場所)
    データ領域
    (実行のためのデータの場所)
    ヒープ領域
    (動的に確保するメモリの場所)
    スタック領域
    (一時変数などに使用するメモリの場所)
    スタック領域は
    上に向かって(アドレスの小さい方に)
    領域が増えていく
    0x00000000
    0xFFFFFFFF

    View Slide

  74. スタックについて
    74
    スタック
    push pop

    View Slide

  75. スタックについて
    75
    スタック
    引数2
    push pop

    View Slide

  76. スタックについて
    76
    スタック
    引数2
    引数1
    push pop

    View Slide

  77. スタックについて
    77
    スタック
    引数2
    引数1
    リターンアドレス(制御データ)
    push pop

    View Slide

  78. スタックについて
    78
    スタック
    引数2
    引数1
    リターンアドレス(制御データ)
    ローカル変数
    push pop

    View Slide

  79. スタックについて
    79
    スタック
    引数2
    引数1
    リターンアドレス(制御データ)
    ローカル変数
    push pop
    リターンアドレスや
    引数などは
    スタックにpushされる
    ローカル変数は
    スタック領域を増やすことで
    確保している
    (pushやpopではない)

    View Slide

  80. Where is the BUG? (CWE-121.c)
    80

    View Slide

  81. Where is the BUG? (CWE-121.c)
    81

    View Slide

  82. What is the EVIL input?
    ?
    82

    View Slide

  83. What is the EVIL input?
    ‘A’ * 16 ~
    83

    View Slide

  84. CWE-121 Stack-based Buffer Overflow
    概要:スタック上のバッファから大量のデータが流れ込み
    その下にある変数や重要なデータなどが上書きされてしまうもの
    サンプル:nameへの大量の入力でバッファオーバーフローを起こすことができる
    84
    https://cwe.mitre.org/data/definitions/121.html
    bufというバッファに溜め込める
    大きさを超えたデータが
    nameから流れ込んでしまった

    View Slide

  85. スタック上でバッファオーバーフローが起きる時
    85
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    入力用バッファ
    (データを入力する場所)
    重要なデータ
    (リターンアドレスや文字列など)
    スタック

    View Slide

  86. スタック上でバッファオーバーフローが起きる時
    86
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    入力用バッファ
    (データを入力する場所)
    データ入力後
    重要なデータ
    (リターンアドレスや文字列など)
    重要なデータ
    (リターンアドレスや文字列など)
    入力されたデータ 入




    スタック スタック

    View Slide

  87. スタック上でバッファオーバーフローが起きる時
    87
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    入力用バッファ
    (データを入力する場所)
    データ入力後
    重要なデータ
    (リターンアドレスや文字列など)
    重要なデータ
    (リターンアドレスや文字列など)
    入力されたデータ
    上書きされてしまった部分





    スタック スタック

    View Slide

  88. GDBで見てみる
    88
    $ gdb -q CWE-121
    (gdb) b *main+99
    (gdb) b *main+104
    (gdb) run
    (入力) AAAAAAAAAAAAAAAA
    (gdb) x/20xw $esp
    (gdb) c
    (gdb) x/20xw $esp

    View Slide

  89. メモリの状態
    89
    buf
    ecx
    上書きされた部分

    View Slide

  90. Where is the BUG??(CWE-124.c)
    90

    View Slide

  91. Where is the BUG??(CWE-124.c)
    91

    View Slide

  92. What is the EVIL input?
    92
    ? ?

    View Slide

  93. What is the EVIL input?
    93
    -10 P@ssword

    View Slide

  94. CWE-124 Buffer Underwrite (‘Buffer Underflow’)
    概要:書き込みの際にバッファより上の領域に対してデータが流れ込み
    書き込むバッファより上の領域に合ったデータが上書きされるもの
    サンプル:num_of_indent変数マイナスの値を入力することで
    バッファより上の領域にデータを書き込める
    94
    https://cwe.mitre.org/data/definitions/124.html
    scanf関数で
    マイナスの値が入力されるのを
    チェックしなければならなかった

    View Slide

  95. スタック上でバッファアンダーフローが起きる時
    95
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    入力用バッファ
    (データを入力する場所)
    重要なデータ
    (リターンアドレスや文字列など)
    スタック

    View Slide

  96. スタック上でバッファアンダーフローが起きる時
    96
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    入力用バッファ
    (データを入力する場所)
    データ入力後
    重要なデータ
    (リターンアドレスや文字列など)
    入力用バッファ
    (データを入力する場所)
    入力されたデータ





    スタック スタック

    View Slide

  97. スタック上でバッファアンダーフローが起きる時
    97
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    入力用バッファ
    (データを入力する場所)
    データ入力後
    重要なデータ
    (リターンアドレスや文字列など)
    入力用バッファ
    (データを入力する場所)
    入力されたデータ
    上書きされてしまった部分





    スタック スタック

    View Slide

  98. GDBで見てみる
    98
    $ gdb -q CWE-124
    (gdb) b *main+145
    (gdb) b *main+150
    (gdb) run
    (入力) -10
    (gdb) x/20xw $ebp - 0x26
    (gdb) c
    (入力) P@ssword
    (gdb) x/20xw $ebp - 0x26
    (gdb) x/s $ebp - 0x26

    View Slide

  99. メモリの状態
    99
    buf
    “P@ssword”になっている
    password
    bufのアドレス(0xffffd00c) -
    passwordのアドレス(0xffffd002)
    = 0xa(10)

    View Slide

  100. Where is the BUG??? (CWE-126.c)
    100

    View Slide

  101. Where is the BUG??? (CWE-126.c)
    101

    View Slide

  102. What is the EVIL input?
    ?
    102

    View Slide

  103. What is the EVIL input?
    24 ~
    103

    View Slide

  104. CWE-126 Buffer Over-read
    概要:スタック上のバッファからの読み込みのときに
    読み込んでいるバッファを超えてさらに読み込んでしまうもの
    サンプル:scanf関数で大きな値を入力するとその分だけ読み込んでしまう
    104
    https://cwe.mitre.org/data/definitions/126.html
    scanf関数で
    大きすぎる値が入力されるのを
    防がなければならなかった

    View Slide

  105. スタック上でバッファオーバーリードが起きる時
    105
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    出力用バッファ
    (出力データがある場所)
    重要なデータ
    (リターンアドレスや文字列など)
    スタック スタック

    View Slide

  106. スタック上でバッファオーバーリードが起きる時
    106
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    出力用バッファ
    (出力データがある場所)
    データ出力後
    重要なデータ
    (リターンアドレスや文字列など)
    重要なデータ
    (リターンアドレスや文字列など)
    出力されたデータ 出




    スタック スタック

    View Slide

  107. スタック上でバッファオーバーリードが起きる時
    107
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    出力用バッファ
    (出力データがある場所)
    データ出力後
    重要なデータ
    (リターンアドレスや文字列など)
    重要なデータ
    (リターンアドレスや文字列など)
    出力されたデータ
    余計に出力されて
    しまった部分
    (重要なデータ含む)





    スタック スタック

    View Slide

  108. GDBで見てみる
    108
    $ gdb -q CWE-126
    (gdb) b *main+149
    (gdb) run
    (入力) A
    (入力) 24
    (gdb) x/20xw $ebp - 0x28

    View Slide

  109. メモリの状態
    109
    name
    “!53cr37!”になっている buf
    nameの大きさ(16)+”!53cr37!”の大きさ(8)
    =24

    View Slide

  110. Where is the BUG???? (CWE-127.c)
    110

    View Slide

  111. Where is the BUG???? (CWE-127.c)
    111

    View Slide

  112. What is the EVIL input?
    ?
    112

    View Slide

  113. What is the EVIL input?
    -16
    113

    View Slide

  114. CWE-127 Buffer Under-read
    概要:スタック上のバッファからの読み込みのときに
    読み込んでいるバッファよりも上から読み込んでしまうもの
    サンプル:scanf関数でマイナスの値を入力することで
    バッファの上にあるデータを読み込める
    114
    https://cwe.mitre.org/data/definitions/127.html
    scanf関数で
    マイナスの値が入力されるのを
    チェックしなければならなかった

    View Slide

  115. スタック上でバッファアンダーリードが起きる時
    115
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    出力用バッファ
    (出力データがある場所)
    重要なデータ
    (リターンアドレスや文字列など)
    スタック

    View Slide

  116. スタック上でバッファアンダーリードが起きる時
    116
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    出力用バッファ
    (出力データがある場所)
    データ出力後
    重要なデータ
    (リターンアドレスや文字列など)
    出力用バッファ
    (出力データがある場所)
    出力されたデータ





    スタック スタック

    View Slide

  117. スタック上でバッファアンダーリードが起きる時
    117
    下位アドレス
    (数字が小さい)
    上位アドレス
    (数字が大きい)
    出力用バッファ
    (出力データがある場所)
    データ出力後
    重要なデータ
    (リターンアドレスや文字列など)
    出力用バッファ
    (出力データがある場所)
    出力されたデータ
    余計に出力されて
    しまった部分
    (重要なデータ含む)





    スタック スタック

    View Slide

  118. GDBで見てみる
    118
    $ gdb -q CWE-127
    (gdb) b *main+145
    (gdb) run
    (入力) A
    (入力) -24
    (gdb) x/20xw $ebp - 0x38

    View Slide

  119. メモリの状態
    119
    secret_buf
    “P@ssword”になっている
    user_buf
    secret_bufのアドレス(0xffffcff0) -
    user_bufのアドレス(0xffffd000)
    = 0x10(16)

    View Slide

  120. Where is the BUG ????? (CWE-170.c)
    120

    View Slide

  121. Where is the BUG ????? (CWE-170.c)
    121

    View Slide

  122. What is the EVIL input?
    ?
    122

    View Slide

  123. What is the EVIL input?
    ‘A’ * 15
    123
    ※16文字以上の入力でも可 ただしその場合は一度で loginを実行できない
    16文字の入力の場合、 ’\n’の文字がバッファに貯まるため、パスワード入力時に失敗する

    View Slide

  124. CWE-170 Improper Null Termination
    概要:しっかりとしたNULL文字終端をしていないということ
    サンプル:read関数に大量の文字列を送ることでNULL文字をなくすことができる
    124
    https://cwe.mitre.org/data/definitions/170.html
    read関数の後で
    適切なNULL文字の挿入を
    すべきだった

    View Slide

  125. read関数でNULL文字(‘\0’)が入らないワケ
    125
    A A A A \n \0 S E C R E T
    buffer secret
    read(0,buffer,6)
    AAAA(改行)
    A A A A A \n S E C R E T
    buffer secret
    read(0,buffer,6)
    AAAAA(改行)
    1つの文字列 1つの文字列
    1つの文字列

    View Slide

  126. GDBで見てみる
    126
    $ gdb -q CWE-170
    (gdb) b *main+102
    (gdb) b *main+107
    (gdb) run
    (gdb) x/20xw $ebp - 0x21
    (gdb) c
    (入力) AAAAAAAAAAAAAAA
    (gdb) x/20xw $ebp - 0x21

    View Slide

  127. メモリの状態
    127
    “!53cre7!”になっている
    buf
    buf
    改行文字が挿入されている

    View Slide

  128. Level4 : Dash
    CWE-122 / CWE-244 / CWE-415 / CWE-416
    128

    View Slide

  129. かなり難しくなります
    メモリについての知識が
    必要になります!
    一度に全部覚える
    必要はありません!
    少しずつ理解していきましょう!
    129

    View Slide

  130. メモリについて
    130
    コード領域
    (実行するプログラムの場所)
    データ領域
    (実行のためのデータの場所)
    ヒープ領域
    (動的に確保するメモリの場所)
    スタック領域
    (一時変数などに使用するメモリの場所)
    0x00000000
    0xFFFFFFFF

    View Slide

  131. メモリについて
    131
    コード領域
    (実行するプログラムの場所)
    データ領域
    (実行のためのデータの場所)
    ヒープ領域
    (動的に確保するメモリの場所)
    スタック領域
    (一時変数などに使用するメモリの場所)
    ヒープ領域は
    下に向かって(アドレスの大きい方に)
    領域が増えていく
    0x00000000
    0xFFFFFFFF

    View Slide

  132. ヒープについて
    132
    ヒープ

    View Slide

  133. ヒープについて
    133
    ヒープ
    管理領域(ヒープ管理のための場所)
    データ領域
    (実際にユーザが使えるメモリの場所)
    malloc
    ptr

    View Slide

  134. ヒープについて
    134
    ヒープ
    管理領域(ヒープ管理のための場所)
    データ領域
    (実際にユーザが使えるメモリの場所)
    free
    ptr
    管理領域(重なる部分もある)

    View Slide

  135. Where is the BUG ? (CWE-122.c)
    135

    View Slide

  136. Where is the BUG ? (CWE-122.c)
    136

    View Slide

  137. What is the EVIL input?
    137
    ?

    View Slide

  138. What is the EVIL input?
    ‘A’*24+’Overwrite!’
    138

    View Slide

  139. CWE-122 Heap-based Buffer Overflow
    概要:ヒープ上で割り当てたメモリ領域の大きさを超えたデータが書き込まれること
    サンプル:gets関数によって割り当てたヒープ上のメモリ領域の大きさを超えて
    別のメモリ領域に書き込んでいる
    139
    https://cwe.mitre.org/data/definitions/122.html
    割り当てたメモリ領域に対して
    入力サイズを合わせるべきだった

    View Slide

  140. malloc
    malloc
    ヒープ上のオーバーフローで上書きできるワケ
    140
    ptr2が指し示す
    メモリ領域
    ptr1が指し示す
    メモリ領域
    ヒープ
    ptr1
    ptr2

    View Slide

  141. ヒープ上のオーバーフローで上書きできるワケ
    141
    ptr2が指し示す
    メモリ領域
    ptr1が指し示す
    メモリ領域
    ヒープ
    ptr1
    ptr2
    入力されたデータ





    View Slide

  142. ヒープ上のオーバーフローで上書きできるワケ
    142
    ptr2が指し示す
    メモリ領域
    ptr1が指し示す
    メモリ領域
    ヒープ
    ptr1
    ptr2
    入力されたデータ
    上書きされた領域





    View Slide

  143. GDBで見てみる
    143
    $ gdb -q CWE-122
    (gdb) b *main+27
    (gdb) b *main+89
    (gdb) b *main+94
    (gdb) run
    (gdb) print $eax
    (gdb) c
    (gdb) x/20xw $1
    (gdb) c
    (入力) AAAAAAAAAAAAAAAAAAAAAAAAOverwrite!
    (gdb) x/20xw $1

    View Slide

  144. メモリの状態
    144
    ptr1の示すメモリ領域
    上書きされた部分
    ptr2の示すメモリ領域

    View Slide

  145. Where is the BUG ?? (CWE-244.c)
    145

    View Slide

  146. Where is the BUG ?? (CWE-244.c)
    146

    View Slide

  147. What is the EVIL input?
    ?
    147

    View Slide

  148. What is the EVIL input?
    37 ~ 4096
    148

    View Slide

  149. CWE-224 Clearing of Heap Memory Before Release (‘Heap Inspection’)
    概要:reallocを使った際に重要なデータをそのまま残してしまうこと
    サンプル:reallocするサイズを極端に小さくしなければ残ったパスワードが表示される
    149
    https://cwe.mitre.org/data/definitions/244.html
    ptr2の内容に入力する前に
    ゼロクリアすべきだった

    View Slide

  150. malloc
    reallocで割り当てたメモリの中身
    150
    ptr1が指し示す
    mallocで割り当てた
    メモリ領域
    ヒープ
    ptr1

    View Slide

  151. reallocで割り当てたメモリの中身
    151
    ヒープ
    ptr1
    書き込んだデータ

    View Slide

  152. realloc
    reallocで割り当てたメモリの中身
    152
    reallocで再度割り当てた領域
    ヒープ
    ptr1
    書き込んだデータ
    ptr2

    View Slide

  153. reallocで割り当てたメモリの中身
    153
    reallocで再度割り当てた領域
    ヒープ
    ptr1
    書き込んだデータ
    書き込んだデータは
    そのまま残ってしまう
    (サイズを小さくした場合は
    差分だけが消える)
    ptr2

    View Slide

  154. GDBで見てみる
    154
    $ gdb -q CWE-244
    (gdb) b *main+78
    (gdb) b *main+199
    (gdb) run
    (gdb) print $eax
    (gdb) c
    (入力) 37
    (gdb) print $eax
    (gdb) x/s $2

    View Slide

  155. メモリの状態
    155
    mallocの返り値も
    reallocの返り値も
    一緒になっている
    $2の指し示す場所には
    元から格納されていた
    文字列がある

    View Slide

  156. Where is the BUG ??? (CWE-415.c)
    156

    View Slide

  157. Where is the BUG ??? (CWE-415.c)
    157

    View Slide

  158. What is the EVIL input?
    ?
    158

    View Slide

  159. What is the EVIL input?
    ‘A’ * 9 ~
    159

    View Slide

  160. CWE-415 Double Free
    概要:一度freeしたメモリ領域を再度freeすること
    サンプル:文字列の長さを10にすると2回freeされてしまう
    160
    https://cwe.mitre.org/data/definitions/415.html
    最後にまとめてfreeすべきだった
    (条件分岐内で分けて
    freeを書かなくてよかった)

    View Slide

  161. GDBで見てみる
    161
    $ gdb -q CWE-415
    (gdb) b *main+157
    (gdb) b *main+206
    (gdb) run
    (入力) AAAAAAAAAA
    (gdb) x/xw $esp
    (gdb) c
    (gdb) x/xw $esp

    View Slide

  162. メモリの状態
    162
    どちらも同じ値
    (freeへの引数が
    どちらも一緒)

    View Slide

  163. Where is the BUG ???? (CWE-416.c)
    163

    View Slide

  164. Where is the BUG ???? (CWE-416.c)
    164

    View Slide

  165. What is the EVIL input?
    ?
    165
    ?

    View Slide

  166. What is the EVIL input?
    3→4→AAA
    166
    4

    View Slide

  167. CWE-416 Use After Free
    概要:freeしたあとにNULL代入をせず再度使用すること
    サンプル:一度freeしたメモリ領域をそのまま使うことで
    中に入っていたデータを抜き出すことができる
    167
    https://cwe.mitre.org/data/definitions/416.html
    freeした後のポインタは
    NULLを代入しておくべきだった

    View Slide

  168. malloc
    freeの後にNULL代入せずに使用すると
    168
    ptr1が指し示す
    mallocで割り当てた
    メモリ領域
    ヒープ
    ptr1

    View Slide

  169. freeの後にNULL代入せずに使用すると
    169
    ptr1が指し示す
    mallocで割り当てた
    メモリ領域
    ヒープ
    ptr1
    入力したデータ

    View Slide

  170. free
    freeの後にNULL代入せずに使用すると
    170
    freeした際の管理データ
    ヒープ
    ptr1
    入力したデータ

    View Slide

  171. freeの後にNULL代入せずに使用すると
    171
    freeした際の管理データ
    ヒープ
    ptr1
    入力したデータ
    NULL代入されてないptr1を使うことで
    管理データを書き換えたり
    入力したデータを
    読み取ったりすることができる

    View Slide

  172. GDBで見てみる
    172
    $ gdb -q CWE-416
    (gdb) b *main+146
    (gdb) b *main+395
    (gdb) b *main+400
    (gdb) run
    (gdb) x/xw $esp (※0x0804b008)
    (gdb) c
    (入力) 3
    (入力) 4
    (gdb) x/20xw 0x0804b008
    (gdb) c
    (入力) AAA
    (gdb) x/20xw 0x0804b008

    View Slide

  173. メモリの状態
    173
    管理領域の部分が
    0クリアされている
    freeされたptrが指し
    示すメモリ領域
    管理領域の部分に
    書き込んでいる

    View Slide

  174. Level5 : Flying
    CWE-??? / CWE-??? / CWE-??? / CWE-??? / CWE-???
    174

    View Slide

  175. ここまでの集大成として
    プログラムの中から
    脆弱性を探してみましょう!
    今までに学んだ知識を総動員して
    取り組んでみてください!
    175

    View Slide

  176. 出題するプログラムについて
    ls,wc,strings,rev,whichのコマンドを真似したプログラムです
    (実際の動作とは異なっていますが、気にしないでください)
    各プログラムから脆弱性を探してください
    こうなったら正解です
    ・プログラムが異常終了する
    ・本来の動作とは異なる動きをした(予想の動作と異なった)
    想定解以外もあるかもしれません
    176

    View Slide

  177. Where is the BUG? (ls_vuln.c)
    177

    View Slide

  178. Where is the BUG?? (wc_vuln.c)
    178

    View Slide

  179. Where is the BUG??? (strings_vuln.c)
    179

    View Slide

  180. Where is the BUG???? (rev_vuln.c)
    180

    View Slide

  181. Where is the BUG????? (which_vuln.c)
    181

    View Slide

  182. Re:Level5
    Flying with Conpass
    CWE-??? / CWE-??? / CWE-??? / CWE-??? / CWE-???
    182

    View Slide

  183. This is the BUG! (ls_vuln.c)
    183

    View Slide

  184. PoC
    184

    View Slide

  185. This is the BUG!! (wc_vuln.c)
    185

    View Slide

  186. PoC
    186

    View Slide

  187. This is the BUG!!! (strings_vuln.c)
    187

    View Slide

  188. PoC
    188

    View Slide

  189. This is the BUG!!!! (rev_vuln.c)
    189

    View Slide

  190. PoC
    190

    View Slide

  191. This is the BUG!!!!! (which_vuln.c)
    191

    View Slide

  192. PoC
    192

    View Slide

  193. Thank you for your attention!
    (おつかれさまでした!)
    193

    View Slide