mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
[ruby/cgi] Check integer overflow in long range
https://hackerone.com/reports/1328463 https://github.com/ruby/cgi/commit/ccaf6027e0
This commit is contained in:
parent
fbd7337016
commit
e4b35b158a
2 changed files with 28 additions and 2 deletions
|
@ -32,12 +32,21 @@ preserve_original_state(VALUE orig, VALUE dest)
|
|||
rb_enc_associate(dest, rb_enc_get(orig));
|
||||
}
|
||||
|
||||
static inline long
|
||||
escaped_length(VALUE str)
|
||||
{
|
||||
const long len = RSTRING_LEN(str);
|
||||
if (len >= LONG_MAX / HTML_ESCAPE_MAX_LEN) {
|
||||
ruby_malloc_size_overflow(len, HTML_ESCAPE_MAX_LEN);
|
||||
}
|
||||
return len * HTML_ESCAPE_MAX_LEN;
|
||||
}
|
||||
|
||||
static VALUE
|
||||
optimized_escape_html(VALUE str)
|
||||
{
|
||||
VALUE vbuf;
|
||||
typedef char escape_buf[HTML_ESCAPE_MAX_LEN];
|
||||
char *buf = *ALLOCV_N(escape_buf, vbuf, RSTRING_LEN(str));
|
||||
char *buf = ALLOCV_N(char, vbuf, escaped_length(str));
|
||||
const char *cstr = RSTRING_PTR(str);
|
||||
const char *end = cstr + RSTRING_LEN(str);
|
||||
|
||||
|
|
|
@ -104,6 +104,23 @@ class CGIUtilTest < Test::Unit::TestCase
|
|||
assert_not_predicate CGI.escapeHTML("Ruby".freeze), :frozen?
|
||||
end
|
||||
|
||||
def test_cgi_escape_html_large
|
||||
ulong_max, size_max = RbConfig::LIMITS.values_at("ULONG_MAX", "SIZE_MAX")
|
||||
return unless ulong_max < size_max # Platforms not concerned
|
||||
|
||||
size = (ulong_max / 6 + 1)
|
||||
begin
|
||||
str = '"' * size
|
||||
escaped = CGI.escapeHTML(str)
|
||||
rescue NoMemoryError
|
||||
omit "Not enough memory"
|
||||
rescue => e
|
||||
end
|
||||
assert_raise_with_message(ArgumentError, /overflow/, ->{"length = #{escaped.length}"}) do
|
||||
raise e if e
|
||||
end
|
||||
end
|
||||
|
||||
def test_cgi_unescapeHTML
|
||||
assert_equal("'&\"><", CGI.unescapeHTML("'&"><"))
|
||||
end
|
||||
|
|
Loading…
Reference in a new issue