Class: Rubycc::Link::CompatRuntime
- Inherits:
-
Object
- Object
- Rubycc::Link::CompatRuntime
- Defined in:
- lib/rubycc/link/compat_runtime.rb
Overview
rubycc's compiler-support runtime: the small set of symbols a CRuby built
by a compiler other than rubycc leaves for the C runtime to supply, and
which rubycc must therefore provide itself the way gcc's driver quietly
links libgcc. It is delivered as an ar archive appended to the tail of
every link so the linker's lazy member extraction pulls a definition in
only when an input actually references it; a link that never mentions one
of these symbols gets none of this code, exactly as if the archive were not
on the command line.
The one member of record is rb_gc_guarded_ptr_val, the target of
RB_GC_GUARD's non-__GNUC__ fallback (ruby/internal/memory.h). Because
rubycc deliberately does not define GNUC (DESIGN R7), CRuby's macro
expands to a call to this function rather than the GNU inline-asm barrier;
yet a gcc-built CRuby, having taken the asm path itself, never exports the
function. The whole contract is to hand the pointer back untouched — the
call is itself the optimization barrier that keeps the guarded VALUE live,
and rubycc performs no optimization that the barrier would need to defeat.
The archive is built by compiling the runtime's own C source with rubycc (a self-host: rubycc compiles its own support code) into an ET_REL object, then wrapping it in a one-member ranlib-indexed archive. Each entry in the source table is one self-contained function so the set can grow a symbol at a time without any member dragging in an unrelated definition.
Constant Summary collapse
- SOURCES =
The runtime's source fragments, keyed by the member name each is archived under. One function per fragment keeps the lazy pull-in surgical: only the fragment defining a referenced symbol is extracted. Compiled PIC because the definitions land in shared objects.
volatileis kept on the parameter and return types so the declaration matches CRuby's own prototype spelling; it qualifies the pointee, not the ABI, so it has no effect on the generated code.valis unused by design — the argument exists only so the call site materializes the guarded value as a real function argument, which is the entire point of the guard. { "rb_gc_guarded_ptr_val" => <<~C /* rubycc compat runtime: definitions CRuby's non-GNUC fallback paths reference. RB_GC_GUARD's fallback calls rb_gc_guarded_ptr_val, which a gcc-built CRuby does not export; returning the pointer unchanged is the whole contract (the call itself is the optimization barrier, and rubycc does not optimize). Pulled in lazily, only when referenced. */ typedef unsigned long __rubycc_VALUE; volatile __rubycc_VALUE *rb_gc_guarded_ptr_val(volatile __rubycc_VALUE *ptr, __rubycc_VALUE val) { return ptr; } C }.freeze
- SOURCE_FILENAME =
A stable synthetic filename for each fragment's diagnostics and file symbol, so a compile error (should the source ever regress) points at the runtime rather than at a user file.
"rubycc_compat_runtime.c"
Class Method Summary collapse
-
.archive_bytes(target: "x86_64") ⇒ Object
The compiler-support runtime as an
ararchive (an ASCII-8BIT String), ready to append to a link's input list.
Class Method Details
.archive_bytes(target: "x86_64") ⇒ Object
The compiler-support runtime as an ar archive (an ASCII-8BIT String),
ready to append to a link's input list. target selects the machine the
fragments are compiled for, so the runtime members match the objects they
are merged with — an aarch64 link must not pull in an x86_64 definition.
Memoized per target: the bytes are deterministic (N4) and their
construction — compiling every fragment — is done once per target per
process.
69 70 71 |
# File 'lib/rubycc/link/compat_runtime.rb', line 69 def archive_bytes(target: "x86_64") (@archive_bytes ||= {})[target] ||= build_archive(target) end |