Skip to content
  • Koichi Sasada's avatar
    dd723771
    fastpath for ivar read of FL_EXIVAR objects. · dd723771
    Koichi Sasada authored
    vm_getivar() provides fastpath for T_OBJECT by caching an index
    of ivar. This patch also provides fastpath for FL_EXIVAR objects.
    FL_EXIVAR objects have an each ivar array and index can be cached
    as T_OBJECT. To access this ivar array, generic_iv_tbl is exposed
    by rb_ivar_generic_ivtbl() (declared in variable.h which is newly
    introduced).
    
    Benchmark script:
    
    Benchmark.driver(repeat_count: 3){|x|
      x.executable name: 'clean', command: %w'../clean/miniruby'
      x.executable name: 'trunk', command: %w'./miniruby'
    
      objs = [Object.new, 'str', {a: 1, b: 2}, [1, 2]]
    
      objs.each.with_index{|obj, i|
        rep = obj.inspect
        rep = 'Object.new' if /\#/ =~ rep
        x.prelude str = %Q{
          v#{i} = #{rep}
          def v#{i}.foo
            @iv # ivar access method (attr_reader)
          end
          v#{i}.instance_variable_set(:@iv, :iv)
        }
        puts str
        x.report %Q{
          v#{i}.foo
        }
      }
    }
    
    Result:
    
          v0.foo # T_OBJECT
    
                   clean:  85387141.8 i/s
                   trunk:  85249373.6 i/s - 1.00x  slower
    
          v1.foo # T_STRING
    
                   trunk:  57894407.5 i/s
                   clean:  39957178.6 i/s - 1.45x  slower
    
          v2.foo # T_HASH
    
                   trunk:  56629413.2 i/s
                   clean:  39227088.9 i/s - 1.44x  slower
    
          v3.foo # T_ARRAY
    
                   trunk:  55797530.2 i/s
                   clean:  38263572.9 i/s - 1.46x  slower
    dd723771
    fastpath for ivar read of FL_EXIVAR objects.
    Koichi Sasada authored
    vm_getivar() provides fastpath for T_OBJECT by caching an index
    of ivar. This patch also provides fastpath for FL_EXIVAR objects.
    FL_EXIVAR objects have an each ivar array and index can be cached
    as T_OBJECT. To access this ivar array, generic_iv_tbl is exposed
    by rb_ivar_generic_ivtbl() (declared in variable.h which is newly
    introduced).
    
    Benchmark script:
    
    Benchmark.driver(repeat_count: 3){|x|
      x.executable name: 'clean', command: %w'../clean/miniruby'
      x.executable name: 'trunk', command: %w'./miniruby'
    
      objs = [Object.new, 'str', {a: 1, b: 2}, [1, 2]]
    
      objs.each.with_index{|obj, i|
        rep = obj.inspect
        rep = 'Object.new' if /\#/ =~ rep
        x.prelude str = %Q{
          v#{i} = #{rep}
          def v#{i}.foo
            @iv # ivar access method (attr_reader)
          end
          v#{i}.instance_variable_set(:@iv, :iv)
        }
        puts str
        x.report %Q{
          v#{i}.foo
        }
      }
    }
    
    Result:
    
          v0.foo # T_OBJECT
    
                   clean:  85387141.8 i/s
                   trunk:  85249373.6 i/s - 1.00x  slower
    
          v1.foo # T_STRING
    
                   trunk:  57894407.5 i/s
                   clean:  39957178.6 i/s - 1.45x  slower
    
          v2.foo # T_HASH
    
                   trunk:  56629413.2 i/s
                   clean:  39227088.9 i/s - 1.44x  slower
    
          v3.foo # T_ARRAY
    
                   trunk:  55797530.2 i/s
                   clean:  38263572.9 i/s - 1.46x  slower
Loading