Building Q+ from Source
This document describes the standalone build, the self-hosting step, the regression suite, and how to troubleshoot a build that does not match the expected artifacts.
Requirements
- Linux x86-64 (the validated platform; other platforms are not tested in this release)
gcc(GCC 8 or newer is recommended; the build uses-ffile-prefix-map)bashand standard coreutils (sha256sum,mktemp,mv)- GNU
makeis not required
No system libraries beyond the C standard library are needed. tools/build.sh uses gcc by default and honors the CC environment variable, so a compatible C compiler can be selected when needed.
Quick build
From the repository root:
tools/build.sh
The script produces:
build/bqvmsha256ca0539df3190874eadae942cc1a1166bc0213475abbf146469e42eff17ee79a0(traceback/行表版;u64 bitwise opcodes)build/qboot.qbcsha256abd9fb8341a23efcb86d0b073331cd2e1247d920a33ee7b0108ff28f908d0d63(u64 bitwise TC/gen)
Both artifacts are executable directly; no installation step is required. tools/build.sh also accepts an optional output directory:
tools/build.sh <tmp>/qplus-build
What the build does
tools/build.sh runs four stages: VM build, two-step self-host compiler, AOT toolchain rebuild (verified against the shipped fixed point), and a small-heap helper VM.
- Build the VM. It compiles the C sources of
bqvmand its minimal runtime (insrc/runtime/bootstrap_qvm/andsrc/runtime/mini_kernel/) intobuild/bqvm. The compiler flags include-ffile-prefix-mapand-fmacro-prefix-map, which remove the absolute path of the source tree, so a build from any directory produces the same binary for the same C toolchain. - Self-host the compiler. The freshly built
build/bqvmrunsbootstrap/qboot.qbcon the compiler sourcesrc/compiler/qboot/qboot_v52_final3_fix2.qand writesbuild/qboot.qbc. The bootstrap bytecode compiles the compiler; the output is the compiler.
The script prints the two artifact paths and their SHA-256 checksums on success:
[Q+ build] bqvm=<outdir>/bqvm qboot=<outdir>/qboot.qbc
<sha256> <outdir>/bqvm
<sha256> <outdir>/qboot.qbc
Expected hashes
For Q+ 1.19.0-dev, a clean build with the reference toolchain produces:
| Artifact | SHA-256 |
|---|---|
build/bqvm | 3c04689aa3bb04401b8a2e31f0305466c02fccd55bf2cbe3a39104752698d34ffaf6db53cfad4b3b4f225e21821cda835c72e699a92f6d5228fb973d |
build/bqvm_small | a362904d11ff1100b8c201302e026847ba6ab3f7ec2dc640636d0122c3625dc5d8a55cde396bee4ba42bd53f5ada85af66ae98362459e1558639fe62 |
build/qboot.qbc | 44c21db965319cd87c2ca6d83c683e316eadafdee52cbdd2ad04af3e83cf100b |
build/cgtest.qbc | 4d620b1fcb395a1e81591766e199e2a3542246860e8d2471e8f54e1c152396cd |
build/cgtest_aot | 9518f9c4a68e57ac4994d70d03c157e984919b46b6e3597903116ea0d8e93fc2 |
bootstrap/qboot.qbc | 44c21db965319cd87c2ca6d83c683e316eadafdee52cbdd2ad04af3e83cf100b (seed = built qboot) |
bootstrap/cgtest_aot | 9518f9c4a68e57ac4994d70d03c157e984919b46b6e3597903116ea0d8e93fc2 (AOT fixed point) |
bootstrap/stage0.q sha256 7a954aa542678d2d44e5e239e600c712c20fe974510c57809d45595036713aab. bootstrap/SHA256SUMS is kept in sync. Reproducibility signals: build/qboot.qbc == bootstrap/qboot.qbc, and build/cgtest_aot == bootstrap/cgtest_aot (AOT fixed point).
Build from scratch
The build does not require an existing build/ directory. To force a clean build:
rm -rf build
tools/build.sh
bootstrap/qboot.qbc is part of the repository and must not be deleted; it is the seed for the self-hosting step.
Run the regression suite
tools/test.sh
If build/bqvm or build/qboot.qbc is missing, the script builds it first. The suite checks:
- Examples. All 193 programs in
src/examples/must compile. - Type-check fixtures. All
src/tests/typecheck/good*.qfixtures must compile. - Expected failures.
parse_*.qfixtures must exit with status 2 (parse error), andbad*.qfixtures must exit with status 4 (type error), exactly as their names promise. - Feature and semantics fixtures. All 9 fixtures in
src/tests/features/and all 6 fixtures insrc/tests/semantics/must compile. - Runtime smoke test.
src/examples/arith_sum.qis compiled, executed, and must print5050.
On success the script prints:
QPLUS_LANGUAGE_TESTS_PASS
On failure it prints one or more FAIL … lines and exits with a non-zero status. The robustness fixtures in src/tests/robustness/ exercise the compiler's handling of malformed input; they are not part of tools/test.sh in this release.
The suite is fast: on a typical machine a clean build takes a few seconds, and the regression run then takes around ten seconds.
Compile and run a program manually
# Compile: <compiler-qbc> <source.q> -o <output.qbc>
build/bqvm --timeout-ms 0 build/qboot.qbc src/examples/fib.q -o <tmp>/fib.qbc
# Run: <program.qbc> [program arguments...]
build/bqvm <tmp>/fib.qbc
Notes:
-o <file>names the output file. Without it the compiler writesoutput.qbcin the current directory; always pass-oin scripts so the output path is explicit.--timeout-ms Nlimits VM execution toNmilliseconds. The default is 60000;0disables the limit. The build and test scripts use--timeout-ms 0when compiling.- Arguments after the QBC file are passed to the Q+ program.
build/bqvm --helpprints all VM options;build/bqvm --versionprints the VM and minimal-runtime versions.
What the standalone build does not include
The build script covers the VM and the self-hosted compiler. The AOT backend sources under src/compiler/qplusc/ are included in the repository but are not built by tools/build.sh in this release. The language regression suite and all commands in this document use the bytecode toolchain only.
Continuous integration
.github/workflows/ci.yml runs tools/build.sh followed by tools/test.sh on ubuntu-latest for pushes and pull requests.
Troubleshooting
The build fails with missing source: …
The checkout is incomplete. Re-extract the release archive or re-clone the repository and confirm that tools/build.sh lists only files that exist under src/runtime/.
gcc: command not found
Install a C toolchain. On Debian/Ubuntu:
sudo apt update && sudo apt install build-essential
Permission denied when running tools/build.sh
Either run the script through the shell or restore the executable bit:
bash tools/build.sh
# or
chmod +x tools/build.sh tools/test.sh
build/qboot.qbc has the wrong checksum
The Q+ compiler output is deterministic. A mismatch almost always means the source tree differs from the release:
- Check
sha256sum bootstrap/qboot.qbc. It must be44c21db965319cd87c2ca6d83c683e316eadafdee52cbdd2ad04af3e83cf100b. - Make sure you did not edit
src/compiler/qboot/,stdlib/std/, orbootstrap/. - Rebuild from a clean directory (
rm -rf build) and compare again. - Confirm that
build/bqvmbehaves: it must be the VM produced by this repository, andbuild/bqvm --versionmust succeed.
If bootstrap/qboot.qbc matches but build/qboot.qbc does not, the compiler source has been modified.
build/bqvm has a different checksum
This is expected when the host C toolchain differs. Use build/qboot.qbc as the reproducibility check, and run tools/test.sh to confirm the VM behaves correctly. If you need the reference binary, use the release artifact built with the reference toolchain.
A compile times out
Increase or disable the VM execution limit for the compile step:
build/bqvm --timeout-ms 0 build/qboot.qbc big.q -o big.qbc
Release tree components(1.30.0-dev / spec v4.61)
| 组件 | 版本 | 门禁 |
|---|---|---|
| 语言 / VM / AOT | 1.19.0-dev,spec v4.61(qboot 44c21db9、bqvm 3c04689aa3bb04401b8a2e31f0305466c02fccd55bf2cbe3a39104752698d34f、AOT 9518f9c4) | tools/build.sh + tools/test.sh + tools/robustness_test.sh |
| VS Code / LSP 扩展 | 0.6.0(发布支持组件);0.7–0.12 optional/dev;IDE 0.19 overlay 外部(不随 tar;描述滞后,语言树以集成版为准) | QPLUS_ROOT=$PWD editors/vscode/scripts/validate.sh --integration(190) |
| qpm 包管理器 | 0.5-alpha(prod POC:批量/并行/per-file/多包/签名可信链/update-vendor/撤销/透明日志+compact proof/gossip/verify-sth/witness/checkpoint 链/包级 SBOM+依赖图/SPDX 签名 POC) | bash tools/qpm/ci/selftest.sh(657/657)+ production 55/55 + update 47/47 + revoke 37/37 + sign 29/29 + trust 38/38 + translog 46/46 + translog2 69/69 + translog3 45/45 + translog4 50/50 + sbom 41/41 + sbom2 41/41 |
| 文档站 + Playground | v4.61 | python3 site/build_site.py && python3 site/ci/selftest.py |
| 平台(Windows / ARM64) | build+smoke+子集;Windows async 仅 Fiber sockets 子集;Windows AOT / ARM64 AOT 显式 SKIP | bash ci/portability_check.sh(PASS=11/FAIL=0/SKIP=3) |
| OS SDK | 1.18.0(loopback TCP/UDP/async POC;OS-10 argv PASS;MVP/原型/NOT PUBLISHED;conformance 14/2/4、tests 29/29、fuzz 7 组 339、api_stability 128/0、examples 5/5、qpm e2e 18/18;OS-07/08 PARTIAL;exec 未实现如实) | 见 docs/OS_SDK_1.5_MVP.md(外部,非发布) |
Tests fail with FAIL …
Read the failing line: it names the fixture and the unexpected condition. A single failure usually comes from a locally modified fixture or standard-library module. Re-check your changes against docs/qplus_language_spec.md and CONTRIBUTING.en.md, then open an issue if the failure reproduces on an unmodified checkout.
1.19.0-dev build notes (2026-10-30)
The v1.1 compiler source is larger than the v1.0 bootstrap compiler's source-read window, so the build is a two-step bootstrap (bootstrap/qboot.qbc -> bootstrap/stage0.q -> src/compiler/qboot/...). The rebuilt compiler is verified to be a deterministic fixed point.
The build additionally produces:
build/cgtest.qbcsha256d0295342b67c15e65ba539511c4241146e0905c1ee75e2387a619bad08eae2f1(AOT u64 bitwise codegen) must equal the shippedbootstrap/cgtest_aotfixed point);build/stage0.qbc- capacity-only bootstrap compiler;build/bqvm_smallsha256e24b284b36b173003af532d36780d47628c3fab692835ef349fa4fd8405af4f6(small-heap VM)
Relative use std.<module> paths are resolved against the current working directory. Set QPLUS_ROOT=<tree-root> to additionally resolve them when running from another directory (the build/test scripts run from the tree root, so this is optional).
tools/test.sh covers examples, typecheck fixtures, features/semantics, type bounds, integer matrix, runtime errors (including heap exhaustion), and VM/AOT parity plus AOT loud-fail checks. Release packaging is tools/package.sh.
Clean-build anchors for 1.19.0-dev:
build/bqvmsha256ca0539df3190874eadae942cc1a1166bc0213475abbf146469e42eff17ee79a0(traceback/行表版;u64 bitwise opcodes)build/qboot.qbcsha256abd9fb8341a23efcb86d0b073331cd2e1247d920a33ee7b0108ff28f908d0d63(u64 bitwise TC/gen)build/cgtest.qbcsha256d0295342b67c15e65ba539511c4241146e0905c1ee75e2387a619bad08eae2f1(AOT u64 bitwise codegen)build/cgtest_aotsha2561e619ad37109b383ecc3fb1343898a06196db4f1ea5af41849fcfc2c664a268c(deterministic; equalsbootstrap/cgtest_aotfixed point; u64 bitwise)
P2-B1 build notes (2026-10-29)
The AOT ELF tool now implements integer/float conversions (I2F, F2I, I2I) and CALL_INDIRECT (function values in globals and struct fields), with VM/AOT byte-parity tests. Unknown or unmapped sys_* builtins still fail loudly (exit code 5, no ELF). Small-int boundary checks now also cover array-element assignment, impl method arguments and UFCS arguments. The FS/payload AOT compiler (cgtest_fs.q, not part of the language release) was hardened the same way in the development tree.
P2-B2 notes (2026-10-29)
- Runtime traceback (VM, stderr): function name + bytecode pc per frame;
QPLUS_TRACEBACK=0disables it. Source line numbers require a QBC debug line table (not implemented yet). - Benchmark suite:
bench/run.sh(9 programs; bqvm vs AOT ELF, plus C references) writes raw per-run data tobench/results/. Known AOT correctness gaps surfaced by the suite are recorded honestly inbench/README.md. - Wrapping arithmetic:
use std.algprovideswrapping_add/sub/mul_u8/_u16/_u32/_i8/_i16/_i32(explicit wraparound, coexisting with default checked semantics). - AOT now fails loudly (rc=5, no ELF) on exponent-notation float constants (QBC const type 10) instead of hanging.
P2-B3 notes (2026-10-29)
qbootnow writes a minimal debug line table after the QBC globals section (u32 count, then (fn, pc, line) u32 triples).bqvmconsumes it so runtime tracebacks printat <fn> (line <N>, pc=<offset>); legacy QBC files without the section still load (traceback falls back to pc only). The AOT backend ignores the debug section and does not emit tracebacks (its error lines remain byte-identical to the VM).- Fixed three AOT correctness bugs surfaced by the benchmark suite: integer
DIV/MODzero-check (test r,0always set ZF) andLENon strings (read as an array header).bench/is now 9/9 VM/AOT-consistent and is part oftools/test.sh.
P2-C1 notes (2026-10-29)
- Nested functions may read enclosing function locals/parameters: captures are passed as implicit by-value arguments at each call site (snapshot semantics; writes inside the nested function only affect its local copy). Self-recursion is supported; taking the address of a capturing nested function or delaying the call through a fn slot is rejected loudly (TC).
- Generic struct instantiations (
Box<i32>vsBox<string>) are tracked by the type checker for field typing and assignment checks (erased codegen: one struct layout, one code copy). dyn Traitis a clear[TC11]loud error (static dispatch only); static trait contracts keep working.
P2-C2 notes (2026-10-29)
async fnandawaitare accepted;await edesugars toawait_task(e)fromstd.alg. The current PoC is a single-threaded cooperative task queue:spawn(fn()->i32)enqueues,await_task(id)runs queued tasks FIFO to completion (deterministic; no suspension or preemption);yield_now()runs one queued task. VM and ELF AOT both support it (byte-parity tested). Suspending futures, cancellation and OS threads/channels are not implemented yet; the design blueprint isdocs/CONCURRENCY.md.
编辑器对齐(B2):editors/vscode 源码树为 0.5.0 dev 基线;v1.0 发布 pack 的 editors 0.6.0 由发布工程 overlay 构建。LSP 支持组件 = 0.6.0;0.9.0/0.10.0/0.11.0/0.12.0 为 OPTIONAL/DEV(不进 tar、未发布 Marketplace)。