Speedup test_shape.rb
Many tests start by exhausting all shapes, which is a slow process. By exposing a method to directly move the bump allocator forward we cut test runtime in half. Before: ``` Finished tests in 1.544756s ``` After: ``` Finished tests in 0.759733s, ```
This commit is contained in:
parent
0745c0c5ef
commit
2d7fb9c2fa
10
shape.c
10
shape.c
@ -1057,6 +1057,15 @@ rb_shape_shapes_available(VALUE self)
|
||||
return INT2NUM(MAX_SHAPE_ID - (GET_SHAPE_TREE()->next_shape_id - 1));
|
||||
}
|
||||
|
||||
static VALUE
|
||||
rb_shape_exhaust(int argc, VALUE *argv, VALUE self)
|
||||
{
|
||||
rb_check_arity(argc, 0, 1);
|
||||
int offset = argc == 1 ? NUM2INT(argv[0]) : 0;
|
||||
GET_SHAPE_TREE()->next_shape_id = MAX_SHAPE_ID - offset;
|
||||
return Qnil;
|
||||
}
|
||||
|
||||
VALUE rb_obj_shape(rb_shape_t* shape);
|
||||
|
||||
static enum rb_id_table_iterator_result collect_keys_and_values(ID key, VALUE value, void *ref)
|
||||
@ -1239,5 +1248,6 @@ Init_shape(void)
|
||||
rb_define_singleton_method(rb_cShape, "of", rb_shape_debug_shape, 1);
|
||||
rb_define_singleton_method(rb_cShape, "root_shape", rb_shape_root_shape, 0);
|
||||
rb_define_singleton_method(rb_cShape, "shapes_available", rb_shape_shapes_available, 0);
|
||||
rb_define_singleton_method(rb_cShape, "exhaust_shapes", rb_shape_exhaust, -1);
|
||||
#endif
|
||||
}
|
||||
|
@ -191,12 +191,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
attr_reader :very_unique
|
||||
end
|
||||
|
||||
obj = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
obj.instance_variable_set(:"@a#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
(RubyVM::Shape::SHAPE_MAX_VARIATIONS * 2).times do
|
||||
TooComplex.new.instance_variable_set(:"@unique_#{_1}", 1)
|
||||
@ -216,13 +211,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
assert_separately([], "#{<<~"begin;"}\n#{<<~'end;'}")
|
||||
begin;
|
||||
class Hi; end
|
||||
|
||||
obj = Hi.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 2
|
||||
obj.instance_variable_set(:"@a#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes(3)
|
||||
|
||||
obj = Hi.new
|
||||
i = 0
|
||||
@ -243,26 +232,16 @@ class TestShapes < Test::Unit::TestCase
|
||||
@a = 1
|
||||
end
|
||||
end
|
||||
# Try to run out of shapes
|
||||
o = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
A.new
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
A.new
|
||||
end;
|
||||
end
|
||||
|
||||
def test_run_out_of_shape_for_class_ivar
|
||||
assert_separately([], "#{<<~"begin;"}\n#{<<~'end;'}")
|
||||
begin;
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
c = Class.new
|
||||
c.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
c = Class.new
|
||||
c.instance_variable_set(:@a, 1)
|
||||
@ -282,12 +261,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
begin;
|
||||
[].instance_variable_set(:@a, 1)
|
||||
|
||||
i = 0
|
||||
o = Object.new
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
ary = 10.times.map { [] }
|
||||
|
||||
@ -302,12 +276,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
def test_run_out_of_shape_for_module_ivar
|
||||
assert_separately([], "#{<<~"begin;"}\n#{<<~'end;'}")
|
||||
begin;
|
||||
o = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
module Foo
|
||||
@a = 1
|
||||
@ -321,12 +290,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
def test_run_out_of_shape_for_class_cvar
|
||||
assert_separately([], "#{<<~"begin;"}\n#{<<~'end;'}")
|
||||
begin;
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
c = Class.new
|
||||
c.class_variable_set(:"@@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
c = Class.new
|
||||
|
||||
@ -348,13 +312,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
class TooComplex < Hash
|
||||
end
|
||||
|
||||
# Try to run out of shapes
|
||||
o = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
tc = TooComplex.new
|
||||
tc.instance_variable_set(:@a, 1)
|
||||
@ -387,15 +345,10 @@ class TestShapes < Test::Unit::TestCase
|
||||
a = Hi.new
|
||||
|
||||
# Try to run out of shapes
|
||||
o = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
assert_equal 1,a.transition
|
||||
assert_equal 1,a.transition
|
||||
assert_equal 1, a.transition
|
||||
assert_equal 1, a.transition
|
||||
end;
|
||||
end
|
||||
|
||||
@ -409,12 +362,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
end
|
||||
end
|
||||
|
||||
o = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
a = A.new
|
||||
assert_equal true, a.instance_variable_defined?(:@a)
|
||||
@ -424,12 +372,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
def test_run_out_of_shape_instance_variable_defined_on_module
|
||||
assert_separately([], "#{<<~"begin;"}\n#{<<~'end;'}")
|
||||
begin;
|
||||
o = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
module A
|
||||
@a = @b = @c = @d = 1
|
||||
@ -445,12 +388,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
o = Object.new
|
||||
10.times { |i| o.instance_variable_set(:"@a#{i}", i) }
|
||||
|
||||
i = 0
|
||||
a = Object.new
|
||||
while RubyVM::Shape.shapes_available > 2
|
||||
a.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
o.remove_instance_variable(:@a0)
|
||||
(1...10).each do |i|
|
||||
@ -471,12 +409,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
|
||||
a = A.new
|
||||
|
||||
o = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
a.remove_instance_variable(:@b)
|
||||
assert_nil a.b
|
||||
@ -506,12 +439,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
|
||||
a = A.new
|
||||
|
||||
o = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 1
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
a.dup
|
||||
end;
|
||||
@ -522,12 +450,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
o = []
|
||||
o.instance_variable_set(:@a, 1)
|
||||
|
||||
i = 0
|
||||
o = Object.new
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
ary = 1_000_000.times.map { [] }
|
||||
begin;
|
||||
@ -546,12 +469,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
begin;
|
||||
class Hi; end
|
||||
|
||||
obj = Hi.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 2
|
||||
obj.instance_variable_set(:"@a#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes(2)
|
||||
|
||||
obj = Module.new
|
||||
3.times do
|
||||
@ -571,12 +489,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
begin;
|
||||
class Hi; end
|
||||
|
||||
obj = Hi.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 2
|
||||
obj.instance_variable_set(:"@a#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes(2)
|
||||
|
||||
obj = Object.new
|
||||
i = 0
|
||||
@ -748,12 +661,7 @@ class TestShapes < Test::Unit::TestCase
|
||||
end
|
||||
assert_equal [0, 1, 2, 3, 4], ivars
|
||||
|
||||
o = Object.new
|
||||
i = 0
|
||||
while RubyVM::Shape.shapes_available > 0
|
||||
o.instance_variable_set(:"@i#{i}", 1)
|
||||
i += 1
|
||||
end
|
||||
RubyVM::Shape.exhaust_shapes
|
||||
|
||||
object.remove_instance_variable(:@ivar_2)
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user