feat(runtime): read-only accessors for the compiled identity, and use one
el_cgi_init loaded the declared identity into runtime globals and printed it, and
nothing read it back out. No accessor existed and it writes no state, so every
consumer still read identity from the mutable state store. studio.el's registry
read state_get("soul_principal") — a key with no producer anywhere — and reported
an empty principal under a heading reading 'Principal Covenant v1'.
Adds cgi_name/cgi_dharma_id/cgi_principal/cgi_network/cgi_engram. READ-ONLY on
purpose: there is deliberately no setter. Publishing these into the state store
would have been one line and would have recreated exactly the runtime-mutable copy
IDPROTO claims 1-2 forbid ('not modifiable by any runtime mechanism including
environment variables, configuration files, or API calls').
dharma_registry now reads the compiled constant. cgi_id keeps its state read
deliberately — the runtime instance id is a different fact from the compiled
dharma_id, and conflating them would hide a binary running under an id its own
declaration never claimed.
Measured, same corpus, binary the only variable:
deployed engine -> "principal":""
accessor build -> "principal":"william-christopher-anderson"
interface: 110 routes in, 110 out, nothing removed
Requires the codegen fix in el (fix/cgi-identity-emission); without it the
declaration is never compiled in and the accessors return empty.
Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -53,8 +53,23 @@ fn handle_config(method: String, body: String) -> String {
|
||||
}
|
||||
|
||||
fn dharma_registry() -> String {
|
||||
// COMPILED IDENTITY, not state (2026-08-09). soul_principal had no producer at
|
||||
// all — the #132 gate flagged it as a dead read and the registry reported an
|
||||
// empty principal under a heading that says "Principal Covenant v1". The value
|
||||
// was never missing: it is declared in soul.el's cgi block, and as of the
|
||||
// codegen fix it is compiled into the binary and loaded at startup.
|
||||
//
|
||||
// Read it from the compiled constant rather than the state store. The design is
|
||||
// explicit that this identity is "not modifiable by any runtime mechanism
|
||||
// including environment variables, configuration files, or API calls" — so
|
||||
// publishing it into state (the cheap fix) would have recreated exactly the
|
||||
// mutable copy it forbids. cgi_principal() is read-only and has no setter.
|
||||
//
|
||||
// cgi_id keeps its state read deliberately: the RUNTIME instance id is a
|
||||
// different fact from the compiled dharma_id, and conflating them would hide
|
||||
// the case where a binary runs under an id its declaration never claimed.
|
||||
let cgi_id: String = state_get("soul_cgi_id")
|
||||
let principal: String = state_get("soul_principal")
|
||||
let principal: String = cgi_principal()
|
||||
return "{\"registry\":[{\"cgi\":\"" + cgi_id + "\","
|
||||
+ "\"principal\":\"" + principal + "\","
|
||||
+ "\"covenant\":\"Principal Covenant v1\","
|
||||
|
||||
+19
@@ -5634,6 +5634,25 @@ void el_cgi_init(el_val_t name, el_val_t dharma_id, el_val_t principal,
|
||||
}
|
||||
|
||||
|
||||
/* ── Compiled-identity accessors (2026-08-09) ─────────────────────────────────
|
||||
* el_cgi_init loads the declaration into these globals at startup and printed
|
||||
* them, and NOTHING read them back out — no accessor existed, and el_cgi_init
|
||||
* writes no state. So a binary carried its declared identity and every consumer
|
||||
* still read it from the mutable state store, which is exactly what IDPROTO
|
||||
* claims 1-2 forbid ("not modifiable by any runtime mechanism including
|
||||
* environment variables, configuration files, or API calls").
|
||||
*
|
||||
* These are READ-ONLY on purpose. There is deliberately no setter: publishing
|
||||
* the values into the state store would have been one line and would have
|
||||
* recreated the mutable copy the design prohibits. A caller can read the
|
||||
* compiled identity; nothing can change it after el_cgi_init.
|
||||
*/
|
||||
el_val_t cgi_name(void) { return EL_STR(_el_cgi_name ? _el_cgi_name : ""); }
|
||||
el_val_t cgi_dharma_id(void) { return EL_STR(_el_cgi_dharma_id ? _el_cgi_dharma_id : ""); }
|
||||
el_val_t cgi_principal(void) { return EL_STR(_el_cgi_principal ? _el_cgi_principal : ""); }
|
||||
el_val_t cgi_network(void) { return EL_STR(_el_cgi_network ? _el_cgi_network : ""); }
|
||||
el_val_t cgi_engram(void) { return EL_STR(_el_cgi_engram ? _el_cgi_engram : ""); }
|
||||
|
||||
/* ── Batch 3: Engram in-process graph store ──────────────────────────────── */
|
||||
/*
|
||||
* Single global EngramStore allocated lazily on first call. All node and
|
||||
|
||||
@@ -782,6 +782,14 @@ el_val_t trace_span_start(el_val_t name);
|
||||
el_val_t trace_span_end(el_val_t span_handle);
|
||||
el_val_t emit_event(el_val_t name, el_val_t duration_ms);
|
||||
|
||||
/* Compiled-identity accessors — read-only by design (2026-08-09). */
|
||||
el_val_t cgi_name(void);
|
||||
el_val_t cgi_dharma_id(void);
|
||||
el_val_t cgi_principal(void);
|
||||
el_val_t cgi_network(void);
|
||||
el_val_t cgi_engram(void);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user