mirror of
https://github.com/ruby/ruby.git
synced 2022-11-09 12:17:21 -05:00
Fix tests for CVE-2018-6914
Since the current working directory is not involved in `Tempfile` and `Dir.mktmpdir` (except for the last resort), it is incorrect to derive the traversal path from it. Also, since the rubyspec temporary directory is created under the build directory, this is not involved in the target method. Fixed sporadic errors in test-spec.
This commit is contained in:
parent
ad4da86669
commit
fee5cde00b
3 changed files with 64 additions and 72 deletions
|
@ -5,56 +5,51 @@ require 'tmpdir'
|
|||
|
||||
describe "CVE-2018-6914 is resisted by" do
|
||||
before :each do
|
||||
@tmpdir = ENV['TMPDIR']
|
||||
@dir = tmp("CVE-2018-6914")
|
||||
Dir.mkdir(@dir)
|
||||
touch "#{@dir}/bar"
|
||||
|
||||
@traversal_path = Array.new(@dir.count('/'), '..').join('/') + @dir + '/'
|
||||
@traversal_path.delete!(':') if platform_is(:windows)
|
||||
ENV['TMPDIR'] = @dir
|
||||
@dir << '/'
|
||||
|
||||
@tempfile = nil
|
||||
end
|
||||
|
||||
after :each do
|
||||
ENV['TMPDIR'] = @tmpdir
|
||||
@tempfile.close! if @tempfile
|
||||
rm_r @dir
|
||||
end
|
||||
|
||||
it "Tempfile.open by deleting separators" do
|
||||
expect = Dir.glob(@traversal_path + '*').size
|
||||
@tempfile = Tempfile.open([@traversal_path, 'foo'])
|
||||
actual = Dir.glob(@traversal_path + '*').size
|
||||
actual.should == expect
|
||||
@tempfile = Tempfile.open(['../', 'foo'])
|
||||
actual = @tempfile.path
|
||||
File.absolute_path(actual).should.start_with?(@dir)
|
||||
end
|
||||
|
||||
it "Tempfile.new by deleting separators" do
|
||||
expect = Dir.glob(@traversal_path + '*').size
|
||||
@tempfile = Tempfile.new(@traversal_path + 'foo')
|
||||
actual = Dir.glob(@traversal_path + '*').size
|
||||
actual.should == expect
|
||||
@tempfile = Tempfile.new('../foo')
|
||||
actual = @tempfile.path
|
||||
File.absolute_path(actual).should.start_with?(@dir)
|
||||
end
|
||||
|
||||
it "Tempfile.create by deleting separators" do
|
||||
expect = Dir.glob(@traversal_path + '*').size
|
||||
Tempfile.create(@traversal_path + 'foo') do
|
||||
actual = Dir.glob(@traversal_path + '*').size
|
||||
actual.should == expect
|
||||
actual = Tempfile.create('../foo') do |t|
|
||||
t.path
|
||||
end
|
||||
File.absolute_path(actual).should.start_with?(@dir)
|
||||
end
|
||||
|
||||
it "Dir.mktmpdir by deleting separators" do
|
||||
expect = Dir.glob(@traversal_path + '*').size
|
||||
Dir.mktmpdir(@traversal_path + 'foo') do
|
||||
actual = Dir.glob(@traversal_path + '*').size
|
||||
actual.should == expect
|
||||
actual = Dir.mktmpdir('../foo') do |path|
|
||||
path
|
||||
end
|
||||
File.absolute_path(actual).should.start_with?(@dir)
|
||||
end
|
||||
|
||||
it "Dir.mktmpdir with an array by deleting separators" do
|
||||
expect = Dir.glob(@traversal_path + '*').size
|
||||
Dir.mktmpdir([@traversal_path, 'foo']) do
|
||||
actual = Dir.glob(@traversal_path + '*').size
|
||||
actual.should == expect
|
||||
actual = Dir.mktmpdir(['../', 'foo']) do |path|
|
||||
path
|
||||
end
|
||||
File.absolute_path(actual).should.start_with?(@dir)
|
||||
end
|
||||
end
|
||||
|
|
|
@ -374,53 +374,43 @@ puts Tempfile.new('foo').path
|
|||
assert_file.not_exist?(path)
|
||||
end
|
||||
|
||||
TRAVERSAL_PATH = Array.new(Dir.pwd.split('/').count, '..').join('/') + Dir.pwd + '/'
|
||||
|
||||
def test_open_traversal_dir
|
||||
expect = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
t = Tempfile.open([TRAVERSAL_PATH, 'foo'])
|
||||
actual = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
assert_equal expect, actual
|
||||
rescue Errno::EINVAL
|
||||
if /mswin|mingw/ =~ RUBY_PLATFORM
|
||||
assert "ok"
|
||||
else
|
||||
raise $!
|
||||
end
|
||||
assert_mktmpdir_traversal do |traversal_path|
|
||||
t = Tempfile.open([traversal_path, 'foo'])
|
||||
t.path
|
||||
ensure
|
||||
t&.close!
|
||||
end
|
||||
end
|
||||
|
||||
def test_new_traversal_dir
|
||||
expect = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
t = Tempfile.new(TRAVERSAL_PATH + 'foo')
|
||||
actual = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
assert_equal expect, actual
|
||||
rescue Errno::EINVAL
|
||||
if /mswin|mingw/ =~ RUBY_PLATFORM
|
||||
assert "ok"
|
||||
else
|
||||
raise $!
|
||||
end
|
||||
assert_mktmpdir_traversal do |traversal_path|
|
||||
t = Tempfile.new(traversal_path + 'foo')
|
||||
t.path
|
||||
ensure
|
||||
t&.close!
|
||||
end
|
||||
end
|
||||
|
||||
def test_create_traversal_dir
|
||||
expect = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
t = Tempfile.create(TRAVERSAL_PATH + 'foo')
|
||||
actual = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
assert_equal expect, actual
|
||||
rescue Errno::EINVAL
|
||||
if /mswin|mingw/ =~ RUBY_PLATFORM
|
||||
assert "ok"
|
||||
else
|
||||
raise $!
|
||||
end
|
||||
assert_mktmpdir_traversal do |traversal_path|
|
||||
t = Tempfile.create(traversal_path + 'foo')
|
||||
t.path
|
||||
ensure
|
||||
if t
|
||||
t.close
|
||||
File.unlink(t.path)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def assert_mktmpdir_traversal
|
||||
Dir.mktmpdir do |target|
|
||||
target = target.chomp('/') + '/'
|
||||
traversal_path = target.sub(/\A\w:/, '') # for DOSISH
|
||||
traversal_path = Array.new(target.count('/')-2, '..').join('/') + traversal_path
|
||||
actual = yield traversal_path
|
||||
assert_not_send([File.absolute_path(actual), :start_with?, target])
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -65,22 +65,29 @@ class TestTmpdir < Test::Unit::TestCase
|
|||
}
|
||||
end
|
||||
|
||||
TRAVERSAL_PATH = Array.new(Dir.pwd.split('/').count, '..').join('/') + Dir.pwd + '/'
|
||||
TRAVERSAL_PATH.delete!(':') if /mswin|mingw/ =~ RUBY_PLATFORM
|
||||
|
||||
def test_mktmpdir_traversal
|
||||
expect = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
Dir.mktmpdir(TRAVERSAL_PATH + 'foo') do
|
||||
actual = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
assert_equal expect, actual
|
||||
assert_mktmpdir_traversal do |traversal_path|
|
||||
Dir.mktmpdir(traversal_path + 'foo') do |actual|
|
||||
actual
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def test_mktmpdir_traversal_array
|
||||
expect = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
Dir.mktmpdir([TRAVERSAL_PATH, 'foo']) do
|
||||
actual = Dir.glob(TRAVERSAL_PATH + '*').count
|
||||
assert_equal expect, actual
|
||||
assert_mktmpdir_traversal do |traversal_path|
|
||||
Dir.mktmpdir([traversal_path, 'foo']) do |actual|
|
||||
actual
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def assert_mktmpdir_traversal
|
||||
Dir.mktmpdir do |target|
|
||||
target = target.chomp('/') + '/'
|
||||
traversal_path = target.sub(/\A\w:/, '') # for DOSISH
|
||||
traversal_path = Array.new(target.count('/')-2, '..').join('/') + traversal_path
|
||||
actual = yield traversal_path
|
||||
assert_not_send([File.absolute_path(actual), :start_with?, target])
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
Loading…
Add table
Reference in a new issue