A non-String executable name or bindir previously raised TypeError from
File.basename or File.join. Guard the type so verify_spec raises
Gem::InstallError instead of aborting with an unexpected exception.
https://github.com/ruby/rubygems/commit/89bf13a11b
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Escape the executable name interpolated into the generated wrapper so a
name containing quotes cannot change the generated Ruby.
https://github.com/ruby/rubygems/commit/9f32631b77
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Reject a bindir that resolves outside the gem directory during pre-install
checks.
https://github.com/ruby/rubygems/commit/cd61a78b25
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
post_install_message may be a non-String such as an array, so call to_s
before clean_text to avoid raising during install.
https://github.com/ruby/rubygems/commit/95b6bfbd16
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Reword the comment to explain that the UTF-8 guard avoids splitting
multibyte sequences, and assert preservation with U+0400, whose
continuation byte falls in the C1 byte range.
https://github.com/ruby/rubygems/commit/0db489ff2e
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Route the post-install message through Gem::Text#clean_text before
printing it so a crafted message cannot emit raw terminal control
sequences.
https://github.com/ruby/rubygems/commit/cc62ee89ab
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Match C1 controls (U+0080-U+009F) as codepoints and only for valid UTF-8
text, so multibyte characters are preserved and other encodings are left
unchanged.
https://github.com/ruby/rubygems/commit/c272a8b138
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
As opposed to a recursive loop. We do this by keeping a stack of
frames (very similar to how the stack of values was already
stored). Each frame represents the state of a container. Since
there are only 2 in JSON, it doesn't have to get too complex.
Each frame in the iterative parser now holds an enum describing
its "phase", in order to support suspending parsing.
For performance to be on par with the previous implementation,
we directly jump to the proper handler in most cases.
`JSON_ParserState.stack` was renamed into `.value_stack`,
as with the introduction of the frames stack, the naming became
confusing.
https://github.com/ruby/json/commit/a760d9ae9b
Co-Authored-By: Jean Boussier <jean.boussier@gmail.com>
Guards against accidentally reintroducing the removed external tool
version output.
https://github.com/ruby/rubygems/commit/3060a5498a
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Keeping up with each version manager's invocation convention is not
worth the maintenance cost. chruby in particular is wrapped as a shell
function and cannot be run as `chruby --version` at all, so the line
always reported a missing version.
https://github.com/ruby/rubygems/issues/9528https://github.com/ruby/rubygems/commit/85cb212067
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
The inline `# zizmor: ignore[artipacked]` comment is a second trailing
comment on the checkout line, which prevents Dependabot from updating the
version comment. Suppress these findings in .github/zizmor.yml instead so
the pins stay a single comment and Dependabot keeps them in sync.
Dependabot left the version comment as v6.0.2 on the four lines that
carry a trailing `# zizmor: ignore[artipacked]`, since its comment
rewriter only handles a version comment as the last token on the line.
zizmor flagged the resulting hash/comment mismatch. Update every
checkout pin in .github to the v6.0.3 commit and comment at once.
This saves ~115KiB of code on lobsters but mostly it's just a common-sense thing I've been meaning to do for a while.
I have also thought about splitting up `GuardType` into different kinds of guards but I like the HIR uniformity.
Before:
```
ZJIT stats:
code_region_bytes: 15,630,336
zjit_alloc_bytes: 19,423,844
compile_time 1509.19ms
profile_time 22.26ms
gc_time 19.16ms
invalidation_time 6.28ms
```
After:
```
ZJIT stats:
code_region_bytes: 15,515,648
zjit_alloc_bytes: 19,333,088
compile_time 1535.77ms
profile_time 22.61ms
gc_time 16.83ms
invalidation_time 6.50ms
```
The new spec was unassigned, so the shard-based CI jobs would skip it and
spec_helper would warn. Add it to shard_d per the file's guidance.
https://github.com/ruby/rubygems/commit/35a0782cd2
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Define SplitCompactIndexEntryOnFirstColon unconditionally so it can be
exercised on any RubyGems, prepending it only when the host RubyGems still
splits compact index entries on every colon. Mark the override private to
preserve the visibility of the original Gem::Resolver::APISet::GemParser
method, and add a spec covering the colon-preserving behavior.
https://github.com/ruby/rubygems/commit/d6af5c724d
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Bundler delegates compact index parsing to the host RubyGems'
Gem::Resolver::APISet::GemParser. Before RubyGems 4.0.13 that splits each
entry on every colon, mangling metadata values that contain colons such as
the `created_at` timestamps the cooldown feature reads, so cooldown silently
stops filtering when Bundler runs on an older RubyGems. Shim parse_dependency
to split only on the first colon in that case.
https://github.com/ruby/rubygems/commit/f3a3bda98e
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Useful for adding comments to HIR/LIR/disasm that are not specific to an instruction.
Possibly most useful for temporarily printing more information
while debugging by keeping the statements interleaved with the HIR.
With a local change like this
diff --git a/zjit/src/hir.rs b/zjit/src/hir.rs
index bff384fa65..de5b41caa1 100644
--- a/zjit/src/hir.rs
+++ b/zjit/src/hir.rs
@@ -2491,6 +2491,8 @@ fn type_specialize(&mut self) {
cme = unsafe { rb_aliased_callable_method_entry(cme) };
def_type = unsafe { get_cme_def_type(cme) };
}
+ eprintln!("WTH");
+ hir_comment!(self, block, "HOWDY def_type {:?}", def_type);
if def_type == VM_METHOD_TYPE_ISEQ {
// TODO(max): Allow non-iseq; cache cme
// Only specialize positional-positional calls
The print statement (1) shows up early (anywhere)
whereas the HIR comment (2) is interleaved with the rest of
the HIR so you can easily correlate debug info to the compilation of
whatever function you are observing:
1. WTH
Optimized HIR:
fn test@test.rb:2:
bb0():
EntryPoint interpreter
v1:BasicObject = LoadSelf
Jump bb2(v1)
bb1(v4:BasicObject):
EntryPoint JIT(0)
Jump bb2(v4)
bb2(v6:BasicObject):
v11:Fixnum[1] = Const Value(1)
2. # HOWDY def_type 0
PatchPoint MethodRedefined(Object@0x10184ed10, foo@0x9c01, cme:0x101967060)
The comments show up in HIR, LIR, and disasm:
bb2(v6:BasicObject):
v11:Fixnum[1] = Const Value(1)
# HOWDY def_type 0
PatchPoint MethodRedefined(Object@0x1220fed10, foo@0x9c01, cme:0x123717060)
--
PatchPoint Exit(PatchPoint(NoTracePoint))
# Insn: v11 Const Value(1)
# Insn: v18 # HOWDY def_type 0
# Insn: v19 PatchPoint MethodRedefined(Object@0x103aaed00, foo@0x9c01, cme:0x103bc7080)
PatchPoint Exit(PatchPoint(MethodRedefined(Object@0x103aaed00, foo@0x9c01, cme:0x103bc7080)))
--
0x1230bc0f0: nop
# Insn: v11 Const Value(1)
# Insn: v18 # HOWDY def_type 0
# Insn: v19 PatchPoint MethodRedefined(Object@0x103c6ed20, foo@0x9c01, cme:0x103d87070)
0x1230bc0f4: nop
If the ISEQ we're compiling is a `ISEQ_TYPE_METHOD` and it's defined on a
class that no immediate object's class inherits from (exclude
`BasicObject`, `Object`, `Numeric`, etc), and the allocator is the
default allocator, then we can assume the `self` is heap-allocated.
This lets us skip HeapBasicObject guards for a lot of instance variable
lookups, for example:
```ruby
class C
def foo = @foo
end
```
Thanks to @jhawthorn for the idea and @tenderlove for convincing me it was reasonable.
`FIXNUM_MIN / -1` overflows to a `Bignum` rather than a `Fixnum`, so type it as returning an `Integer` rather than `Fixnum`. Users that expect a `Fixnum` can guard to narrow the result back to `Fixnum`.
Closes: https://github.com/Shopify/ruby/issues/990
When version and platform match across sources, prefer the earlier
source. This formalises existing behaviour and matches Bundler.
Cross-version selection is unchanged.
https://github.com/ruby/rubygems/commit/8f2cd72650