console.c: OOB access

* ext/io/console/console.c (console_set_winsize): fix
  out-of-bounds access.  [ruby-core:79004] [Bug #13112]

git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@57280 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
This commit is contained in:
nobu 2017-01-07 22:52:03 +00:00
parent d59dfcdb04
commit 5b856ee1a6
2 changed files with 34 additions and 2 deletions

View File

@ -535,12 +535,14 @@ console_set_winsize(VALUE io, VALUE size)
VALUE row, col, xpixel, ypixel;
const VALUE *sz;
int fd;
int sizelen;
GetOpenFile(io, fptr);
size = rb_Array(size);
rb_check_arity(RARRAY_LENINT(size), 2, 4);
rb_check_arity(sizelen = RARRAY_LENINT(size), 2, 4);
sz = RARRAY_CONST_PTR(size);
row = sz[0], col = sz[1], xpixel = sz[2], ypixel = sz[3];
row = sz[0], col = sz[1], xpixel = ypixel = Qnil;
if (sizelen == 4) xpixel = sz[2], ypixel = sz[3];
fd = GetWriteFD(fptr);
#if defined TIOCSWINSZ
ws.ws_row = ws.ws_col = ws.ws_xpixel = ws.ws_ypixel = 0;

View File

@ -236,11 +236,41 @@ defined?(PTY) and defined?(IO.console) and TestIO_Console.class_eval do
begin
assert_equal([0, 0], s.winsize)
rescue Errno::EINVAL # OpenSolaris 2009.06 TIOCGWINSZ causes Errno::EINVAL before TIOCSWINSZ.
else
assert_equal([80, 25], s.winsize = [80, 25])
assert_equal([80, 25], s.winsize)
assert_equal([80, 25], m.winsize)
assert_equal([100, 40], m.winsize = [100, 40])
assert_equal([100, 40], s.winsize)
assert_equal([100, 40], m.winsize)
end
}
end
def test_set_winsize_invalid_dev
[IO::NULL, __FILE__].each do |path|
open(path) do |io|
begin
s = io.winsize
rescue SystemCallError => e
assert_raise(e.class) {io.winsize = [0, 0]}
else
assert(false, "winsize on #{path} succeed: #{s.inspect}")
end
end
end
end
if IO.console
def test_set_winsize_console
s = IO.console.winsize
assert_kind_of(Array, s)
assert_equal(2, s.size)
assert_kind_of(Integer, s[0])
assert_kind_of(Integer, s[1])
assert_nothing_raised(TypeError) {IO.console.winsize = s}
end
def test_close
IO.console.close
assert_kind_of(IO, IO.console)