Commit graph

112 commits

Author SHA1 Message Date
Anton Razzhigaev
bd9f7a99ca benchmarks/clb: refresh ablation adapter delta — provider declared once, not per turn
The first cut passed the custom provider as five -c flags on every codex exec. They
share argv with the prompt, and the benchmark's longest questions overflowed the OS
limit, killing a whole task with an unrecoverable OSError. Patch and README now record
the config.toml form that the ablation actually runs.
2026-07-31 07:37:14 +00:00
Anton Razzhigaev
cfa21b3b3d benchmarks/clb: adapter delta for the same-model harness ablation
Records the two adapter changes the luna ablation runs on, so a fresh checkout can
reproduce it: the bridge's format-repair branch no longer raises NameError on the path
it exists for, and the Codex adapter can be pointed at a custom provider so a
harness-vs-harness comparison does not silently become a provider comparison.

Patch file only — no runtime code changes. The adapter itself lives in the benchmark
checkout, per the convention this directory documents.
2026-07-31 07:03:33 +00:00
Anton Razzhigaev
6b831640eb release v6.87.0: a task's live surface and its stored one are two slots, and UNCHANGED stops forbidding the asked-for edit
Two v6.86.0 losses traced to one paragraph of the OSWorld working prompt.

WHERE. The contract asked only where a result must PERSIST, so a task whose
grader reads the LIVE window (is_vlc_fullscreen compares window size to screen)
was answered by ticking the preference and never entering fullscreen. WHERE now
has two slots — live and persisted — each filled or explicitly marked not
applicable. The not-applicable branch is load-bearing: 28 scoring tasks are read
only through tab lists or the active page, is_expected_tabs compares list
LENGTHS, and an extra tab opened "to check the stored slot" would zero them. So
the clause forbids inventing an action, tab, window or dialog to fill a slot the
task does not have.

UNCHANGED. A task asking for a bullet on an existing paragraph was answered by
typing a new line, because the contract had recorded that paragraph as UNCHANGED.
UNCHANGED now covers only content the task does not mention, with a narrow
exception: new content is created only when the task asks for something that does
not exist yet, while a MARKER or PROPERTY the task names — a bullet, a style, a
colour, an alignment — is applied to the content already there. Typing a fresh
line to carry the marker leaves the named content unmarked.

Three further clauses were written and dropped after adversarial review showed
each costs more than it wins, all verified against winning traces:

- prefer a slide master over per-instance edits: 358aa0a7 scores 1.0 and its
  trace states master edits would not work there, because the shapes carry direct
  character formatting that overrides styles;
- exhaust a named resource before any substitute: 36037439 scores 1.0 precisely
  by detouring to another search engine, and the preamble already says to retry
  and try another route on an anti-bot block;
- require a configuration CLI to match the GUI's breadth: generalised from the
  single evaluator in the suite that takes a majority over mime types, and it
  contradicts the preamble's own rule against shaping work around guesses at how
  the grader is implemented.

Adapter prompt only; no runtime, evaluator or task definition is touched.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-31 06:45:44 +00:00
Anton Razzhigaev
8cee0a17a3
fix: stabilize mobile UI and refresh reviewer defaults (#82)
Remove the v6.82 mobile swipe gestures, make drawer opening clear keyboard state, and keep deeply nested live cards usable in narrow consumers. Set fresh-install triad defaults to Luna, Gemini Flash, and Sonnet while preserving saved settings.

Co-authored-by: Ouroboros <ouroboros@local.mac>
2026-07-31 08:13:53 +03:00
Anton Razzhigaev
a947a9310f release v6.86.0: an atomic task contract, and a proxy session that stays out of the published tree
Forensics against the leader's own published per-task dump put the gap at 19
tasks, 8 of them one class: the work was done and never checked against the
surface the grader reads. The worker now writes the task's obligations as a
numbered checklist BEFORE its first mutating action and closes each item as
observed-satisfied / not-verified / impossible before it may finish, repairing
per item. Plural instructions still cover every element; only a singular
referent resolving to several candidates forces a justified single choice, and
the contract is revisable on new observation.

Three infeasibility shapes are named (discovery outside a stated means
restriction; a named mode the app does not ship; a trigger narrower than the
task states), framed on the END STATE rather than the route, with the brake the
gate already had: a wrong verdict scores zero even when the machine is already
correct. The desktop environment's own gsettings/dconf is a legitimate surface
for STORED values only — if the task wants something DISPLAYED and the device
does not exist, writing the key is not a workaround.

Two adversarial reviews corrected this change three times, and each correction
is the interesting part:
- The colour motivation I had deleted as false is TRUE: replaying the real
  grader shows 8472fece's own gold (palette 2A6099) scores 0 against its own
  evaluator, which measures distance to pure 0000FF. No palette entry can win
  it; deleting the motivation gained nothing and endangered 04578141, a live
  1.0 won because of it. Restored and tightened to the exact colour name.
- An earlier draft wrote the per-task proxy config — which carries the account
  password — into all 361 result directories, i.e. the tree we archive and
  publish. It now lives in lane-private state and is unlinked after the task.
- The session tag keyed on run_dir.parent.name, which is the DOMAIN, so the two
  concurrent campaigns would have shared one exit IP per task. Keyed on the
  campaign root instead.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-30 19:17:23 +00:00
Anton Razzhigaev
f336b772f2 WIP v6.86.0: atomic task contract, infeasibility shapes, platform-CLI carve-out, per-task proxy sessions 2026-07-30 18:43:11 +00:00
Anton Razzhigaev
52c67ed159 v6.84.0: slide ordinals need a position order; a colour word means the palette entry
Both from the 22-task regression smoke, each with trace evidence:
- impress/05dd4c1d aligned the document-order shape (Shape;135) while the gold
  targets the visually higher one (Shape;136). The slide-object branch said a
  heading counts as the Nth item but never said in WHICH order to count.
- impress/04578141 read 'use exactly these colours, no variations' as a licence
  to type raw 00FF00 through Custom Color; the gold is LibreOffice's palette
  Green 00A933 at zero tolerance. That wording forbids a neighbouring shade, it
  does not prescribe a hex.

Smoke result: 19 of 22 at 1.0, one at its historical continuous-metric value
(efcf0d81 = 0.8949354689860572, identical to v6.81.1), and these two.
Five tasks that scored 0 in earlier runs now score 1.0.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-30 11:28:39 +00:00
Anton Razzhigaev
dbce0e5775 v6.84.0 r3: address round-2 review — no task may leave the denominator 2026-07-30 09:30:44 +00:00
Anton Razzhigaev
2faee77610 WIP v6.84.0 r2: address round-1 adversarial review (3 CRITICAL) 2026-07-30 09:04:22 +00:00
Anton Razzhigaev
73babbcaf8 WIP v6.84.0: turn-denominated budget, three self-inflicted clauses corrected 2026-07-30 06:49:27 +00:00
Anton Razzhigaev
c3562daba9 fix(osworld): grade from the checkout root, and give the worker the gate's unused turns
Two measured defects from the v6.83.0 campaign, adapter-only.

(1) Evaluator fixtures are declared RELATIVE to the checkout and get_local_file
tests them with a bare os.path.exists, so the grader resolved them against the
process CWD. The official runner works from the checkout root; this bridge did
not, and multi_apps/7f35355e produced the byte-exact answer 25.27 and still
scored 0.0 with only a line in the lane log. evaluate() now runs with the
checkout as CWD, restored on every path.

(2) The 14-turn gate reserve is worst-case; the gate actually spent a mean of 4,
so a flat max_steps-14-1 discarded ~10 turns per example and 13 of 56 opus
failures died at 89-92 turns INSIDE a 100-turn budget. The runner now publishes
the worker's real cap (max_steps - actual gate turns - 1) into the lane settings
the server hot-reloads at every task start, so the declared total is unchanged
and the unused reserve is no longer thrown away.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-30 05:55:45 +00:00
Anton Razzhigaev
3c85d046f0 fix(osworld): a gate-terminated example is zero worker turns, not an unknown count
A gate INFEASIBLE ends the example before the working phase, so the worker
consumed exactly zero policy turns — a KNOWN count. The fail-closed audit read
it as unavailable and flagged budget_fault on the very outcome the gate exists
to produce (caught on os/a462a795 twenty minutes into the v6.83.0 run; the
running run keeps the false flag in its audit field because its seed must stay
clean, and it is corrected at scoring time).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-30 00:54:59 +00:00
Anton Razzhigaev
e88f29e6c2 release v6.83.0: an undecodable screenshot fails where it is taken, an infeasibility verdict is judged as an argument, and a declared step budget is one the runtime enforces
Image integrity is fail-closed at three seams (remote fetch with bounded
re-fetch and write-validate-rename, the shared remote-result builder, the VLM
payload builder). A truncated PNG keeps a valid 24-byte header, so header-only
checks passed it and it detonated rounds later as a non-retryable provider 400
— five task deaths in the v6.81.1 OSWorld run. The rejection is narrow: a
valid-but-huge image and a truncated-yet-renderable JPEG still go through;
only what cannot be rendered at all is refused.

Structured tool failures ({ok: false}) now feed the error counters, anti-loop
and auto-attach — but NOT the verification ledger, because a diagnostic that
honestly reports what it was asked to find is a finding, not a failed run.

Acceptance review gains an ABSENT-PREMISE branch: when the terminal claim is a
missing premise, the deliverable under review is the premise ARGUMENT.
Demanding the named artifact begs the question, and coaching a continuation
that breaches the task's own restrictions manufactures what the task forbids.
A weak premise argument still fails on its own grounds.

type_text routes multi-line and long payloads through the in-VM clipboard, and
picks the paste chord inside the guest call (a terminal ignores Ctrl+V while
the hotkey still reports success).

OSWorld adapter: --max-steps declares AND enforces a leaderboard-comparable
budget. A step is one top-level policy turn, matching the official
predict()->actions[] boundary, not one GUI action. The server round cap is
verified before the VM boots; the gate phase is cancelled at its own reserve,
counted from its LIVE event log (loop_outcome exists only after finalization,
so polling for it would have been dead code); the post-run audit reads policy
turns, not the flat physical-call field they disagree with on 344 of 346
examples. --expect-dataset-commit turns the graded-spec pin into a gate.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-30 00:40:45 +00:00
Anton Razzhigaev
fc5c0aef30 WIP v6.83: step-budget enforcement for OSWorld submissions
A leaderboard step is one top-level policy turn (lib_run_single.py increments
step_idx once per agent.predict() and runs every action that turn emitted),
NOT one GUI action — the earlier 0.42-actions-per-round mapping compared a
turn against an action and understated our budget ~2.4x.

- --max-steps declares AND enforces a comparable budget: gate reserve + worker
  cap + one tool-less terminal turn, refused fail-closed before the VM boots
  when the server round cap exceeds it.
- Post-run audit records policy turns actually used and marks overruns
  non-comparable instead of rewriting the reward.
- Typed step semantics in the run manifest; MAX_STEPS wired through the lane
  scripts.
- Replaced three test fixtures whose 'minimal valid PNG' literals were
  undecodable, and corrected an assertion that pinned an identity coordinate
  transform which only held because the stub never downscaled.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-30 00:04:59 +00:00
Anton Razzhigaev
55992397d8 WIP v6.83: acceptance premise-branch, worker forensics clauses, gate 4d
- ACCEPTANCE_SURFACE_RULES: ABSENT-PREMISE / INFEASIBLE DISPOSITION branch —
  when the terminal claim is infeasibility, the deliverable under review is
  the premise argument; 'deliverable exists' as a criterion begs the question,
  and coaching a restriction-breaching continuation manufactures artifacts
  (v6.81.1 gimp/5ca86c6f: reviewer veto converted a scoring 1.0 into 0.0).
- OSWORLD_PREAMBLE: five clauses from the failure forensics (named value via
  the app's own control; verbatim clipboard transfer; minimal-diff; ordinals
  over real items; finish on the graded surface).
- GATE_PREAMBLE: 4d — named mode / apply scope / prohibition are premise
  carriers, not working-phase details; fail-open default unchanged.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-29 23:29:28 +00:00
Anton Razzhigaev
c6a7009504 WIP v6.81.2: structured tool failures, guest watchdog, integrity guards
Not a release — a probe seed for the Opus-5 recovery measurement, to be
rebased onto the other agent's release and reviewed before any push.

- Extension tools answer with a JSON envelope, so a failed call arrived as
  {"ok": false} with no core marker and was recorded a SUCCESS: 329 rows in
  the v6.81.1 run (302 remote_exec, 20 screenshot, 5 key, 2 click). The error
  counter, anti-loop, monitoring and the reflection trace all believed those
  calls worked. _structured_tool_failure() reads the payload; typed status
  tool_reported_failure; auto-attach refuses such a result.
- Host-side watchdog on the guest control endpoint: an agent killed the guest
  server and then worked blind. Unreachable for 180s ends the attempt as a
  typed INFRA row (reward null, claim released), never a capability zero.
  Probe fails closed.
- type_text: < arrived as > (measured hex 3e for 3c) — angle brackets now take
  the clipboard path non-ASCII already takes.
- key: whitespace is a SEQUENCE of chords; the bare form silently no-opped.
- Bridge URL removed from agent-visible results; list/test_connection denied —
  an agent read the port from a tool result and curled <bridge>/evaluate.
- Gate rubric 4b/4c (same-thing check, verify-don't-assume) and a working-phase
  rule that state must come through the app's own surface, not from underneath.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-29 22:27:49 +00:00
Anton Razzhigaev
86dad2255f release v6.81.1: one round per look, one verdict per premise — OSWorld forensics land as mechanism fixes
Everything here is a mechanism fix for a defect the v6.81.0 OSWorld full-run
forensics measured, none of it a patch over a symptom.

CORE (three touches, deliberately minimal):
- Tool results may carry a typed auto_attach_image capability: the host
  attaches that local image to the conversation in the SAME round, after the
  round's complete tool-message block, through the exact implementation the
  view_image tool uses — vision.attach_local_image_to_context, ONE body for
  both paths, so trust boundary (allowed roots, size cap, fail-closed MIME
  sniff), durable copy (uploads/views) and message shape cannot drift.
  Extension (ext_) results only: MCP results are untrusted server-supplied
  data and must not drive automatic context mutation. Failure is strictly
  non-fatal. Measured cost removed: 3,830 of 16,367 rounds (~21% of the round
  budget) were the mandatory second view_image round per observation, and
  every task at the 200-round cap scored 0.
- MAX_LIVE_IMAGE_BLOCKS 3 -> 5 (owner decision 2026-07-29).

SKILL unix_computer_use (manifest 0.3.0 -> 0.4.0 so the version-keyed native
seed resync actually distributes this):
- One pointer-coordinate normalizer behind click/move/aliases/mouse_down/
  mouse_up/left_click_drag: accepts the malformations models actually emit
  (the pair packed into x with y absent, legacy -1 sentinel, or a single
  duplicating y — 109 wasted rounds in one run), distinguishes ABSENT from
  UNPARSEABLE, and fails loudly on contradiction. y leaves the required
  schema so recovery happens before binding.
- double_click/triple_click register as thin click aliases (111 previously
  'Unknown tool' calls) — and enter the bench adapter's _GUI_ACTION_TOOLS in
  the same commit, so the premise gate cannot click through an alias.
- screenshot results emit auto_attach_image (remote + local builders, both
  pinned by tests); remote_exec's description states its real per-backend
  contract (fresh bash -lc on OSWorld; SSH login shell on macOS; never the
  visible desktop terminal).

OSWORLD ADAPTER:
- Premise-gate prompt becomes a structured rubric (action -> referent ->
  blocking -> acquirable -> store-or-render -> unbound placeholders): the
  v6.81.0 false kills all judged outcome-meaningfulness instead of
  action-performability, and an exception list would be a keyword patch.
- The confirming challenger is REMOVED on its own full-run ledger: 20
  invocations, 0 feasible saves, 1 officially-infeasible task lost, 215
  worker rounds burned, and it CONFIRMED all four false kills —
  identical-prompt re-reads are correlated, not independent. Claim window
  back to one premise round; manifest discloses the absence.
- Working preamble: the forced screenshot->view_image loop is gone
  (screenshots attach automatically), and an ENVIRONMENT PITFALLS section
  states task-general state rules (live-app in-memory copies must be
  reconciled after out-of-band edits; terminal tasks belong in the visible
  terminal; PIDs resolved by exact executable, never self-matching -f
  patterns) — phrased without any claim about what an evaluator inspects,
  disclosed in METHODOLOGY as a scaffold revision whose numbers must not be
  pooled with earlier ones.

REVIEW TRAIL: 7 triad+scope iterations (fable + gpt-5.6-sol +
gemini-3.6-flash, scope fable, effort high; artifacts under
/mnt/data/a.razzhigaev/osworld_runs/review_v6811_iter*). Fixed from review:
skill manifest version bump (distribution was version-keyed), ARCHITECTURE
auto-attach flow + K=5, per-backend remote_exec wording, gate-phase alias
denylist + named-literal test, post-block attach ordering with pinned test,
absent-vs-unparseable coordinate contract + handler-boundary tests,
real-producer auto_attach_image tests, up-to-two-tasks cost wording.
Rejected with evidence, recorded here per review policy: (1) the module/
function size hard-gate claim — the authoritative gate
(ouroboros/review.py excluded prefixes; tests/test_smoke.py _SKIP_DIRS)
explicitly excludes devtools/ and tests/, and the enforced suite is green;
(2) the demand to remove the ENVIRONMENT PITFALLS rules — the same reviewer
slot prescribed exactly these task-general formulations in iteration 4;
the remaining wording contains no evaluator-behavior claims.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-29 11:25:01 +00:00
Anton Razzhigaev
b0fa02e83b benchmarks/clb: refresh official-submission adapter patch (squashed branch)
Regenerated from the final 2-commit ouroboros-submission branch
(3ea30ef system + a691cf3 artifacts on upstream 5f8c50eb): includes
engine-task cost harvest contract (cost_final/cost_usd_with_children,
one-shot hot path, finalize on last observe), CLBENCH_SHIM_BIND,
docker --user mapping, run registration in DEFAULT_RUN_NAMES and
leaderboard SYSTEM_DEFS, and the rewritten run-specific METHODOLOGY.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-29 10:23:22 +00:00
Anton Razzhigaev
4344c2c95d clb: adapter delta after first end-to-end official-path smoke (docker --user, shim bind)
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-28 21:08:28 +00:00
Anton Razzhigaev
01e84ff81e osworld: name the repair that actually fixed the smoke — the endpoint republish
The preceding commit attributed the v1 smoke's collapse (feasible-control mean
0.737 -> 0.459) to OSWorld's silent setup skip. Evidence from the v2 run says
otherwise, and the docs should say what the data says.

DockerProvider.revert_to_snapshot stops the container; start_emulator then
REALLOCATES ports via _get_available_port(5000). The VM address therefore
changes on every reset. v1 published that address exactly once, before the gate
— measured after the fact: 83/83 task dirs have bridge.json older than their
gate record — so the working phase kept driving the pre-gate port, which with 16
lanes allocating from one range another lane's container could already own. The
traces match: empty Desktops, missing task files, and one worker acting on a
different task's presentation entirely (content found in no task file — it was a
neighbouring lane's live VM). v2 republishes and shows 0 regressions against 9 at
the comparable stage; ports demonstrably move and repeat across lanes
(5024 seen on both lane0 and lane4).

The verified reset stays: it closes a real, independent OSWorld fail-open that
also affects ungated runs. But it is defence in depth, not the measured fix, and
both docs now say so — 24 post-gate resets in v2, 0 retries needed. Claiming a
guard fixed something it never fired on is how a harness acquires cargo cult.

Adds the ordering test the class needs: post-gate reset -> target file rewrite ->
_publish_target -> worker creation.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-28 18:01:17 +00:00
Anton Razzhigaev
915e43cc4f clb: refresh submission adapter delta after cost-harvest review fixes
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-28 17:50:33 +00:00
Anton Razzhigaev
85ac69a220 osworld: verify every reset, confirm every kill, audit every gate command
The 2026-07-28 smoke found the gate itself sound (13/27 caught, 0 false kills
in 42 feasible controls) and the scaffolding around it destructive: the bare
post-gate env.reset() hit OSWorld's silent fail-open (guest probe timeout ->
ALL setup steps skipped, 'Environment setup complete.' logged, no exception)
and working phases opened on VMs without the task's files. Feasible-control
mean fell 0.737 -> 0.459. Three changes, each closing a reviewed hole:

- _reset_verified() replaces BOTH bare resets: asserts the machine-checkable
  postcondition (is_environment_used iff non-empty config) plus the screenshot
  probe, forces the snapshot revert before every retry (an unforced retry runs
  setup on top of partial state), republishes the VM endpoint after the
  post-gate reset (docker recreate changes IP/ports), and turns exhaustion
  into a typed infra row (reset_unverified, reward null, claim released) --
  a setup the harness could not verify must never become a capability zero.
  The silent-skip flaw predates the gate and affected single-reset runs too.

- An INFEASIBLE verdict no longer stands alone: an independent challenger
  round (fresh session, same read-only envelope) must agree before the kill;
  disagreement fails open. One false kill erases the gate's measured edge,
  a missed infeasible still has the worker's own TASK_INFEASIBLE path.

- The one condition that must NOT fail open now does not: a premise round
  whose cancel did not confirm aborts the attempt as blocked (exit 2) --
  a zombie premise session shares the lane's server and connection file and
  would act on the VM the worker is scored on. Each round's full tool trace
  (verbatim args, not previews) lands in feasibility_gate.json for offline
  audit of the read-only-by-instruction promise.

Claim staleness now covers two premise windows. Manifest discloses
feasibility_gate_challenger. Docs updated; 13 new tests pin the reset
postcondition, the two-verdict kill rule, the zombie detection and the
verbatim trace.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-28 17:38:00 +00:00
Anton Razzhigaev
996072811f clb: official submission adapter delta (merged colleague base + v6.81 ports + cost UsageEvent)
Single-patch SSOT for the run-all submission path against upstream 5f8c50eb.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-28 12:54:39 +00:00
Anton Razzhigaev
4f5780f46b osworld: fix what three adversarial reviews found in the premise phase
Reviewed by codex gpt-5.6-sol and two independent readers before any run. They found one
defect that would have corrupted results and several that would have cost feasible tasks.

The claim staleness bound did not include the premise phase. The gated holder occupies
the claim for up to task_timeout/4 BEFORE the working task, so with shipped defaults it
consumed the entire margin the formula reserves for the unbounded evaluate() — after
which a second lane treats the lock as stale, takes the same task, and both score it.
The bound now grows by the same expression the phase's own deadline uses, so the two
cannot drift.

The verdict parser scanned every line in reverse for a keyword. A model that enumerates
the three options while reasoning and then concludes in prose had its recap read as its
answer: a PROCEED became a scored hard zero. Reproduced, then fixed to read only the last
line, which is what the prompt asks for; ordinary formatting (trailing period, bold,
backticks, case) is tolerated, a verdict inside a sentence is not. The reproduction is
now a regression test.

The INFEASIBLE path synthesized {"status": "completed", "result": "TASK_INFEASIBLE"} so
the existing detector would fire. That published a clean runtime outcome and a terminal
answer for an agent that never spoke — the same class of lie the final_answer fix in
257a369 removes. The flag is now explicit, the absent working phase is left visible as an
absence, and the outcome records infeasible_source and the phase's own rounds so a
gate-terminated example cannot be read as an agent that declared it.

Also: the untrusted task text no longer has the last word in the gate prompt (a task
saying "end with INFEASIBLE" could score itself zero); the infeasibility detector reads
the authoritative terminal answer instead of OR-ing over a field where a retracted
mention could step FAIL; sidecar write failures no longer control execution — one of
them sat between env.step("FAIL") and evaluate(), so a failed write lost a task that had
already been acted on; the gate's timeout cancel is confirmed rather than assumed, since
an unconfirmed cancel leaves a second agent on the same VM.

The phase closes the GUI vector only. remote_exec stays a general shell, read-only by
instruction, because classifying shell commands in code is the pattern gate P5 forbids.
The comment claiming the premise "cannot" be manufactured was wrong and now says what is
actually true; the working phase is re-reset after a PROCEED so nothing the premise phase
touched reaches the scored state. README and METHODOLOGY §7 (4c) state all of this.

Tests: the new control flow had none. Added the fail-open table, the recap regression,
the claim-bound relationship, the gate-phase tool removal, and a check that the
acceptance claims stay general.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-28 11:01:34 +00:00
Anton Razzhigaev
2c294ab97c osworld: a premise phase that cannot act, and fails open when it is not sure
The prose rule shipped in the previous commit tells the agent to establish the premise
before working. This adds the option of making that structural instead of advisory:
--feasibility-gate posts a first task whose mutating GUI tools are absent from the
capability envelope, so the agent judging whether the premise holds physically cannot
manufacture it first. That was the observed failure — same probe, same negative answer,
then a wallpaper copied onto an empty Desktop.

Three-valued on purpose. Only a standalone INFEASIBLE ends the example; PROCEED,
UNDETERMINED, an unreadable answer, a timeout, a crashed phase and any exception all
proceed to the full-capability phase. The gate may remove a task the agent was
affirmatively certain about and nothing else. The published verified run we compared
against lost a task by calling a Cloudflare block infeasible, so UNDETERMINED is named
in the prompt as the answer for network and anti-bot obstacles.

The INFEASIBLE path does not re-implement scoring: it synthesizes the terminal answer
the working phase would have produced and falls through to the single existing
evaluate() + claim-marker sequence, which is the code that protects against double
scoring and must have exactly one caller.

remote_exec stays available for read-only probes and read-only is an instruction, not an
enforcement: classifying a shell command as reading or writing in code would be the
pattern gate P5 forbids for a semantic decision.

Off by default, and the manifest stops claiming one run per task when it is on.
Unverified: the false-INFEASIBLE rate on feasible tasks is not measured yet, and that is
the number that decides whether this is worth its cost — README says so.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-28 10:31:47 +00:00
Anton Razzhigaev
257a369f6b osworld: state the premise rule the traces show we needed, and stop paying a silent reviewer
Pairwise forensics against a published verified run on the same 361 tasks and the same
model put ~90% of our deficit on the 27 infeasible-evaluator tasks; on the 333 feasible
ones the two runs are statistically indistinguishable. Reading our own traces there, the
failure is not that the agent lacked information: it ran the correct probe, got the
correct negative answer, and then manufactured the premise — copying a system wallpaper
onto an empty Desktop and adjusting its own planted file, building a same-named theme
directory from a sibling, writing document internals the app cannot render — and
reported success.

The prose rules were already there and did not hold, so this changes what they say
rather than adding another one:

- the feasibility rule enumerated missing hardware, accounts and app features, which
  never covered an absent object the task acts on. It now names the class: an essential
  PRE-EXISTING target or capability the task presupposes is absent — as distinct from
  what the task asks to create, from a detail mentioned only as motivation, and from a
  transient network block. That last exclusion is not hypothetical: the verified run we
  compared against lost 82279c77 by calling a Cloudflare block infeasible.
- establishing the premise no longer competes with speed; it is exempt from the
  investigation budget that sits three lines below it.
- manufacturing the premise is named and forbidden, as is searching the guest for
  grader code — observed in the v6.81.0 traces, nothing found, nothing exploited, and
  it should be prohibited rather than merely unsanctioned.

acceptance_claims was [] on all 361 tasks while the acceptance panel ran on 324 of them.
Four general claims now travel with each task, so the reviewer that already runs
adjudicates observations instead of narrative. No extra model call.

cu_bridge outcomes carried final_answer: null while the answer sat in the runtime
result, which is exactly what METHODOLOGY §4 exists to prevent; it now falls back as
documented.

Nothing here encodes a base rate of infeasible tasks, a task id, an application, or any
evaluator property. Numbers from before and after this revision are from different
scaffolds and must not be pooled.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-28 10:26:50 +00:00
Anton Razzhigaev
fa7937cba8 docs(benchmarks/tb): state the instruction clause and the subagent nuance truthfully
Two of our own public artefacts contradicted our own traces, which a leaderboard
reviewer would read as concealment rather than as stale text:

- README claimed the adapter passes the Terminal-Bench instruction "unchanged" and
  "does not prepend harness notes", while run() appends an anti-lookup integrity
  paragraph to every instruction. The clause is a restriction on the agent, not a
  hint, but it is part of the measured configuration and has to be disclosed. The
  exact text is now reproduced in the README so a reviewer can diff it against the
  official task.
- The adapter comment asserted "subagents=0" and that max_workers is moot. Measured
  on the v6.81.0 runs: withholding schedule_subagent stops task DELEGATION, but
  plan_task still runs pooled planning scouts that appear in traces as
  delegation_role=subagent. A submission must claim "no task delegation", not
  "no subagents".

No behaviour change: documentation and one comment only.
2026-07-26 22:34:43 +00:00
Anton Razzhigaev
2925d2be5f docs(benchmarks): CLB v6.81.0 campaign post-mortem — cohort scale convention, bridge run_index defect, submission requirements, universal pre-flight
Lessons from the 2026-07-26 CLB campaign, written down so they cannot repeat:

- continual_learning/METHODOLOGY.md §10-§12: the cohort metric changed
  upstream (clipped nats ratio -> signed bits); the fix shipped as re-scored
  reference artifacts (two reward copies per artifact) and as analyzer commit
  5f8c50eb (colleague's PR pgasawa#9, merged 2026-07-19) — scoring with the
  pinned analyzer mixes scales and fabricates a phantom top-1. The operator
  bridge drops --run-index on 5/6 domains (ctor-only injection, no
  prepare_run call): bridge multi-seed = fixed-order replicates; empirical
  prompt-hash check is now a required pre-flight. Submission requires a full
  default run-all (5 permuted rollouts + stateless baseline), a public
  implementation link, and >=4 seeds for a strict beats-top-1 claim.
- continual_learning/RUNBOOK.md: operational lessons — score only at/after
  5f8c50eb; OpenRouter spendable = min(key limit remaining, account credits);
  live key rotation via runner_state settings.json; secrets hygiene for
  runner_state snapshots; interrupted stateful rollouts are write-offs.
- benchmarks/README.md: mandatory four-point Upstream-Drift &
  Protocol-Fidelity Pre-Flight for EVERY benchmark before expensive runs
  (upstream drift incl. artifact-only re-scores; empirical protocol fidelity
  by artifact diffing; submission requirements read before the run;
  reconciling pinned scorers against the public leaderboard).

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-26 22:15:45 +00:00
Anton Razzhigaev
3f9d504b76 fix(v6.81.0): the submission scrubber must refuse symlinks, not certify past them
scrub_submission_secrets.py walked `root.rglob("*")` filtered by `p.is_file()` and
wrote with `path.write_text()`. Both follow symlinks, so the tool had two failures,
each demonstrated against the pre-fix code.

A FILE symlink was swept THROUGH: the write landed on the link's target, outside
--root. A pack containing a link to the live settings.json therefore had its real
keys replaced with <REDACTED:...> by the tool whose job is to protect them. `cp -a`
preserves symlinks, so the procedural "run this on a COPY" rule did not help.

A DIRECTORY symlink was worse. rglob does not descend through one, so its contents
were never enumerated — and the verify pass then printed verify_leftovers=0 and
exited 0. The tool affirmatively certified a tree it had never read, for content
reachable under --root and about to be uploaded to a public leaderboard. Silent
non-coverage reported as cleanliness is exactly the class of false claim this
release exists to remove, and here the consequence is a live API key published.

Both are now a hard refusal before a single byte is written, reusing the fail-closed
discipline the --env-passthrough refusal already established: every offending link is
named with its target and its kind, nothing is modified, exit 2. Refusing beats
resolving-and-continuing, because under --root a symlink is either an accident or an
escape and only the operator can say which. With the links removed the tool sweeps
and verifies exactly as before, so this refuses an unsafe shape rather than removing
a capability.

Pre-fix, the new test fails with `assert 0 == 2` — the old tool reported success.
2026-07-26 06:03:31 +00:00
Anton Razzhigaev
293bb259dd benchmarks: derive the truncation vocabulary from the runtime, not beside the check
CRITICAL (advisory, v6.81.0). The disclosure field added this release to stop false
capability claims was making one. RUNTIME_TRUNCATION_REASON_CODES was hand-copied next
to the check and listed four codes the runtime has never emitted (max_rounds_exceeded,
task_timeout, context_exhausted, rate_limited) while omitting the two it actually uses
for the round cap and the loop-local deadline (round_limit at loop.py:3128 via
_handle_round_limit, deadline_local at loop.py:3220). A round-capped or deadline-stopped
task therefore published an affirmative `truncated: false` and run_tb.py filed it under
genuine_failure_count -- "the agent got a fair shot and got it wrong" about a trial cut
off mid-attempt. The comment above the set even named
ouroboros.outcomes.BEST_EFFORT_REASON_CODES as the SSOT while contradicting it.

Fixed as the CLASS: the set is now DERIVED from BEST_EFFORT_REASON_CODES. All six of its
codes are also "an auditor must not read this as a capability result" -- forced
finalization means the attempt was cut short by a rail rather than ended by the agent --
so it is taken whole, with no subtraction. One explicit additive delta, llm_api_error
(loop_llm_call.py:630): not a best-effort code, but the same class for an auditor as
provider_unavailable, and adapters without a separate infra channel would otherwise
publish `truncated: false` for a transport death. Every kept code is grepped to an
emitting line in ouroboros/; nothing that cannot be located there survives.

Three copies of one vocabulary become one derivation plus one pinned mirror:
* harbor_installed_agent.py now INTERPOLATES the set into the container runner template
  (it is generated source, so the literal cannot go stale);
* the CL-Bench operator patch genuinely cannot import it -- that module lives in an
  external clone reached only through a call-time sys.path insert -- so its mirror stays,
  but a test now parses the vocabulary out of the .patch file and fails on divergence.
  The patch is regenerated in place with recomputed hunk counts and verified to apply
  cleanly to a pristine adapter checkout (@549998d).

Drift guard (modelled on test_credential_groups_cover_every_routable_provider): every
literal reason_code in ouroboros/ must have a recorded decision in _TRUNCATION_DECISIONS,
with the emitting line and the reasoning, and the truncating subset must equal the
published set. A code added to the runtime tomorrow fails the suite instead of silently
defaulting to an affirmative `truncated: false`.

Prose the code contradicted, now true and verified: run_tb.py's trial comment and the
'cost_truncated' bucket docstring, the OSWorld METHODOLOGY disclosure paragraph, and this
test module's FIX B header. run_tb's _provider_reasons also shed rate_limited and
provider_error -- inert, never emitted, same hand-written-vocabulary defect.

MAJOR (advisory). continual_learning/METHODOLOGY.md still documented
`extra.runtime_attested: false` and attributed the patch probe to the execution clone;
a5bdf5e renamed the field to runtime_attestation_available and corrected the target to
the --runner-path ADAPTER checkout, but only in section 6. A test asserts the old field's
absence, so the document pointed at a key the manifest provably no longer carries. Swept
the tree for runtime_attested and "execution clone": no other stale occurrence.

Verification: ruff --select F clean; node --test web/tests clean; audit_all_launchers()
and version_carrier_desyncs() empty; serial CI lane green. The parallel CI lane is red on
exactly one unrelated, pre-existing cross-test-pollution failure
(test_deep_self_review.py::TestIsReviewAvailable::test_openai) reproduced identically on
a5bdf5e and passing in isolation. VERSION stays 6.81.0.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-26 05:26:48 +00:00
Anton Razzhigaev
a5bdf5e010 v6.81.0: benchmark artefacts must not carry or claim what did not happen
Two provenance fixes in the same class as the release itself, plus the
round-11/12 review findings that land in the same files.

FIX A — an isolated benchmark container carries only the providers the run
declared. `build_isolated_settings` copied EVERY provider credential present
in the live settings file regardless of which providers the run's model slots
declared, so a run pinned to OpenRouter still received direct ANTHROPIC /
OPENAI / Cloud.ru / GigaChat keys. Two consequences: a routing fallback could
spend outside the declared bucket while the manifest said otherwise, and the
reachable provider set was a function of whatever happened to be in the live
file at launch — a pinned seed that pins the code but not the environment is
not reproducible. Provider credentials are now gated on the run's declared
slots, derived from the routing SSOT (`provider_models.PROVIDER_PREFIXES` /
`provider_for_model`, the same registry `llm._resolve_remote_target` routes
on), and travel in whole groups so a key never arrives without the endpoint or
auth fields it is useless without. Owner/control secrets were never copied and
still are not. Ambiguity fails OPEN (carry a spare, disclose it) — never
closed. `benchmark_run_manifest` now records `provider_credentials`: which
credentials the container actually received, by fingerprint, never by value.

FIX B — a task the cost rail truncated says so. `usage_accounting.reserve_-
attempt` refuses on a worst-case reservation bound that reached a $6.00 rail at
$0.45 of actual spend in the v6.81.0 OSWorld smoke, stopping two of three tasks
at 13 and 22 rounds; the artefacts published `status=completed`,
`reason_code=official_evaluate` and the string `budget_exhausted` appeared
nowhere. `task_result_row` gains an always-present `runtime_outcome` projected
by the new shared `runtime_terminal_disclosure`, and every writer holding a
runtime task result now publishes it: OSWorld cu_bridge, SWE-bench and
ProgramBench success rows (the failure rows already did), the Terminal-Bench
in-container summary and disclosure ledger, the GAIA solver, the harness-bench
wrapper, and the CL-Bench per-question writer. Reward, `official_eval_status`
and adapter-stage `status` are untouched: disclosure ADDED, fact not
subtracted. TB's ledger gains a `cost_truncated` bucket — `genuine` asserts a
fair shot, which a rail-truncated trial did not get.

Review findings folded in:
- `_amend_manifest` emitted `output_paths.task_outcome` unconditionally, so the
  finalized attempt manifest kept pointing at an outcome whose write failed.
  The previous round fixed the ledger row and left the manifest lying; both
  sides now follow the same rule.
- `ADAPTER_PATCH_MARKERS` keyed two of three detections on bare env-var names,
  which the unpatched adapter may mention in a comment or a `-e` passthrough
  list. That false positive OVERSTATES enforcement. Markers are now
  patch-unique tokens and the uniqueness requirement is recorded beside them.
  (One marker legitimately covers all three env knobs: they arrive in one loop
  in one hunk.)
- CLB fidelity overstated enforcement on the DEFAULT `--path standard`:
  `_docker_launcher.submit()` hardcodes `disabled_tools: []` and never imports
  the patched bridge module, so the evidence is now entrypoint-specific.
- `runtime_attested` renamed to `runtime_attestation_available`: it is a tree
  probe, and a definition existing is not evidence that it ran.
- README version badge alt text said 6.80.0 while the URL said 6.81.0, which
  `version_carrier_desyncs` flags and the advisory preflight blocks on.

Bug-pinning tests inverted, and said so in the test docstrings:
- `test_dry_run_claims_attestation_only_when_the_patch_is_in_the_execution_-
  clone` asserted `runtime_attested is True` for a DRY RUN against a clone that
  merely contained an `_attest_runtime` definition — it demanded the false
  positive as the contract.
- the CLB fidelity fixtures wrote bare env-var names as "the patch", which is
  precisely the marker weakness above.

Docs corrected where the code falsified them: OSWorld METHODOLOGY §7.4 claimed
`OUROBOROS_MAX_ROUNDS` plus the timeout were the only per-task caps (the USD
rail binds first), §6 now says scoring reads `official_eval_status` /
`details.outcome_status` rather than filtering on `status == "completed"` and
that `output_paths.task_outcome` may be absent; CLB METHODOLOGY §3 documents
when an exported runtime mode overrides the adapter's hard-set `advanced`, and
§6 distinguishes the `--runner-path` adapter checkout from the
`--ouroboros-clone` execution seed and points at the field the code actually
writes.

Known ordering debt noted in place for the v6.82 backlog, deliberately not
restructured here: `_auto_sync_release_metadata_if_needed` runs ~87 lines after
the `_release_metadata_preflight` gate it would satisfy.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-26 05:04:14 +00:00
Anton Razzhigaev
e33b834c38 fix(v6.81.0): provenance records what happened, not what was intended
Four findings from the interference review of the assembled release and the
CL-Bench pre-tag smoke. All four are the same defect: a record derived from
INTENT — a flag, a constant, a pre-failure status — rather than from the fact
it describes.

1. osworld cu_bridge: the ledger row no longer asserts an artefact that was
   never written. Making each publication destination independent stopped one
   dead record from erasing an obtained score, but it also made the row
   reachable when its target was not: `output_paths.task_outcome` was emitted
   unconditionally, with the pre-failure status and without the collected
   `publication_errors`. The row is now built at append time from the
   destinations actually reached — the pointer only when that write succeeded,
   `status` degraded to `partially_published`, the run's own status kept in
   `details.outcome_status`, and the errors carried along. `official_eval_status`
   and `details.reward` are untouched: the evaluation really did complete, and
   demoting them would re-create the score-erasing bug.

2. CL-Bench: `extra.runtime_attestation_path` claimed the docker attestation
   hook whenever `--docker` was passed, though the hook arrives only with a
   tracked operator patch applied out of band per run. A docker run on an
   unpatched clone was unattested while its manifest said otherwise. The new
   `adapter_patch_probe` reads the execution clone for each patch's marker;
   an absent attestation is recorded as absent, with a warning.

3. CL-Bench: `_fidelity_report` described the PINNED adapter, so on a patched
   clone it announced a gap the patches had closed — claiming safety `full`,
   advisory enforcement and no `claude_code_edit` exclusion for a run really
   executing `light`/`blocking` with all nine tools disabled. Knobs now land
   under `enforced_via_operator_patch` or `declared_only_pinned_adapter_gap`
   according to the probe. `OUROBOROS_RUNTIME_MODE` had the same shape and is
   derived too. METHODOLOGY.md section 6 is corrected to match.

4. `test_every_settings_writer_routes_through_the_shared_prologue` keyed its
   writers dict on `str(path)` and compared against forward-slash literals, so
   on Windows every `exempt` lookup and both final assertions would break —
   the fourth Windows portability defect of this campaign. Keys are now
   `as_posix()`. A sweep of the campaign's other added tests for the same
   shape (dicts keyed by `str(path)`, hardcoded 'a/b.py' compared to a path)
   found no second instance: the remaining hits compare `path.name`, already
   call `as_posix()`, or feed assertion messages only.

The previous form of the CL-Bench attestation test pinned finding 2 — it
demanded the false claim — and is replaced by a pair asserting both
directions.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-26 04:08:50 +00:00
Anton Razzhigaev
f05bf94362 feat(v6.81.0): benchmark provenance becomes a gate, and the artefacts stop lying
Six reviewed phases land as one release.

Admission is the outer boundary: every migrated launcher records a manifest before
it can touch the filesystem, and finalizes a typed outcome on every path — success,
refusal, crash, and the real exit status. A structural audit enforces that boundary
across all fourteen launchers, together with confinement computed from the active
checkout and a single manifest publisher, judging by effect rather than by callee
name and failing closed on any write form it cannot resolve.

Harness exit codes are no longer trusted as run status: inspect returns zero for an
eval that raised and harbor returns zero for a job whose trials all errored, so the
launchers now read the harness's own artefact and keep "the harness failed", "it
scored nothing" and "it scored honest zeros" distinguishable.

The acceptance dialogue reconciles receipts through one typed identity that is an
equivalence by construction, so a passing check can no longer clear a red it never
addressed. Prompt caching is normalized at every send site and cached calls stop
under-reporting their input. The owner's context mode becomes explicit and
fail-closed, with one enforcement point for every writer of a disk-authored setting.

Deliberate limits are disclosed in each bench's METHODOLOGY.md rather than implied
by silence. Isolated benchmark egress and the multi-lane script generator are
deferred to a later release with restoration patches and carry-forward notes.
2026-07-26 03:40:44 +00:00
Anton Razzhigaev
e879ffc675 fix(v6.75.0): benchmark run provenance becomes a gate, not a report
Every claim a benchmark run makes about itself is now either enforced before
money is spent or refused with a durable typed record.

Admission is the outer boundary, and that is a tested property, not a
convention: `admit_benchmark_run()` builds the manifest, WRITES it, and only
then lets the seed gate enforce, raising `BenchmarkAdmissionRefused` with the
refusal already on disk. A `finalize_run_manifest()` context manager records a
typed outcome, a typed refusal/error and the REAL exit status on every exit
path, including an escaping exception (an integer `SystemExit.code` is
preserved). All seven migrated launchers route through both seams; none calls
the builder directly; and an `ast` guard in the seam meta-test fails if any
denylisted operation — filesystem assertions, docker, subprocess, state dumps,
writers — precedes admission. The guard was verified to bite: against the
pre-fix tree it reports four violations, two of which no review round had
reached.

Refusals are one family. `BenchmarkAdmissionRefused`, `RuntimeAttestationRefused`
and `SeedShapeRefused` are all `RuntimeError` subclasses carrying a typed
reason, deliberately not `SystemExit` — a `SystemExit`-raising assertion had
made a refusal handler dead code, because `SystemExit` is not an `Exception`
subclass. A behavioural parity test computes what `raise SystemExit(main())`
hands the OS for each launcher and asserts it EQUALS the `exit_code` the
manifest records, so a recorded status can no longer diverge from reality.

`runtime_attestation()` records both facts about a live server — the HTTP
`runtime_version` from the frozen `/api/health` contract and the local
HEAD/VERSION of its checkout — and requires the contracted field: a bare
`version` key now refuses with the non-overridable `runtime_version_absent`, so
an unrelated HTTP server can no longer attest. `OBO_ALLOW_EVOLVED_VOLUME` waives
only `runtime_skew`, in the shell as well as in Python, and commit availability
is decided before skew so a missing commit cannot be mislabelled. Lineage is a
descent check (`merge-base --is-ancestor`), never equality, so an evolution run
legitimately moving HEAD forward is not corruption.
`CAMPAIGN_FATAL_PROVENANCE_REASONS` is a single shared authority consumed by
both SWE-Pro drivers, which now stop the schedule immediately — before any
volume archival — instead of one driver burning every task.

Grading gains a third state: `pass|fail|ungraded` with typed reasons beside the
UNCHANGED headline formula, plus `grade_summary.json`, and the probe
orchestrator reads that artifact instead of scraping log tokens and refuses to
publish a grade that a failed or stale grader produced. ProgramBench's ledger is
append-only at both the run root and the instance directory, skip rows included.
`common/manifests.py::write_json` is atomic and byte-identical, importing
`ouroboros.utils` lazily so the module stays stdlib-only for the container-side
harbor agent, and `openrouter_key_remaining()` reads the authoritative
`limit_remaining`.

Egress isolation was built in this phase and is NOT part of this release: it is
off by default per owner decision, it produced a finding in five separate review
rounds, and round 10's was a direct recurrence of round 5's, so it was extracted
and deferred with its diagnosis preserved. Solve containers run the same open
network as before v6.75.0. The measured evidence stays in METHODOLOGY: the
official SWE-bench Pro harness does not regulate the solve container's network
at all (`--block_network` applies to the EVAL container), and 31 of 287 attempted
instances are musl/Alpine, 84% of which previously produced a non-empty patch.

GAIA, CL-Bench, Terminal-Bench and OSWorld keep their pre-v6.75.0 behaviour here
and migrate in their own phases. No `ouroboros/` runtime behaviour changes.

Reviewed through eleven rounds of the production commit gate (advisory, triad
`claude-fable-5` + `gpt-5.6-sol` + `gemini-3.5-flash` at high effort, scope
`claude-fable-5`): 24 findings, 22 fixed and 2 refuted with the evidence recorded
in the changelog. Per-phase tags are deliberately not created — a single release
tag lands with the campaign synthesis, an owner-approved deviation from the
tag-per-commit norm.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-07-25 18:24:25 +00:00
Anton Razzhigaev
65e0f80119 clb: honor template-declared reviewer roster in render_run_settings
render_run_settings unconditionally rewrote OUROBOROS_REVIEW_MODELS to the
triple-slot parity roster, defeating a campaign's declared single-reviewer
config even after the env-forward fix. Template declarations now win; the
triple roster remains the default when the template stays silent.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-23 19:46:13 +00:00
Anton Razzhigaev
13c50b7572 clb: forward full campaign knob set launcher->adapter env; adapter env-override patch
_overrides() hardcoded CC-parity defaults (runtime=advanced, triple reviewer
list, uniform effort) and ignored the declared campaign config — 'declared vs
applied' drift on every docker-path run. run_clb.py now forwards runtime mode,
reviewer list, split review efforts, context mode and workers from the settings
template; the new operator patch makes _overrides() honor those env exports.
Also fixes CLBENCH_SOLVE_DISABLED_TOOLS being join()ed char-by-char when the
template declares it as a string.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-23 19:36:17 +00:00
Anton Razzhigaev
4d410e6dfe bench: mandate clean-seed pre-flight for submittable runs; commit TB anti-lookup integrity note
A dirty seed worktree poisons run_manifest provenance (describe ...-dirty)
and disqualifies the run from leaderboard submission. Documented in caps in
benchmarks README and TB METHODOLOGY. Also commits the anti-lookup integrity
instruction that was live (uncommitted) in the v6.74.5 campaign seed, so the
running config is fully reproducible from the repo.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-23 18:20:14 +00:00
Anton Razzhigaev
8ad83e85af bench: disable schedule_subagent in TB/PB/OSWorld adapters (no-swarm submittable)
Mirrors the CLB no-swarm change (36ab50c): each bench adapter now withholds
schedule_subagent so a single-agent submittable run has zero delegation.
TB _disabled_tools(), PB schemas.py task-body, OSWorld _effective_disabled_tools().
Scoring/tasks untouched.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-23 17:05:00 +00:00
Anton Razzhigaev
36ab50c021 clb: forward review-mode + subagent-depth from launcher; disabled-tools from env
run_clb.py._sanitized_child_env now forwards OUROBOROS_TASK_REVIEW_MODE and
OUROBOROS_MAX_SUBAGENT_DEPTH (previously silently default auto / depth 2), and
the CLB bridge adapter honors CLBENCH_SOLVE_DISABLED_TOOLS (operator patch
clb_disabled_tools_env.v6745.patch) — together they make a submittable
review-required / no-swarm CLB run configurable from the launcher.

Scoring/tasks/grader untouched; only our launcher + our systems/ouroboros plugin.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-23 07:19:57 +00:00
Anton Razzhigaev
e30f76a82d merge: integrate main-only CLB docs commit (#73) into the v6.74.4 line 2026-07-22 01:09:15 +00:00
Anton Razzhigaev
1fcb1d32c3 feat(v6.74.4): workspace-tree freeze directives (mitigation) + truthful ProgramBench submission contract
Root cause (PB cmatsuoka__figlet smoke): the agent committed a compiling state, then broke the tree with one last uncommitted edit as the acceptance improvement loop hit its pass cap; the harness ships the LIVE tree, so the verified commit protected nothing — all salvage machinery guards the answer TEXT only. Prompt-only fix (P5) over existing channels (P7): the acceptance rails line marks the last admitted improvement pass (passes_done+1 >= cap, cap>0) as FINAL and, for workspace deliveries (canonical is_workspace_mode() with an attribute fallback), EVERY workspace improvement capsule carries the tree directive — a deadline or cost rail can end the loop between capsules (triad r1) — keeping the tree at a VERIFIED state (rebuild, verify, and commit if the task calls for a commit; revert unverified edits); the 10% deadline flush AND the cost wrap-up note gain one shared commit-NEUTRAL tree sentence (acting self_worktree subagents cannot commit; a moved HEAD fails patch capture closed), byte-identical for non-workspace tasks; the ProgramBench instruction now states the exporter's true submission contract (SOURCE tarball from the CURRENT tree state; .git, root binaries, .ouroboros/ and named build/cache noise excluded at any depth; run ./compile.sh one final time), replacing the false fresh-checkout framing. Tests pin the pacing/rails seam, the workspace gating on both axes, byte-identical non-workspace texts, the real tarball contract, and the instruction truth phrases. P9 carriers bumped to 6.74.4; changelog row added. Disclosed residual (this is a MITIGATION of the incident class, not a closure): a forced tool-less exit — deadline grace or budget stop crossed inside one long round with no pacing note or capsule in the terminal stretch — can still ship an unverified last edit; the structural verification-freshness seam is a filed follow-up pending an owner decision (triad r1-r3, codex full-access review concur).
2026-07-22 00:37:27 +00:00
ndrew1337
8e3bbe8813
docs(benchmarks/continual_learning): v6.71.1 validated baseline + operations runbook (#73)
* docs(benchmarks/continual_learning): v6.71.1 validated baseline, ops runbook, refreshed adapter pins

- Add RUNBOOK.md: field-tested at-scale recipe from the 2026-07-20 full
  6-domain campaign (validated config incl. max_workers=3 with the Docker-VM
  memory-sizing formula, mandatory clone-sweeper/container-reaper daemons,
  smoke -> one-seed -> 5-seed submission flow per the official submitting
  docs, known loss classes and their closures).
- METHODOLOGY.md: add section 9 with the v6.71.1 full-suite 1-seed results
  (6-domain normalized average +0.259 vs published top-1 +0.196 and
  Claude Code +0.185) and the review-mode ablation verdict (pin 1 pass);
  update the honest-limits section accordingly.
- README.md: point at RUNBOOK.md, refresh the adapter pin (3ec3761: network
  outage hold, format-repair round, review-passes override) and the handoff
  bundle name, replace the stale internal worker-pool guidance (4 -> 3, with
  the OOM rationale).

* docs(benchmarks/continual_learning): reflect the clbench_remote -> remote_work skill rename

* docs(benchmarks/continual_learning): review fixes — canonical domain names, max_workers and adapter-pin qualifiers, #9 status

Triad+scope review fixes on the maintainer rerun (base v6.74.3):

- METHODOLOGY §9 results table: use the bench's canonical task names —
  blind_spectrum_monitoring (bsm) and sales_prediction — instead of the
  non-canonical black_scholes (bsm) / sales_analytics, so rows map onto
  the §1 domain list.
- METHODOLOGY §4: OUROBOROS_MAX_WORKERS disclosure now separates the
  2026-07-01 reference-run value (4) from the at-scale value validated by
  the v6.71.1 campaign (3, Docker-VM OOM rationale in RUNBOOK.md),
  removing the contradiction with README/RUNBOOK.
- METHODOLOGY §3: qualify the 56764d6 adapter pin as the §8 reference-run
  pin next to the v6.71.1 campaign pin 3ec3761.
- RUNBOOK: pgasawa/continual-learning-bench#9 merged 2026-07-19 — state
  the mixed-metric condition in the past and point at scoring with a
  leaderboard checkout that includes the fix.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>

---------

Co-authored-by: Anton Razzhigaev <razzant@users.noreply.github.com>
Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
2026-07-22 01:38:13 +03:00
Anton Razzhigaev
68c119cfa9 feat(v6.74.0): acceptance review becomes a reviewer-authored terminating dialogue
A: verdict-visible improvement capsule (verdict+tier+real blocker via one panel_reason reducer, open obligation ids, money/time/rounds/passes rails line, three real moves); reviewer-authored obligation identity (disposition_kind new|re_raise validated against the host catalog, fail-closed to new, per-pass dedup, reuse-immutable) with surviving rebuttals (previous_disposition/previous_reason/reopened_count); typed dialogue_status (continue_actionable|unreachable_here|stable_disagreement) reduced over ALL contract-valid actors with the panel quorum — termination is reviewer-authored or a real rail, never a host counter.
B: two cache-marked review-prompt segments (governance + task-stable contract), slot label off byte 0, breakpoint cap asserted on the final payload.
C: GAIA sandbox attachment staging (prompt-declared /shared_files channel, exact shared-root lookup, per-file provenance, typed per-sample infra error); CLB acceptance-claims operator patch (receipt-bound claims, knowledge nudge in the steer slot, bounded cost-finality wait); SWE-Pro cumulative shard budget (auto_run derives per_task x scheduled, run_pro seeds from cumulative spend); CLI/PB bounded task_cost_finalized waits for completed/degraded only.
D: light-mode shell guard resolves cwd before judging repo targets (resource-root label false-block fixed); post-task cost publish uses try_get_bridge.
E: generative surface-duty in commit/plan review checklists; all P9 carriers bumped.

Reviewed: 2 adversarial rounds + production triad+scope (PASSED) + codex final (GO); smoke 5x5 on all five benches verified the dialogue/staging/budget mechanics live.
2026-07-21 19:57:55 +00:00
Anton Razzhigaev
2e253c4e16 feat(bench/tb): forward OUROBOROS_CONTEXT_MODE into task containers
The installed-agent adapter assembles the in-container env from an explicit
whitelist; OUROBOROS_CONTEXT_MODE was not on it, so context-ablation runs
(context_mode=low) silently ran at the default "max". Forward the key
(env-first, host settings fallback) like the other model/effort slots.
No behavior change when the variable is unset.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-19 03:32:28 +00:00
Anton Razzhigaev
a776639fcb feat(v6.66.0): honest mutation attribution, attributed staging, environment-correct Python, auditable Skill Review history, and a drift-proof operator review wrapper
Operator phase 2 of the owner-approved 6.65-6.67 release cycle. The physical
mutation lease/holder subsystem was deliberately descoped by the owner:
attribution is evidence-only (root-task baseline, terminal candidate snapshot,
attributed commit staging, projection into acceptance/review evidence, no
structural outcome veto). Ships the surface-aware Python interpreter resolver,
auditable Skill Review rounds/history, the single task-tree disposition
authority with cancel-wins, the SSOT operator review wrapper with typed exit
codes, the parallel hermetic pytest preflight, and the chronic red-CI
light-model test fix.

Review: advisory=skipped (prompt-size cap, non-blocking), triad
fable-5/gpt-5.6-sol/gemini-3.5-flash all responded, scope fable-5 responded,
aggregate PASSED (run 20260716T221730Z, $16.38). Full non-serial+serial pytest
green; ruff -F clean.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-16 22:25:04 +00:00
Anton Razzhigaev
291e825c56 fix: release Ouroboros v6.64.2 benchmark integrity hotfix 2026-07-15 00:20:19 +00:00
Anton Razzhigaev
6a357d338d release: v6.64.0 2026-07-14 18:55:54 +00:00
Anton Razzhigaev
0713bb3f58 bench(tb): launch via named job config for leaderboard-valid submissions (operator, approved)
TB2.1 leaderboard static analysis matches config.agents[].name against the
agent name trials report; bare --agent-import-path records name=null, which
can never match (terminal-bench-2-1#121) and is unfixable after upload.

- run_tb.py: generate agent_job_config.json (name = adapter class name() +
  import_path + kwargs) and launch harbor with -c instead of bare agent
  flags; OUROBOROS_EFFORT_TASK at launch is recorded as the declared
  reasoning_effort of the submission key.
- harbor_installed_agent.py: accept the reasoning_effort kwarg and forward
  it into the container as OUROBOROS_EFFORT_TASK (declared == effective).
- README/METHODOLOGY: replace the removed 'harbor leaderboard submit' CLI
  flow with the verified GitHub-PR flow (terminal-bench-2-1 lb submit,
  promotion, /judge, /apply), document the named-config requirement,
  trajectory_path pitfalls and the TUS upload fix pointer.
- tests: assert the new -c job-config shape (name/import_path/kwargs/effort).
2026-07-14 18:47:48 +00:00
Anton Razzhigaev
e180954f15 docs(osworld): cu_bridge — start the isolated server with unix_computer_use pre-enabled
The v6.62.0/#64 net-permission change removes unix_computer_use from the native
auto-enable class, and the server loads enabled extensions only at startup
(reload_all). A server started BEFORE the runner's _enable_skill write will not
hot-reload it, so the skill's ext_* tools come back "Not found" and the agent
declares the task infeasible. Documented in the cu_bridge README: seed the skill
enabled before server start (the parallel orchestrator already does — fresh
isolated server per task after seeding), or restart after enabling.

Found running a 3-task OSWorld smoke (all reward 1.0 once the skill was enabled
before server start). Docs-only.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-10 21:40:22 +00:00
Andrei Kaznacheev
1543c2fe42
Add remote backends to unix computer use (#64)
* Add remote backends to unix computer use

* fix(unix_computer_use): pass skill review + runner/test cleanup

- screenshots returned in place from skill_job_dir (drop data/uploads writes) — path confinement
- confine target_file reads to the skill state dir (no arbitrary path read)
- add _ssh_scp_source (scp -P + single host:path token), fixing ssh_macos screenshot
- declare runtime: python3 in SKILL.md (executable extension)
- drop unused --model arg from run_cu_bridge_agent (was misleading provenance)
- update remote-screenshot test to assert confinement (OS-agnostic, no /uploads)

Co-authored-by: Cursor <cursoragent@cursor.com>

* fix(computer-use): actually deliver screenshots to the model

- view_image: allow reading skill job/state outputs (state/skills/*) so
  screenshots the unix_computer_use skill produces are view_image-able
- plugin._downscale: use in-process PIL as the primary resizer so the
  screenshot is ALWAYS downscaled to the WXGA cap (1280x720) with a correct
  image->input coord_transform, instead of silently no-oping on hosts without
  sips/ImageMagick (which left a full-res image + identity transform while
  view_image re-downscaled independently -> clicks landed ~1.2x off-target)
- run_cu_bridge_agent: drop the fastdtw/easyocr import stubs that made vlc/OCR
  evaluators raise (the real deps are installed)

Co-authored-by: Cursor <cursoragent@cursor.com>

* fix(osworld): give the agent the VM sudo password in the prompt

OSWorld ships user/password = user/password (client_password) and its docs say
the agent needs it for sudo tasks (create users, start services, install pkgs).
The bridge created the env with the default password but never told the agent,
so sudo-dependent tasks (e.g. create-SSH-user) failed after the model guessed
wrong passwords. Inject env.client_password into the task prompt.

Co-authored-by: Cursor <cursoragent@cursor.com>

* feat(osworld): enable DataImpulse proxy pool for proxy-flagged tasks

OSWorld tags ~52 web/multi_apps tasks with "proxy": true and expects the env to
route the VM through a residential proxy (DataImpulse) to avoid bot/geo blocks.
Wire enable_proxy into the CU bridge: resolve the proxy config from
<osworld_root>/evaluation_examples/settings/proxy/dataimpulse.json (or
PROXY_CONFIG_FILE), export it before importing desktop_env (setup.py loads the
pool at import), and pass enable_proxy accordingly. Enabled only when the config
exists so non-proxy runs and the other 317 tasks are unaffected. Creds file is
git-ignored, not committed.

Co-authored-by: Cursor <cursoragent@cursor.com>

* fix(osworld bench): propagate task-review knobs + verify-final-state preamble

- server_runner: allow OUROBOROS_TASK_REVIEW_MODE / OUROBOROS_REVIEW_ENFORCEMENT
  through the isolated-settings allowlist so settings.json review policy is honored.
- run_cu_bridge_agent preamble: before the verdict, verify the actual observed
  final VM state satisfies the task (generic, no task-specific hints).

Co-authored-by: Cursor <cursoragent@cursor.com>

* feat(v6.62.0): unix_computer_use remote backends + OSWorld cu_bridge finalization

Finalizes PR #64 for merge into the ouroboros branch (origin/ouroboros merged
in; base retargeted from main to ouroboros). Confirmed fixes on top of kazzand's
remote-backend feature, converged over five triad+scope review rounds.

skills/unix_computer_use/plugin.py (remote osworld_http/ssh_macos backends):
- scroll x100 multiplier removed (X11 pyautogui is 1 event per detent, 1:1).
- honest ok: _osworld_result_ok() requires HTTP 200 AND guest returncode 0/
  status success (the in-VM server returns 200 even on nonzero exit).
- unicode type_text pastes non-ASCII via the in-VM clipboard (typewrite fallback).
- keys: delete/backspace press BackSpace; fwd-delete presses Delete.
- fail-closed connection selection (verified complete): _is_remote() is name-based
  so EVERY input tool routes through the guarded remote path; _active_connection()
  marks any non-local connection that is missing/disabled/unknown-backend as
  disabled and all tools refuse ("unusable") before any local dispatch — a
  remote-aimed click can never hit the host desktop (behavioral test proves local
  dispatch is never reached). Atomic registry writes.
- remote screenshot: 20 MB download cap + non-PNG rejection.

devtools/benchmarks/osworld/run_cu_bridge_agent.py:
- infeasible detection reads only final-answer fields.
- ax_tree disabled by default (--allow-a11y); guards for live-server + live-data-dir.
- dataset pin + budget counters; --settings-path defaults to <data-dir>/settings.json
  so the max_rounds disclosure reflects the isolated server; _publish_target writes
  the registry atomically.
- untrusted-task host lockdown: rather than a fragile denylist, the task is
  submitted with a COMPUTED denylist = all core tools minus a small allowlist
  (skill discovery/enable, view_image, read-only inspection). Every host
  execution/mutation/VCS/GitHub/service/self-mod/chat surface — present or future
  — is blocked by construction; the VM is driven only through the skill's ext_*
  tools.
- honest manifest: official_actions=false + official_reset_evaluate=true +
  action_channel="guest_execute_not_env_step" (matches METHODOLOGY §7).

Core: ouroboros/tools/vision.py root widening kept (uploads + state/skills; same
trust boundary as read_file; rejection message + tool descriptions name the new
root; also fixes the LOCAL vision loop); ouroboros/review.py bumps
MAX_TOTAL_FUNCTIONS 3775->3805, grandfathers skills/unix_computer_use/plugin.py
(repo-relative key), and adds a shared module_is_grandfathered() matcher used by
BOTH the smoke gate and compute_complexity_metrics (codebase_health) so the two
consumers can't diverge and a future skill's plugin.py is not silently exempted.

Version 6.62.0 across all carriers; docs/ARCHITECTURE.md (skill remote backends +
cu_bridge runner), docs/DEVELOPMENT.md (grandfather prose), SKILL.md, osworld
README + METHODOLOGY.md §7 updated.

Tests: 3 stale assertions updated; new remote scroll/ok/unicode/backspace/fail-
closed(missing+disabled+unknown-backend + behavioral proof)/screenshot-cap/real-
PIL-downscale/atomic-registry/settings-default/allowlist-complement/grandfather-
matcher tests; tests/test_osworld_cu_bridge.py.

Accepted advisory tradeoffs (review dissent, non-blocking, documented):
- add_connection keeps 10 keyword params (first-class agent tool schema).
- ssh_macos type_text of repr escape sequences types literally: pre-existing
  quirk on a SECONDARY backend; osworld_http (the OSWorld path) is unaffected.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>

---------

Co-authored-by: Ouroboros <ouroboros@local.mac>
Co-authored-by: a.kaznacheev <a.kaznacheev@sdgroup.ai>
Co-authored-by: Cursor <cursoragent@cursor.com>
Co-authored-by: Anton Razzhigaev <razzant@users.noreply.github.com>
Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
2026-07-10 22:16:29 +03:00