[pull] master from ruby:master - #1256
Merged
Merged
Conversation
I benchmarked various values of STR_DUPLICATE_MAX_EMBED_LEN and the
performance impacts. For String#dup, creating a view is faster until it
is below 256 bytes. Unsurprisingly, if we add modification to the string,
then it is faster to eagerly create a copy than use a view. Surprisingly,
if we append to the string, it's still faster to go from embedded -> extended
than shared -> extended. However, both of these cases will incur a memory
penalty as the remainder of the slot is wasted memory.
Benchmark:
require "benchmark"
TIMES = 10_000_000
Benchmark.bm do |x|
[64, 128, 256, 512, 1024].each do |len|
len -= 25 # Subtract header length
x.report("String#dup for #{len.to_s}") do
pid = fork do
str = ("a" * len).freeze
i = 0
while i < TIMES
str.dup
i += 1
end
end
Process.wait(pid)
end
x.report("String#dup + String#[]= for #{len.to_s}") do
pid = fork do
str = ("a" * len).freeze
i = 0
while i < TIMES
dup = str.dup
dup[0] = "1"
i += 1
end
end
Process.wait(pid)
end
x.report("String#dup + String#<< for #{len.to_s}") do
pid = fork do
str = ("a" * len).freeze
i = 0
while i < TIMES
dup = str.dup
dup << "1"
i += 1
end
end
Process.wait(pid)
end
end
end
Result:
1024
user system total real
String#dup for 39 0.000085 0.000646 0.207714 ( 0.208041)
String#dup + String#[]= for 39 0.000067 0.000379 0.499957 ( 0.500514)
String#dup + String#<< for 39 0.000069 0.000413 0.600205 ( 0.600984)
String#dup for 103 0.000068 0.000374 0.236938 ( 0.237424)
String#dup + String#[]= for 103 0.000063 0.000401 0.501791 ( 0.502506)
String#dup + String#<< for 103 0.000066 0.000395 0.600041 ( 0.600870)
String#dup for 231 0.000066 0.000370 0.281924 ( 0.282409)
String#dup + String#[]= for 231 0.000064 0.000355 0.574779 ( 0.575599)
String#dup + String#<< for 231 0.000070 0.000395 0.691011 ( 0.691972)
String#dup for 487 0.000070 0.000366 0.355631 ( 0.356230)
String#dup + String#[]= for 487 0.000067 0.000391 0.653774 ( 0.654509)
String#dup + String#<< for 487 0.000066 0.000359 0.891413 ( 0.892607)
String#dup for 999 0.000068 0.000394 0.527350 ( 0.528033)
String#dup + String#[]= for 999 0.000067 0.000378 0.786794 ( 0.787682)
String#dup + String#<< for 999 0.000063 0.000363 1.070604 ( 1.071885)
512
user system total real
String#dup for 39 0.000083 0.000639 0.207305 ( 0.207687)
String#dup + String#[]= for 39 0.000067 0.000398 0.501968 ( 0.502645)
String#dup + String#<< for 39 0.000071 0.000414 0.586533 ( 0.587365)
String#dup for 103 0.000064 0.000397 0.222104 ( 0.222600)
String#dup + String#[]= for 103 0.000069 0.000389 0.483612 ( 0.484240)
String#dup + String#<< for 103 0.000069 0.000380 0.606659 ( 0.607510)
String#dup for 231 0.000067 0.000388 0.292563 ( 0.293070)
String#dup + String#[]= for 231 0.000064 0.000389 0.573774 ( 0.574479)
String#dup + String#<< for 231 0.000069 0.000413 0.739569 ( 0.740614)
String#dup for 487 0.000067 0.000419 0.370516 ( 0.371072)
String#dup + String#[]= for 487 0.000060 0.000337 0.676507 ( 0.677282)
String#dup + String#<< for 487 0.000074 0.000410 0.911670 ( 0.916480)
String#dup for 999 0.000069 0.000397 0.239633 ( 0.240049)
String#dup + String#[]= for 999 0.000066 0.000370 1.196397 ( 1.198272)
String#dup + String#<< for 999 0.000072 0.000396 1.683562 ( 1.686244)
256
user system total real
String#dup for 39 0.000073 0.000588 0.198103 ( 0.198485)
String#dup + String#[]= for 39 0.000067 0.000397 0.475345 ( 0.476011)
String#dup + String#<< for 39 0.000074 0.000408 0.589001 ( 0.589778)
String#dup for 103 0.000073 0.000420 0.244381 ( 0.244818)
String#dup + String#[]= for 103 0.000065 0.000421 0.480720 ( 0.481569)
String#dup + String#<< for 103 0.000070 0.000414 0.589164 ( 0.590123)
String#dup for 231 0.000077 0.000447 0.272169 ( 0.272640)
String#dup + String#[]= for 231 0.000067 0.000425 0.517280 ( 0.518037)
String#dup + String#<< for 231 0.000064 0.000409 0.681593 ( 0.682572)
String#dup for 487 0.000065 0.000390 0.229708 ( 0.230153)
String#dup + String#[]= for 487 0.000067 0.000395 0.872966 ( 0.874233)
String#dup + String#<< for 487 0.000071 0.000411 1.317758 ( 1.320085)
String#dup for 999 0.000070 0.000397 0.255197 ( 0.255609)
String#dup + String#[]= for 999 0.000068 0.000380 1.174781 ( 1.176700)
String#dup + String#<< for 999 0.000067 0.000389 1.729608 ( 1.738797)
128
user system total real
String#dup for 39 0.000105 0.000950 0.205384 ( 0.206565)
String#dup + String#[]= for 39 0.000066 0.000406 0.483924 ( 0.485308)
String#dup + String#<< for 39 0.000075 0.000433 0.590150 ( 0.591641)
String#dup for 103 0.000076 0.000414 0.225900 ( 0.227975)
String#dup + String#[]= for 103 0.000098 0.000604 0.499234 ( 0.503926)
String#dup + String#<< for 103 0.000070 0.000400 0.619562 ( 0.627411)
String#dup for 231 0.000073 0.000445 0.241433 ( 0.243606)
String#dup + String#[]= for 231 0.000067 0.000402 0.843665 ( 0.853293)
String#dup + String#<< for 231 0.000071 0.000392 0.990903 ( 0.994555)
String#dup for 487 0.000073 0.000403 0.234920 ( 0.236132)
String#dup + String#[]= for 487 0.000077 0.000445 0.944582 ( 0.956001)
String#dup + String#<< for 487 0.000069 0.000410 1.337099 ( 1.341250)
String#dup for 999 0.000072 0.000420 0.233520 ( 0.234182)
String#dup + String#[]= for 999 0.000072 0.000419 1.186288 ( 1.188972)
String#dup + String#<< for 999 0.000069 0.000436 1.685112 ( 1.689536)
Ractor::Port has a public allocator, so Ractor::Port.allocate returns a port whose owner Ractor is still NULL; only ractor_port_init() fills it in. The methods dereferenced it unchecked: Ractor::Port.allocate.closed? # [BUG] Segmentation fault at 0x60 Route the paths reachable from Ruby through ractor_port_ptr_check(), which raises TypeError as other uninitialized typed data objects do. The self of #initialize_copy keeps the unchecked accessor because it is legitimately uninitialized there; only orig is checked. Ractor.select did not crash, but such a port has id 0, the same as the current Ractor's default port, so it took messages from it. Port#closed? also loses Primitive.attr! :leaf. It can raise now, and it was not a leaf before either, since the foreign Ractor path takes RACTOR_LOCK(). [Bug #22214]
* ZJIT: Fix trivial inlining for optional argument entries Use SendDirect's jit_entry_idx when reading the callee bytecode for trivial inlining, so optional-argument calls inspect the same entry point that SendDirect selected. This avoids inlining default-argument initialization code when the caller actually provided the optional positional argument. * ZJIT: Require trivial inline target to end at leave Limit the trivial inliner to whole-ISEQ shapes that start at bytecode index 0 and end with the second instruction's leave. Optional argument entries can start in the middle of the ISEQ, so keep those SendDirect calls for the general inliner, which handles jit_entry_idx. This avoids folding default-argument initialization code when the caller actually supplied the optional positional argument. Co-authored-by: Takashi Kokubun (k0kubun) <takashikkbn@gmail.com> Co-authored-by: Alan Wu <XrXr@users.noreply.github.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to subscribe to this conversation on GitHub.
Already have an account?
Sign in.
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
See Commits and Changes for more details.
Created by
pull[bot] (v2.0.0-alpha.4)
Can you help keep this open source service alive? 💖 Please sponsor : )