Bug #9203

fstring_table size and performance

Added by Koichi Sasada 5 months ago. Updated 4 months ago.

[ruby-core:58819]
Status:Closed
Priority:Normal
Assignee:Koichi Sasada
Category:core
Target version:2.1.0
ruby -v:2.1 Backport:1.9.3: UNKNOWN, 2.0.0: UNKNOWN

Description

Clip question discussed on skype.

I have two questions about the following benchmark and result.

(1) why slowdown if seq == true ?
(2) why not GC'ed? (fatal error)

###

require 'benchmark'
a = 0
b = n = 10000000
seq = true

Benchmark.bm{|x|
x.report{
h = {}
(a..b).each{|i|
h[i.tos] = nil
}
}
a, b = b, b+n if seq
x.report{
h = {}
(a..b).each{|i|
h[i.to
s] = nil
}
}
a, b = b, b+n if seq
x.report{
h = {}
(a..b).each{|i|
h[i.to_s] = nil
}
}
}

END
seq == false
ruby 2.1.0dev (2013-12-02 trunk 43956) [i386-mswin32_110]
user system total real
18.720000 0.062000 18.782000 ( 18.854394)
15.460000 0.110000 15.570000 ( 15.569977)
15.366000 0.093000 15.459000 ( 15.481966)

ruby 2.0.0p317 (2013-09-15 revision 42947) [i386-mswin32_110]
user system total real
14.789000 0.094000 14.883000 ( 14.890891)
15.319000 0.078000 15.397000 ( 15.421958)
15.272000 0.078000 15.350000 ( 15.351450)

seq == true
ruby 2.1.0dev (2013-12-02 trunk 43956) [i386-mswin32_110]
user system total real
18.689000 0.187000 18.876000 ( 18.934904)
27.612000 0.250000 27.862000 ( 27.940048)
[FATAL] failed to allocate memory

ruby 2.1.0dev (2013-12-02 trunk 43956) [i686-linux]
user system total real
22.220000 0.400000 22.620000 ( 22.617157)
34.170000 0.130000 34.300000 ( 34.298706)
43.170000 0.110000 43.280000 ( 43.277328)

ruby 2.0.0p317 (2013-09-15 revision 42947) [i386-mswin32_110]
user system total real
14.758000 0.094000 14.852000 ( 14.892891)
15.506000 0.047000 15.553000 ( 15.566477)
15.523000 0.015000 15.538000 ( 15.560976)

History

#1 Updated by Koichi Sasada 5 months ago

To avoid possibility that accidentally marking on machine stack and so on, I use $h instead of local variable h. but same result.

###

require 'benchmark'
a = 0
b = n = 10000000
seq = true

Benchmark.bm{|x|
x.report{
$h = {}
(a..b).each{|i|
$h[i.tos] = nil
}
}
a, b = b, b+n if seq
x.report{
$h = {}
(a..b).each{|i|
$h[i.to
s] = nil
}
}
a, b = b, b+n if seq
x.report{
$h = {}
(a..b).each{|i|
$h[i.to_s] = nil
}
}
}

END
ruby 2.1.0dev (2013-12-02 trunk 43956) [i386-mswin32_110]
user system total real
18.798000 0.234000 19.032000 ( 19.204439)
26.505000 0.406000 26.911000 ( 26.934920)
[FATAL] failed to allocate memory

#2 Updated by Charlie Somerville 5 months ago

It looks like this is a problem with RGenGC.

I can reproduce the performance issue with the script you posted:

λ ./rb x.rb
       user     system      total        real
  16.360000   0.600000  16.960000 ( 16.960314)
  19.370000   0.560000  19.930000 ( 19.938043)
  28.650000   0.780000  29.430000 ( 29.436909)

However if I put GC.start before each x.report line, it fixes the performance issue:

λ ./rb x.rb
       user     system      total        real
  16.650000   0.620000  17.270000 ( 17.263282)
  14.830000   0.280000  15.110000 ( 15.116170)
  14.950000   0.280000  15.230000 ( 15.225395)

#3 Updated by Koichi Sasada 4 months ago

  • Assignee changed from Charlie Somerville to Koichi Sasada

I got it!

So the problem is major marking timing.

#4 Updated by Koichi Sasada 4 months ago

  • Status changed from Open to Closed

I found a bug of GC (Major GC doesn't invoked).
Solved by r44037.

Also available in: Atom PDF