Skip to content

Make the repo buildable from a clean checkout (9 fixes) - #1

Open
Largo wants to merge 9 commits into
igravious:feature/ruby-4.0.0-portfrom
Largo:modernize
Open

Make the repo buildable from a clean checkout (9 fixes)#1
Largo wants to merge 9 commits into
igravious:feature/ruby-4.0.0-portfrom
Largo:modernize

Conversation

@Largo

@Largo Largo commented Aug 8, 2026

Copy link
Copy Markdown

Hi — thanks for CosmoRuby. I set out to build it from a fresh clone and hit a series of blockers; this PR is the minimal set of fixes that gets feature/ruby-4.0.0-port building end-to-end from a clean checkout. No Ruby version change, no new features, nothing restructured.

Each commit is one blocker, in the order I hit them:

# Commit Problem
1 Fix bootstrap chicken-and-egg and regenerate missing ruby_shims cosmo_configure.sh --bootstrap fails on the very file the bootstrap exists to produce: local-includes.mk fatally requires it before it can be built. Also, ruby_shims/ (395 mkdeps headers) isn't in the repo, which sends o//depend into an infinite delete/regen loop (1300+ iterations). Added gen_ruby_shims.sh, which regenerates them deterministically from ruby.deps.mk (394/395 resolve).
2 Parallelize cosmo_configure.sh --bootstrap make invocations -j1 was single-threading a large chunk of cosmopolitan libc.
3 Restore accidentally deleted buildlib.a archive rules The archive rules in tool/build/lib/BUILD.mk were dropped in commit bd1ce47, so buildlib.a always built empty → undefined reference to getargs_*.
4 Make parse.c include parse.h via a portable path The committed generated parse.c #includes an absolute path from your machine (/home/groobiest/...). Repointed at the committed parse.h.
5 Allow CARGO override in yjit/BUILD.mk YJIT's cargo detection comes up empty under cocmd and couldn't be overridden; CARGO ?= lets CARGO=/usr/bin/cargo through.
6 Serialize encdb.h/transdb.h generation Both recipes rm -rf the same temp dir, so they race under -j. An order-only dep fixes it — this is, I think, why the docs recommend -j1; -j8 works after this.
7 Use committed config.h as codegen reference docs/reference/_ext_config_ruby_orig_3_4_7.h doesn't exist on any branch; the chain is comparison-only, so it now uses the committed config.h.
8 Fix mtsh compilation and cocmd-incompatible recipe comments mtsh.o/mtsh_embed.o had prerequisites but no compile recipe, and @# recipe comments crash cocmd.
9 Add missing bin/gem launcher script Packaging fails without it; restored the standard RubyGems script.

Verified by building from a clean checkout on Debian 13 (x86-64, cosmocc 3.9.2 as pinned) and running the produced ruby.com: version/platform banner, require of json/digest/zlib/yaml/stringio, TCP loopback, threads, --yjit reporting +YJIT, gem --version, and env -i ./ruby.com from an empty directory. irb.com and miniruby.com build and run too.

Two gotchas I hit that aren't code problems, in case they're worth documenting: plain cosmo_configure.sh (and --bootstrap) silently resets the tree to plugin mode, so --with-static-linked-ext has to be re-passed before building; and make can exit 0 having stopped halfway without linking, so it's worth checking the binary's mtime rather than $?.

I have further work in follow-up branches if any of it is useful to you — a merge with current jart/cosmopolitan master (it was only 16 commits ahead and conflict-free), a Ruby 4.0.0 → 4.0.6 bump, and sqlite3 as a statically linked extension. It's all contained in the main branch. The main aim is to add cosmopolitan support to my OCRAN Project.

Largo and others added 9 commits August 8, 2026 01:32
1. local-includes.mk fatally errored when build/bootstrap/mtdeps was
   missing, even during the 'cosmo_configure.sh --bootstrap' invocation
   whose whole purpose is to build it (make is invoked with the mkdeps
   stub via MKDEPS= on the command line). Skip the check when MKDEPS
   comes from the command line so bootstrap can run on fresh checkouts.

2. ruby.deps.mk references 395 ruby_shims/*.h mkdeps shim files that
   were never committed (they lived only in the original developer's
   working tree, produced by the also-uncommitted bin/create_shims.sh).
   Without them, make's .DEFAULT rule endlessly deletes and regenerates
   o/$(MODE)/depend. Add gen_ruby_shims.sh which deterministically
   rebuilds the shim directory from the entries in ruby.deps.mk.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The bootstrap block hard-coded make -j1, which on a clean checkout means
building a large part of cosmopolitan libc single-threaded. Use
-j$(nproc) by default, overridable via BOOTSTRAP_JOBS for debugging.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Commit bd1ce47 reordered variable definitions in
tool/build/lib/BUILD.mk and dropped the $(TOOL_BUILD_LIB_A): and
$(TOOL_BUILD_LIB_A).pkg: rules in the process. Without prerequisites the
generic archive rule packs an empty buildlib.a, and everything that
links against it (automate_mkdeps, mtdeps, rubyobj, ...) fails with
undefined references to getargs_* et al.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The committed lrama/bison-generated parse.c contained
#include "/home/groobiest/Code/jart/cosmopolitan/o/third_party/ruby/generated/parse.h"
i.e. an absolute path from the original developer's machine, which
breaks compilation on any other checkout. Point it at the committed
third_party/ruby/parse.h instead (same generated header). The ~900
remaining #line directives referencing that path are cosmetic only.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
CARGO was assigned with := from $(shell command -v cargo), which comes
up empty under the cocmd build shell even when cargo is installed, and
could not be overridden from the environment. Use ?= so callers can pass
CARGO=/usr/bin/cargo.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Both recipes invoke ruby_prepare_encdir, which rm -rf's and recopies the
shared $(RUBY_ENC_TMPDIR). Under make -jN they can run concurrently, so
one recipe deletes enc sources while the other is mid-scan, yielding
nondeterministic failures like:

  x_emoji.h:18: ENC_REPLICATE: stateless-ISO-2022-JP is not defined yet.

Make transdb.h order-only depend on encdb.h. This is likely the reason
the docs recommend building Ruby with -j1.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The generated/config.h rule required
docs/reference/_ext_config_ruby_orig_3_4_7.h, a file that exists only in
the original developer's working tree (never committed on any branch),
making the codegen phase fail on fresh checkouts. Substitute the
committed third_party/ruby/include/ruby/config.h; the chain that
consumes it (generated rbconfig.rb, enc.mk, configure-ext.mk, exts.mk)
is comparison-only, so this merely produces empty reference diffs.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
- mtsh.o and mtsh_embed.o rules listed prerequisites but had no compile
  recipe; their sources live in the mtsh/ subdirectory so no pattern
  rule applies, and linking mtsh.com.dbg failed with 'cannot find
  mtsh.o'. Add the same OBJECTIFY.c recipe used by the sibling caboose
  rules.
- ruby.codegen.mk recipes contained '@# comment' lines. Those are only
  harmless when SHELL is mtsh (which exists solely on machines where
  mtsh was previously built); under the default cocmd shell they abort
  with "unsupported syntax '#'". Turn them into make comments.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
assemble_stdlib.sh copies third_party/ruby/bin/gem into the packaged
/zip/bin, but the bin/ directory was never committed. Restore the
standard RubyGems launcher (identical to MRI's bin/gem).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant