* fix(firmware): keep producer reports writable under small staging budgets
extract_firmware passed max_output_bytes straight to prlimit --fsize. RLIMIT_FSIZE
applies to every regular file the producer writes, including the mandatory
report.json and unblob.log outside the staging tree, so a staging budget smaller
than the report truncated it and failed the extraction even when every staged
file fit. Derive the per-file ceiling as the larger of the staging budget and the
8 MiB report budget; polling and the final inventory still enforce the aggregate
staging budget.
Fixes#3888
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
* fix(firmware): keep files stopped at the size ceiling over budget
The per-file RLIMIT_FSIZE ceiling equalled the largest size its readers
accept, and both the staging inventory and the report reader accept a
file of exactly their budget. A write the kernel stopped at the ceiling
therefore left a truncated file that passed as complete. Raise the
ceiling by one byte so such a file exceeds its budget and is rejected.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
* fix(firmware): report the effective file-size ceiling on limit failures
The exit path re-derived the staging budget for SIGXFSZ and process-limit
recovery, so a small-budget run killed at the 8 MiB + 1 ceiling reported
file_size_bytes 64 and said the cap was max_output_bytes. Pass the
ceiling runFirmwareCommand installs and describe how it is derived.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
* fix(firmware): reject staged files cut off at the per-file limit
RLIMIT_FSIZE stops a write at the limit without extending the file, and
the staging inventory admits a file of exactly max_output_bytes. With a
budget of 8 MiB or more the producer limit equalled the budget, so a
staged file the kernel cut short published as a complete extraction;
an inherited ceiling below the budget did the same.
Derive the per-run limit once in firmwareFileSizeLimit as one byte above
the largest budget, still capped by the inherited ceiling, so a file
stopped at the limit exceeds its budget. When the inherited ceiling
removes that byte, both staging inventories refuse a regular file that
reaches the installed limit with a nonretryable file-size constraint
naming the inherited limit.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
* fix(firmware): derive limit adjustability from the per-run limit
The one byte of headroom makes the per-run file limit equal an
inherited ceiling of exactly max_output_bytes + 1, but adjustability
still compared that ceiling with the raw budget. A SIGXFSZ then advised
raising max_output_bytes, which the same ceiling clamps back to the
same limit.
Decide adjustability in firmwareFileSizeAdjustable from
firmwareFileSizeLimit itself: recommend a larger budget only when it
raises that limit.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
* test(firmware): compare file-size recovery with its owners
The SIGXFSZ adjustability cases and the inherited-ceiling workflow matched
fragments of remediation prose, so a harmless rewrite would fail them.
Compare the emitted guidance with firmwareSignalLimitError for the expected
branch, check that the two branches stay distinct, and compare the inventory
refusal with firmwareFileSizeLimitReached. The selected limit, resource and
retryability stay asserted as structured facts.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
---------
Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>
Co-authored-by: gensokyo-dev <342580529+gensokyo-dev@users.noreply.github.com>
* fix(engines): keep format ceilings fixed and recover the EVMole deadline
Promote the owned EVMole worker wall clock to timeout_ms and name it in
recovery. Fixed CPU, byte, and address-space refusals in this theme say
the adjustable deadline does not raise them.
Refs #5910
Co-authored-by: morluto <morluto@users.noreply.github.com>
* fix(engines): recover the allowance that refused the request
Model capacity recovery follows a structured limit instead of message text,
and the shared header ceiling no longer names Safetensors. Firmware signal
errors keep captured tool output, oversized reports do not suggest an
intermittent rerun, and NativeAOT hydration budget exhaustion explains the
fixed parser allowance on the partial report.
Co-authored-by: morluto <morluto@users.noreply.github.com>
---------
Co-authored-by: Cursor Agent <cursoragent@cursor.com>
Co-authored-by: morluto <morluto@users.noreply.github.com>
* fix(firmware): keep a missing producer report distinct after exit 0
A firmware engine that exits 0 without writing its requested report now
fails with the observed report state (missing, empty, invalid_json,
oversized, not_regular_file), the command, arguments, exit status and
captured output, plus report-specific recovery instead of generic
`rea doctor` advice. REA still does not retry or substitute an empty
result.
Fixes#5876
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
* fix(firmware): keep missing-report recovery from replaying removed paths
The recorded command arguments name REA's private workspace, which is
removed after the attempt. Recovery now presents them as provenance and
tells callers to replace every private path when reproducing the run.
Cover the oversized and not_regular_file report states.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
---------
Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>
* fix: order remaining outputs independently of host locale
String.prototype.localeCompare without a pinned collation follows the
host's ICU default locale, so the same input could be ordered differently
on different machines. 614fb768 moved canonical domain projections to
compareUnicodeCodePoints; provider, application, catalog, and setup
orderings still used locale collation.
Order every remaining source site by Unicode code point, including Mach-O
symbols, firmware extraction paths, ASAR entries (previously pinned to
"en" collation), evidence ID sets, browser and Electron target, script,
and resource inventories, reconstruction obligations, capability and
provider listings, and setup environment details.
The current tool and prompt catalog names order identically under both
comparators, so the catalog identity digest is unchanged.
* fix(artifacts): order ASAR entries by their portable path
@electron/asar lists host-spelled paths, so code-point order over the raw
spelling still differed by host: "a\b" sorts after "a0" on Windows while
"a/b" sorts before it on POSIX. Pair each listing with its portable
archive path once, order by that path, and keep the host spelling for
@electron/asar calls and adapter keys.