https://techlife.cookpad.com/entry/2022/12/26/121950
Ruby3.2.0でReDoS対策が入ったということで、2022年と2023年に報告したReDoSの脆弱性で公表されたものについて効果を確認してみました。[1][2][3][4][5][6][7][8]
(2024年追記)Ruby3.3.xで確認したものはこちら
https://github.com/lostisland/faraday-net_http/pull/27
require'benchmark'defattack_text(length) text='charset='+"\t"* length+"a"+"\t"* length+"a"/\bcharset=\s*(.+?)\s*(;|$)/.match(text)endBenchmark.bmdo|x| x.report{ attack_text(10)} x.report{ attack_text(100)} x.report{ attack_text(1000)} x.report{ attack_text(10000)} x.report{ attack_text(100000)}end
# Ruby 3.1.2❯ bundle exec ruby encoded_body_benchmark.rb user system total real 0.000009 0.000000 0.000009 ( 0.000005) 0.000060 0.000000 0.000060 ( 0.000060) 0.005131 0.000001 0.005132 ( 0.005132) 0.520823 0.000839 0.521662 ( 0.521920) 54.252044 0.137403 54.389447 ( 54.445226)# Ruby 3.2.0❯ bundle exec ruby encoded_body_benchmark.rb user system total real 0.000008 0.000001 0.000009 ( 0.000006) 0.000008 0.000001 0.000009 ( 0.000008) 0.000063 0.000007 0.000070 ( 0.000070) 0.000562 0.000059 0.000621 ( 0.000621) 0.005639 0.001153 0.006792 ( 0.006816)
https://github.com/sinatra/sinatra/pull/1823
require'benchmark'defattack_text(length)("\t"* length+"\ta,a\t").split(/\s*,\s*/)endBenchmark.bmdo|x| x.report{ attack_text(10)} x.report{ attack_text(100)} x.report{ attack_text(1000)} x.report{ attack_text(10000)} x.report{ attack_text(100000)}end
# Ruby 3.1.2❯ bundle exec ruby ip_spoofing_benchmark.rb user system total real 0.000006 0.000000 0.000006 ( 0.000004) 0.000027 0.000000 0.000027 ( 0.000028) 0.002230 0.000000 0.002230 ( 0.002229) 0.219735 0.000466 0.220201 ( 0.220294) 22.132207 0.056974 22.189181 ( 22.218286)# Ruby 3.2.0❯ bundle exec ruby ip_spoofing_benchmark.rb user system total real 0.000006 0.000001 0.000007 ( 0.000005) 0.000007 0.000000 0.000007 ( 0.000007) 0.000030 0.000001 0.000031 ( 0.000030) 0.000269 0.000001 0.000270 ( 0.000269) 0.002656 0.000016 0.002672 ( 0.002673)
https://github.com/advisories/GHSA-crjr-9rc5-ghw8
PoCは非公開です。
# Ruby 3.1.2❯ bundle exec ruby nokogiri_benchmark.rb user system total real 0.000047 0.000020 0.000067 ( 0.000063) 0.000040 0.000001 0.000041 ( 0.000041) 0.002257 0.000016 0.002273 ( 0.002285) 0.219902 0.000521 0.220423 ( 0.220524) 22.096186 0.069899 22.166085 ( 22.181980)# Ruby 3.2.0❯ bundle exec ruby nokogiri_benchmark.rb user system total real 0.000127 0.000187 0.000314 ( 0.000308) 0.000045 0.000001 0.000046 ( 0.000046) 0.000078 0.000000 0.000078 ( 0.000080) 0.000536 0.000103 0.000639 ( 0.000645) 0.005045 0.001094 0.006139 ( 0.006158)
https://discuss.rubyonrails.org/t/cve-2022-30122-denial-of-service-vulnerability-in-rack-multipart-parsing/80729
https://hackerone.com/reports/1489141
require'benchmark'require'rack'regexp= Rack::Multipart::BROKEN_UNQUOTEDdefattack_text(length)'Content-Disposition:a'+"\t"* length+"\tfilename=m"endBenchmark.bmdo|x| x.report{ attack_text(10)[regexp]} x.report{ attack_text(100)[regexp]} x.report{ attack_text(1000)[regexp]} x.report{ attack_text(10000)[regexp]} x.report{ attack_text(100000)[regexp]}end
# Ruby 3.1.2❯ bundle exec ruby broken_unquoted_benchmark.rb user system total real 0.000009 0.000000 0.000009 ( 0.000006) 0.000034 0.000000 0.000034 ( 0.000034) 0.002474 0.000000 0.002474 ( 0.002474) 0.243811 0.000512 0.244323 ( 0.244369) 24.450106 0.058915 24.509021 ( 24.570598)# Ruby 3.2.0❯ bundle exec ruby broken_unquoted_benchmark.rb user system total real 0.000006 0.000001 0.000007 ( 0.000006) 0.000007 0.000000 0.000007 ( 0.000006) 0.000043 0.000005 0.000048 ( 0.000048) 0.000366 0.000035 0.000401 ( 0.000403) 0.003492 0.000377 0.003869 ( 0.003870)
https://github.com/rails/rails-html-sanitizer/security/advisories/GHSA-5x79-w82f-gw8w
https://hackerone.com/reports/1684163
require'benchmark'require'rails-html-sanitizer'defscrub(length) scrubber= Rails::Html::PermitScrubber.new scrubber.tags=['s'] scrubber.attributes=['mask'] mask='url(uu'* length html_fragment= Loofah.fragment('<s mask="'+ mask+'">aa</s>') html_fragment.scrub!(scrubber)endBenchmark.bmdo|x| x.report{ scrub(10)} x.report{ scrub(100)} x.report{ scrub(1000)} x.report{ scrub(10000)} x.report{ scrub(100000)}end
# Ruby 3.1.2❯ bundle exec ruby scrub_benchmark.rb user system total real 0.000219 0.000189 0.000408 ( 0.000407) 0.000327 0.000004 0.000331 ( 0.000334) 0.024247 0.000039 0.024286 ( 0.024305) 2.282625 0.005343 2.287968 ( 2.288805) 228.092186 0.567187 228.659373 (229.374108)# Ruby 3.2.0❯ bundle exec ruby scrub_benchmark.rb user system total real 0.000312 0.000393 0.000705 ( 0.000702) 0.000170 0.000004 0.000174 ( 0.000173) 0.000483 0.000012 0.000495 ( 0.000496) 0.003801 0.000076 0.003877 ( 0.003876) 0.029116 0.000737 0.029853 ( 0.029881)
PoCは非公開です。
# Ruby 3.1.2❯ bundle exec ruby multipart_content_disposition_benchmark.rb user system total real 0.000014 0.000001 0.000015 ( 0.000012) 0.000602 0.000003 0.000605 ( 0.000604) 0.050963 0.000148 0.051111 ( 0.051170) 4.976457 0.018192 4.994649 ( 5.011038)❯ bundle exec ruby byte_range_benchnark.rb user system total real 0.000013 0.000000 0.000013 ( 0.000011) 0.000010 0.000001 0.000011 ( 0.000010) 0.000055 0.000001 0.000056 ( 0.000055) 0.000490 0.000043 0.000533 ( 0.000533) 0.004374 0.000447 0.004821 ( 0.004826)
PoCは非公開です。
# Ruby 3.1.2❯ bundle exec ruby multipart_content_disposition_benchmark.rb user system total real 0.000012 0.000000 0.000012 ( 0.000010) 0.000519 0.000007 0.000526 ( 0.000526) 0.048907 0.000134 0.049041 ( 0.049124) 4.828467 0.011421 4.839888 ( 4.842429)# Ruby 3.2.0❯ bundle exec ruby multipart_content_disposition_benchmark.rb user system total real 0.000014 0.000000 0.000014 ( 0.000010) 0.000072 0.000000 0.000072 ( 0.000072) 0.000697 0.000081 0.000778 ( 0.000778) 0.006980 0.002688 0.009668 ( 0.009751)
PoCは非公開です。
# Ruby 3.1.2❯ bundle exec ruby rfc2183_benchmark.rb user system total real 0.000019 0.000000 0.000019 ( 0.000018) 0.000358 0.000004 0.000362 ( 0.000374) 0.010729 0.000005 0.010734 ( 0.010737) 0.349436 0.000997 0.350433 ( 0.350911) 11.105921 0.027338 11.133259 ( 11.137913) 22.203780 0.054924 22.258704 ( 22.265718)# Ruby 3.2.0❯ bundle exec ruby rfc2183_benchmark.rb user system total real 0.000018 0.000001 0.000019 ( 0.000017) 0.000371 0.000001 0.000372 ( 0.000370) 0.011043 0.000007 0.011050 ( 0.011049) 0.351671 0.001075 0.352746 ( 0.352980) 11.349351 0.031033 11.380384 ( 11.393231) 22.604759 0.055164 22.659923 ( 22.677514)# Regexp.timeout = 1 を設定❯ bundle exec ruby rfc2183_benchmark.rb user system total real 0.000022 0.000002 0.000024 ( 0.000021) 0.000422 0.000001 0.000423 ( 0.000422) 0.012381 0.000041 0.012422 ( 0.012450) 0.349678 0.000886 0.350564 ( 0.352141) rfc2183_benchmark.rb:21:in `[]': regexp match timeout (Regexp::TimeoutError)
PoCは非公開です。
❯ bundle exec ruby cookie_host_benchmark.rb user system total real 0.000010 0.000000 0.000010 ( 0.000008) 0.002671 0.000003 0.002674 ( 0.002687) 2.439260 0.004220 2.443480 ( 2.444101) user system total real 0.000007 0.000004 0.000011 ( 0.000010) 0.000030 0.000001 0.000031 ( 0.000030) 0.002248 0.000006 0.002254 ( 0.002255) 0.219704 0.000269 0.219973 ( 0.220068) 21.977842 0.046066 22.023908 ( 22.034360)❯ bundle exec ruby cookie_host_benchmark.rb user system total real 0.000006 0.000001 0.000007 ( 0.000006) 0.000012 0.000000 0.000012 ( 0.000012) 0.000089 0.000001 0.000090 ( 0.000089) user system total real 0.000003 0.000001 0.000004 ( 0.000003) 0.000004 0.000000 0.000004 ( 0.000004) 0.000026 0.000000 0.000026 ( 0.000026) 0.000247 0.000000 0.000247 ( 0.000247) 0.002451 0.000018 0.002469 ( 0.002469)
PoCは非公開です。
# Ruby 3.1.2❯ bundle exec ruby underscore_benchmark.rb user system total real 0.000011 0.000000 0.000011 ( 0.000010) 0.000119 0.000000 0.000119 ( 0.000120) 0.010398 0.000008 0.010406 ( 0.010406) 1.049821 0.002955 1.052776 ( 1.053137)# Ruby 3.2.0❯ bundle exec ruby underscore_benchmark.rb user system total real 0.000012 0.000000 0.000012 ( 0.000011) 0.000108 0.000001 0.000109 ( 0.000108) 0.009456 0.000003 0.009459 ( 0.009463) 0.955143 0.001402 0.956545 ( 0.956543) 3.853790 0.007212 3.861002 ( 3.862404)# Regexp.timeout = 1 を設定❯ bundle exec ruby underscore_benchmark.rb user system total real 0.000011 0.000000 0.000011 ( 0.000010) 0.000107 0.000000 0.000107 ( 0.000107) 0.009443 0.000003 0.009446 ( 0.009447) 0.955830 0.001711 0.957541 ( 0.957541) .../active_support/inflector/methods.rb:100:in `gsub!': regexp match timeout (Regexp::TimeoutError)
PoCは非公開です。
# Ruby 3.1.2❯ bundle exec ruby locate_benchmark.rb user system total real 0.000018 0.000000 0.000018 ( 0.000016) 0.000044 0.000001 0.000045 ( 0.000044) 0.003033 0.000005 0.003038 ( 0.003038) 0.309519 0.000834 0.310353 ( 0.310375) 31.824798 0.084978 31.909776 ( 31.958167)# Ruby 3.2.0❯ bundle exec ruby locate_benchmark.rb user system total real 0.000018 0.000001 0.000019 ( 0.000016) 0.000016 0.000000 0.000016 ( 0.000016) 0.000070 0.000000 0.000070 ( 0.000071) 0.000617 0.000057 0.000674 ( 0.000674) 0.006024 0.000507 0.006531 ( 0.006554)
PoCは非公開です。
# Ruby 3.1.2❯ bundle exec ruby parse_http_accept_header_benchmark.rb user system total real 0.000730 0.000075 0.000805 ( 0.000806) 0.000029 0.000000 0.000029 ( 0.000029) 0.002216 0.000001 0.002217 ( 0.002220) 0.220513 0.000369 0.220882 ( 0.220962) 22.217365 0.053620 22.270985 ( 22.292816) # Ruby 3.2.1❯ bundle exec ruby parse_http_accept_header_benchmark.rb user system total real 0.000740 0.000137 0.000877 ( 0.001285) 0.000007 0.000000 0.000007 ( 0.000007) 0.000031 0.000000 0.000031 ( 0.000031) 0.000289 0.000001 0.000290 ( 0.000288) 0.002693 0.000028 0.002721 ( 0.002721)
https://www.ruby-lang.org/en/news/2023/03/30/redos-in-time-cve-2023-28756/
require'benchmark'require'time'defrfc2822_parse(length) text="0 Feb 00 00 :00"+" "* lengthTime.rfc2822(text)rescue ArgumentErrornilendBenchmark.bmdo|x| x.report{ rfc2822_parse(100)} x.report{ rfc2822_parse(1000)} x.report{ rfc2822_parse(10000)} x.report{ rfc2822_parse(100000)}end
# Ruby 3.1.1❯ bundle exec ruby rfc2822_benchmark.rb user system total real 0.000326 0.000009 0.000335 ( 0.000344) 0.029284 0.000054 0.029338 ( 0.029469) 2.860528 0.007354 2.867882 ( 2.875771) 290.843621 0.889107 291.732728 (292.665729)# Ruby 3.2.0❯ bundle exec ruby rfc2822_benchmark.rb user system total real 0.000399 0.000001 0.000400 ( 0.000398) 0.035984 0.000014 0.035998 ( 0.036022) 3.612121 0.007010 3.619131 ( 3.621582) 364.668771 0.667106 365.335877 (365.889942)# Regexp.timeout = 1 を設定❯ bundle exec ruby rfc2822_benchmark.rb user system total real 0.000401 0.000003 0.000404 ( 0.000397) 0.037018 0.000043 0.037061 ( 0.037122).../ruby/3.2.0/gems/time-0.2.0/lib/time.rb:515:in `rfc2822': regexp match timeout (Regexp::TimeoutError)
https://github.com/ruby/webrick/pull/114
PoCは非公開です。
# Ruby 3.1.1❯ bundle exec ruby split_header_value_benchmark.rb user system total real 0.420393 0.000661 0.421054 ( 0.421074) 6.692469 0.021099 6.713568 ( 6.715372) 27.340398 0.053937 27.394335 ( 27.400080)# Ruby 3.2.0❯ bundle exec ruby split_header_value_benchmark.rb user system total real 0.000039 0.000005 0.000044 ( 0.000040) 0.000014 0.000001 0.000015 ( 0.000014) 0.000012 0.000001 0.000013 ( 0.000013)
# Ruby 3.1.1❯ bundle exec ruby parse_header_benchmark.rb user system total real 0.000046 0.000000 0.000046 ( 0.000045) 0.002830 0.000006 0.002836 ( 0.002880) 0.289383 0.000658 0.290041 ( 0.291199) 9.288186 0.022931 9.311117 ( 9.347838) user system total real 0.000056 0.000009 0.000065 ( 0.000064) 0.002887 0.000045 0.002932 ( 0.002933) 0.288451 0.000852 0.289303 ( 0.290568) 9.265106 0.021469 9.286575 ( 9.323628)# Ruby 3.2.0❯ bundle exec ruby parse_header_benchmark.rb user system total real 0.000024 0.000003 0.000027 ( 0.000025) 0.000046 0.000006 0.000052 ( 0.000052) 0.000394 0.000068 0.000462 ( 0.000461) 0.002031 0.000367 0.002398 ( 0.002397) user system total real 0.000012 0.000006 0.000018 ( 0.000018) 0.000044 0.000003 0.000047 ( 0.000045) 0.000402 0.000030 0.000432 ( 0.000433) 0.002194 0.000419 0.002613 ( 0.002630)
https://www.ruby-lang.org/en/news/2023/06/29/redos-in-uri-CVE-2023-36617/
PoCは非公開です。
# Ruby 3.1.4❯ ruby port_benchmark.rb user system total real 0.000031 0.000003 0.000034 ( 0.000034) 0.000046 0.000001 0.000047 ( 0.000046) 0.002861 0.000021 0.002882 ( 0.002891) 0.288848 0.000418 0.289266 ( 0.289520) 29.524255 0.130043 29.654298 ( 29.694707)# Ruby 3.2.2❯ bundle exec ruby port_benchmark.rb user system total real 0.000033 0.000002 0.000035 ( 0.000034) 0.000016 0.000000 0.000016 ( 0.000016) 0.000054 0.000000 0.000054 ( 0.000054) 0.000434 0.000028 0.000462 ( 0.000462) 0.004022 0.000382 0.004404 ( 0.004415)
# Ruby 3.1.4❯ bundle exec ruby parser_split_benchmark.rb user system total real 0.000619 0.000007 0.000626 ( 0.000626) 0.000614 0.000006 0.000620 ( 0.000622) 0.003432 0.000016 0.003448 ( 0.003458) 0.289117 0.000848 0.289965 ( 0.290573) 29.683022 0.094622 29.777644 ( 29.896222)# Ruby 3.2.2❯ bundle exec ruby parser_split_benchmark.rb user system total real 0.000575 0.000009 0.000584 ( 0.000585) 0.000558 0.000004 0.000562 ( 0.000562) 0.003463 0.000012 0.003475 ( 0.003486) 0.303833 0.000568 0.304401 ( 0.304554) 30.954630 0.080803 31.035433 ( 31.087450)
2023/1/5 公開されたPoCを追記↩︎
2023/1/19 CVE-2022-44570, CVE-2022-44571, CVE-2022-44572, CVE-2023-22792, CVE-2023-22796, CVE-2023-22799 を追加↩︎
2023/3/19 CVE-2023-27539を追加、記事が長くなってきたのでPoCをアコーディオン内に移動↩︎
2023/4/2 CVE-2023-28756を追加↩︎
2023/4/22 WEBrickを追加↩︎
2023/6/18 CVE-2023-28756のPoCを追加↩︎
2023/7/5 CVE-2023-36617を追加↩︎
2023/8/14 CVE-2022-30122のPoCを追加↩︎
バッジを受け取った著者にはZennから現金やAmazonギフトカードが還元されます。