Skip to content

Studio Federation API

sc_neurocore.federation is the optional Hub-facing Studio federation surface. It is separate from the local FastAPI Studio app under sc_neurocore.studio: the federation package emits schema-A capability manifests, schema-B evidence bundles, and verifiable-honesty envelopes for SC-NeuroCore result claims.

Install the optional platform contract before importing it:

Bash
pip install "sc-neurocore[federation]"

Federation requires Python 3.11 or newer and pins scpn-studio-platform>=0.11,<0.12; the base library still supports Python 3.10. Environments without that platform SDK should not import this package; tests use pytest.importorskip so the base CI lane stays independent of the optional federation dependency.

Capability Manifest

Use build_manifest() to produce the schema-A manifest consumed by the Studio Hub:

Python
from sc_neurocore.federation import build_manifest

manifest = build_manifest()
assert manifest.studio == "sc-neurocore"

The manifest declares contract era v2. A consumer that supports only v1 refuses it; a dependency version alone does not establish era compatibility. The manifest advertises eight verbs:

Verb Purpose Evidence schema
encode Convert float values into stochastic bitstreams. studio.bitstream-encoding.v1
simulate Run stochastic-computing inference. studio.sc-inference.v1
analyse Extract spike-train analysis results. studio.spike-analysis.v1
benchmark Measure backend throughput against the NumPy reference. studio.backend-benchmark.v1
validate Compare fixed-point reference and RTL co-simulation. studio.cosim-parity.v1
compile Lower a model to synthesisable RTL. studio.rtl-compilation.v1
synthesise Record synthesis resource/timing evidence. studio.fpga-deployment.v1
deploy Record FPGA deployment evidence. studio.fpga-deployment.v1

The committed manifest artifact lives at docs/_generated/studio_manifest.json and is generated by:

Bash
python tools/emit_studio_manifest.py
python tools/emit_studio_manifest.py --check

The digest covers the declared verbs and evidence schemas, not the current git state, so the manifest is stable across checkouts with the same federation surface.

Evidence Bundles

sc_inference_evidence() maps a stochastic inference result into a measured software evidence bundle. It renders as reference-validated only when the accelerated backend is bit-identical to the NumPy reference for the fixed seed. Otherwise the claim is bounded and rejected by the shared platform lattice.

fpga_deployment_evidence() maps a pre-silicon synthesis/co-simulation result into a measured bundle on the simulator substrate. It renders as reference-validated only when the RTL co-simulation is bit-exact and re-checked at source; a mismatch becomes validation-gap. A named FPGA synthesis target does not establish that a bitstream executed on a physical board.

Python
import hashlib
from datetime import datetime, timezone

import numpy as np
from scpn_studio_platform.evidence import Freshness

from sc_neurocore.accel import pack_bitstream, sc_forward
from sc_neurocore.federation import (
    ScInferenceResult,
    sc_inference_evidence,
)

started = datetime.now(timezone.utc).isoformat()
length, seed = 257, 173
bits = np.random.default_rng(31).integers(0, 2, size=(2, 3, length), dtype=np.uint8)
weights = np.stack([pack_bitstream(row) for row in bits.reshape(6, length)]).reshape(2, 3, -1)
inputs = np.array([0.125, 0.5, 0.875], dtype=np.float64)
reference = sc_forward(weights, inputs, length=length, seed=seed, backend="numpy")
measured = sc_forward(weights, inputs, length=length, seed=seed, backend="rust")
np.testing.assert_array_equal(measured, reference)
source = weights.astype("<u8").tobytes() + inputs.astype("<f8").tobytes()
source += seed.to_bytes(4, "little") + length.to_bytes(4, "little")
result = ScInferenceResult(
    active_backend="rust",
    reference_backend="numpy",
    max_abs_error=float(np.max(np.abs(measured - reference))),
    bitstream_length=length,
    input_digest="sha256:" + hashlib.sha256(source).hexdigest(),
    result_digest="sha256:" + hashlib.sha256(measured.astype("<f8").tobytes()).hexdigest(),
)

bundle = sc_inference_evidence(
    result,
    operator="opaque:tenant-1",
    studio_version="3.16.0",
    started=started,
    ended=datetime.now(timezone.utc).isoformat(),
    freshness=Freshness.VERIFIED_AT_SOURCE,
)

This example requires the Rust engine as well as the federation extra. It hashes the actual retained input encoding and output bytes after comparing both backends.

Source freshness is explicit. Pass Freshness.VERIFIED_AT_SOURCE only after recomputing the result or checking the retained source artefacts against their digests. Bit-exact inference or co-simulation without that re-check is refused. An unchecked mismatch remains a boundary claim; it never acquires freshness automatically. Historical signed envelopes remain immutable: changing a digest or adding freshness requires authentic new producer evidence and a new seal. Published Platform 0.11.2 and the deployed consumer require separate verification; installing an SDK does not establish admission by a live Hub. In 0.11.2 the low-level manifest validator accepts explicit supported_eras, while its loader and aggregation command retain the default v1 policy. Full v2 consumption requires a consumer that also exposes explicit era negotiation through those entry points and its deployment wrapper; no fallback changes the manifest.

Verifiable-Honesty Envelopes

The attestation helpers wrap platform seals so a rendered claim grade can be verified from signed evidence:

  • seal_sc_inference() uses recompute mode for SC inference against NumPy.
  • attest_fpga_deployment() signs a pre-silicon result pack in attestation mode. The signature identifies the producer; it is not hardware-rooted attestation.
  • verify_envelope() recomputes the grade by schema and detects stripped, forged, or mismatched rendered claims.

Both seal functions take the same explicit freshness argument as the bundle mappers. A source-unchecked bit-exact result is refused before signing. Freshness is part of the signed unit and the regrader checks it; legacy envelopes without that declaration cannot acquire a validated grade by changing a rendered badge. Signed numeric scalars use exact decimal strings, preserving signatures across browser JSON transport. Boolean values cannot stand in for a numeric zero error. Wire counts must be integers in JavaScript's exact range 0..2^53−1; bitstream length must also be positive. Larger integers are refused before signing and cannot earn a validated grade when received as raw wire data.

FpgaArtifact entries require a complete lowercase sha256:<64 hex characters> address and non-empty role/media type. The caller checks actual artifact bytes before declaring source freshness. A pre-silicon parity claim earns the validated grade only when a cosim-transcript artifact backs it. Its result-pack digest binds the complete signed unit, including report fields, artifact addresses and freshness. Physical board execution, hardware latency and measured power need their own device evidence; the current co-simulation mapper does not assert them.

Reference

sc_neurocore.federation

SC-NeuroCore's STUDIO federation vertical on the scpn-studio-platform contract.

Hub-facing federation surface (schema-A capability manifest + schema-B evidence bundles), distinct from the local FastAPI Studio web app under sc_neurocore.studio. Importing this package requires the federation extra (pip install sc-neurocore[federation] → scpn-studio-platform>=0.11,<0.12, the Python 3.11+ SDK with the verifiable-honesty :mod:~scpn_studio_platform.seal module); a clean ModuleNotFoundError is raised when the platform SDK is absent, which is why tests guard with pytest.importorskip("scpn_studio_platform").

Example

from sc_neurocore.federation import build_manifest, fpga_deployment_evidence manifest = build_manifest() manifest.studio 'sc-neurocore'

PLATFORM_SDK_RANGE = '>=0.11,<0.12' module-attribute

The platform SDK SemVer range the studio builds on (matches the federation extra).

PROTOCOL_VERSION = '1' module-attribute

The SYNAPSE wire protocol version the studio pins.

STUDIO_VERSION = _resolve_studio_version() module-attribute

The SC-NeuroCore studio version this manifest stamps (source package version).

NEUROCORE_VERBS = (ENCODE, SIMULATE, ANALYSE, BENCHMARK, VALIDATE, COMPILE, SYNTHESISE, DEPLOY) module-attribute

Every verb the SC-NeuroCore studio advertises, in manifest order.

STUDIO_ID = 'sc-neurocore' module-attribute

The studio identifier this vertical implements (also the federation name).

FpgaArtifact dataclass

A content-addressed artifact backing a pre-silicon co-simulation claim.

Parameters

role What the artifact is — e.g. "synthesis-timing", "synthesis-utilisation", "cosim-transcript" (the bit-exactness proof), or "bitstream". digest SHA-256 of the artifact ("sha256:<hex>"); the identity that binds the claim to the real file. media_type The artifact's media type (e.g. "text/vivado-timing").

Raises

ValueError If a field is blank or the digest is not a lowercase SHA-256 address.

Source code in src/sc_neurocore/federation/attestation.py
Python
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
@dataclass(frozen=True)
class FpgaArtifact:
    """A content-addressed artifact backing a pre-silicon co-simulation claim.

    Parameters
    ----------
    role
        What the artifact is — e.g. ``"synthesis-timing"``, ``"synthesis-utilisation"``,
        ``"cosim-transcript"`` (the bit-exactness proof), or ``"bitstream"``.
    digest
        SHA-256 of the artifact (``"sha256:<hex>"``); the identity that binds the claim
        to the real file.
    media_type
        The artifact's media type (e.g. ``"text/vivado-timing"``).

    Raises
    ------
    ValueError
        If a field is blank or the digest is not a lowercase SHA-256 address.
    """

    role: str
    digest: str
    media_type: str

    def __post_init__(self) -> None:
        """Reject blank descriptions and malformed content addresses."""
        if not all(
            isinstance(value, str) and value.strip() for value in (self.role, self.media_type)
        ):
            raise ValueError("FpgaArtifact fields must be non-empty")
        if not _valid_digest(self.digest):
            raise ValueError("FpgaArtifact digest must be a lowercase SHA-256 content address")

    def to_dict(self) -> dict[str, str]:
        """Return the JSON-serialisable mapping of the artifact."""
        return {"role": self.role, "digest": self.digest, "media_type": self.media_type}

__post_init__()

Reject blank descriptions and malformed content addresses.

Source code in src/sc_neurocore/federation/attestation.py
Python
91
92
93
94
95
96
97
98
def __post_init__(self) -> None:
    """Reject blank descriptions and malformed content addresses."""
    if not all(
        isinstance(value, str) and value.strip() for value in (self.role, self.media_type)
    ):
        raise ValueError("FpgaArtifact fields must be non-empty")
    if not _valid_digest(self.digest):
        raise ValueError("FpgaArtifact digest must be a lowercase SHA-256 content address")

to_dict()

Return the JSON-serialisable mapping of the artifact.

Source code in src/sc_neurocore/federation/attestation.py
Python
100
101
102
def to_dict(self) -> dict[str, str]:
    """Return the JSON-serialisable mapping of the artifact."""
    return {"role": self.role, "digest": self.digest, "media_type": self.media_type}

FpgaDeploymentResult dataclass

A path-free pre-silicon FPGA synthesis/co-simulation result.

Target device identity and synthesis reports do not attest physical execution.

Parameters

device The target device (e.g. "xc7z020-1clg400"). cosim_bit_exact Whether the synthesised RTL co-simulation matched the Q8.8 fixed-point reference bit-for-bit. lut_used, ff_used Look-up tables and flip-flops consumed by the synthesised design. worst_negative_slack_ns Worst negative slack at the target clock; >= 0 means timing closed. clock_mhz The synthesis target clock frequency, in MHz. result_digest SHA-256 of the bitstream / synthesis report.

Raises

ValueError If a resource count, co-simulation flag, clock, timing or digest is invalid.

Source code in src/sc_neurocore/federation/evidence.py
Python
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
@dataclass(frozen=True)
class FpgaDeploymentResult:
    """A path-free pre-silicon FPGA synthesis/co-simulation result.

    Target device identity and synthesis reports do not attest physical execution.

    Parameters
    ----------
    device
        The target device (e.g. ``"xc7z020-1clg400"``).
    cosim_bit_exact
        Whether the synthesised RTL co-simulation matched the Q8.8 fixed-point
        reference bit-for-bit.
    lut_used, ff_used
        Look-up tables and flip-flops consumed by the synthesised design.
    worst_negative_slack_ns
        Worst negative slack at the target clock; ``>= 0`` means timing closed.
    clock_mhz
        The synthesis target clock frequency, in MHz.
    result_digest
        SHA-256 of the bitstream / synthesis report.

    Raises
    ------
    ValueError
        If a resource count, co-simulation flag, clock, timing or digest is invalid.
    """

    device: str
    cosim_bit_exact: bool
    lut_used: int
    ff_used: int
    worst_negative_slack_ns: float
    clock_mhz: float
    result_digest: str

    def __post_init__(self) -> None:
        """Validate finite report values and their SHA-256 identity."""
        if not isinstance(self.device, str) or not self.device.strip():
            raise ValueError("FpgaDeploymentResult.device must be non-empty")
        if type(self.cosim_bit_exact) is not bool:
            raise ValueError("FpgaDeploymentResult.cosim_bit_exact must be a boolean")
        if not all(_wire_count(value) for value in (self.lut_used, self.ff_used)):
            raise ValueError(
                "FpgaDeploymentResult resource counts must be nonnegative safe integers"
            )
        if not _finite_number(self.clock_mhz) or self.clock_mhz <= 0.0:
            raise ValueError("FpgaDeploymentResult.clock_mhz must be finite and > 0")
        if not _finite_number(self.worst_negative_slack_ns):
            raise ValueError("FpgaDeploymentResult timing must be finite")
        if not _valid_digest(self.result_digest):
            raise ValueError(
                "FpgaDeploymentResult digest must be a lowercase SHA-256 content address"
            )

__post_init__()

Validate finite report values and their SHA-256 identity.

Source code in src/sc_neurocore/federation/evidence.py
Python
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
def __post_init__(self) -> None:
    """Validate finite report values and their SHA-256 identity."""
    if not isinstance(self.device, str) or not self.device.strip():
        raise ValueError("FpgaDeploymentResult.device must be non-empty")
    if type(self.cosim_bit_exact) is not bool:
        raise ValueError("FpgaDeploymentResult.cosim_bit_exact must be a boolean")
    if not all(_wire_count(value) for value in (self.lut_used, self.ff_used)):
        raise ValueError(
            "FpgaDeploymentResult resource counts must be nonnegative safe integers"
        )
    if not _finite_number(self.clock_mhz) or self.clock_mhz <= 0.0:
        raise ValueError("FpgaDeploymentResult.clock_mhz must be finite and > 0")
    if not _finite_number(self.worst_negative_slack_ns):
        raise ValueError("FpgaDeploymentResult timing must be finite")
    if not _valid_digest(self.result_digest):
        raise ValueError(
            "FpgaDeploymentResult digest must be a lowercase SHA-256 content address"
        )

ScInferenceResult dataclass

A path-free stochastic-computing inference result.

Parameters

active_backend The accelerated backend that produced the result (e.g. "rust"). reference_backend The bit-true reference backend (the NumPy floor). max_abs_error Maximum absolute difference between the active and reference outputs for the fixed seed; 0.0 means bit-identical. bitstream_length The stochastic bitstream length used. input_digest SHA-256 of the weights/inputs/seed. result_digest SHA-256 of the output firing rates.

Raises

ValueError If a count, error, backend or content address is invalid.

Source code in src/sc_neurocore/federation/evidence.py
Python
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
@dataclass(frozen=True)
class ScInferenceResult:
    """A path-free stochastic-computing inference result.

    Parameters
    ----------
    active_backend
        The accelerated backend that produced the result (e.g. ``"rust"``).
    reference_backend
        The bit-true reference backend (the NumPy floor).
    max_abs_error
        Maximum absolute difference between the active and reference outputs for
        the fixed seed; ``0.0`` means bit-identical.
    bitstream_length
        The stochastic bitstream length used.
    input_digest
        SHA-256 of the weights/inputs/seed.
    result_digest
        SHA-256 of the output firing rates.

    Raises
    ------
    ValueError
        If a count, error, backend or content address is invalid.
    """

    active_backend: str
    reference_backend: str
    max_abs_error: float
    bitstream_length: int
    input_digest: str
    result_digest: str

    def __post_init__(self) -> None:
        """Validate finite measured inputs and their SHA-256 identities."""
        if not _wire_count(self.bitstream_length) or self.bitstream_length == 0:
            raise ValueError("ScInferenceResult.bitstream_length must be a positive safe integer")
        if not _finite_number(self.max_abs_error) or self.max_abs_error < 0.0:
            raise ValueError("ScInferenceResult.max_abs_error must be finite and >= 0")
        if self.active_backend not in ("numpy", "rust") or self.reference_backend != "numpy":
            raise ValueError(
                "ScInferenceResult requires a supported backend and the NumPy reference"
            )
        if not _valid_digest(self.input_digest) or not _valid_digest(self.result_digest):
            raise ValueError(
                "ScInferenceResult digests must be lowercase SHA-256 content addresses"
            )

__post_init__()

Validate finite measured inputs and their SHA-256 identities.

Source code in src/sc_neurocore/federation/evidence.py
Python
121
122
123
124
125
126
127
128
129
130
131
132
133
134
def __post_init__(self) -> None:
    """Validate finite measured inputs and their SHA-256 identities."""
    if not _wire_count(self.bitstream_length) or self.bitstream_length == 0:
        raise ValueError("ScInferenceResult.bitstream_length must be a positive safe integer")
    if not _finite_number(self.max_abs_error) or self.max_abs_error < 0.0:
        raise ValueError("ScInferenceResult.max_abs_error must be finite and >= 0")
    if self.active_backend not in ("numpy", "rust") or self.reference_backend != "numpy":
        raise ValueError(
            "ScInferenceResult requires a supported backend and the NumPy reference"
        )
    if not _valid_digest(self.input_digest) or not _valid_digest(self.result_digest):
        raise ValueError(
            "ScInferenceResult digests must be lowercase SHA-256 content addresses"
        )

attest_fpga_deployment(result, artifacts, *, signer, freshness=None)

Seal pre-silicon co-simulation in attestation mode with a result pack.

The producer signs the complete path-free unit, including source freshness and artifact addresses. Its detached signature vouches for the producer's report; physical device execution and hardware-rooted attestation remain separate.

Parameters

result The path-free synthesis/deployment result. artifacts The content-addressed artifacts the claim rests on; at least one is required, and a cosim-transcript must be present for the claim to grade as validated. signer The studio's :class:~scpn_studio_platform.seal.keys.Signer. freshness Actual source re-check status; bit-exact reports require VERIFIED_AT_SOURCE before signing.

Returns

HonestyEnvelope A studio-self-attested measurement on the simulator substrate.

Raises

ValueError If artifacts are absent or bit-exact evidence lacks a source re-check.

Source code in src/sc_neurocore/federation/attestation.py
Python
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
def attest_fpga_deployment(
    result: FpgaDeploymentResult,
    artifacts: Iterable[FpgaArtifact],
    *,
    signer: Signer,
    freshness: Freshness | None = None,
) -> HonestyEnvelope:
    """Seal pre-silicon co-simulation in **attestation** mode with a result pack.

    The producer signs the complete path-free unit, including source freshness and
    artifact addresses. Its detached signature vouches for the producer's report;
    physical device execution and hardware-rooted attestation remain separate.

    Parameters
    ----------
    result
        The path-free synthesis/deployment result.
    artifacts
        The content-addressed artifacts the claim rests on; at least one is required, and
        a ``cosim-transcript`` must be present for the claim to grade as validated.
    signer
        The studio's :class:`~scpn_studio_platform.seal.keys.Signer`.
    freshness
        Actual source re-check status; bit-exact reports require
        ``VERIFIED_AT_SOURCE`` before signing.

    Returns
    -------
    HonestyEnvelope
        A studio-self-attested measurement on the ``simulator`` substrate.

    Raises
    ------
    ValueError
        If artifacts are absent or bit-exact evidence lacks a source re-check.
    """
    materialised = list(artifacts)
    if not materialised:
        raise ValueError("attestation requires at least one content-addressed artifact")
    _require_source_recheck(result.cosim_bit_exact, freshness)
    unit = _fpga_unit(result, materialised, freshness)
    pack_digest = content_digest(unit)
    attestation = {
        "provider": f"{STUDIO_ID}@{result.device}",
        "result_pack_digest": pack_digest,
        "provider_sig": base64.b64encode(signer.sign(pack_digest.encode("utf-8"))).decode("ascii"),
    }
    return seal(
        unit,
        signer=signer,
        grader=GRADER,
        verifiability_mode="attestation",
        exactness_class="bit-exact",
        attestation=attestation,
    )

regrade_fpga(unit)

Recompute the FPGA grade from the signed unit.

reference-validated requires source-rechecked, measured simulator evidence, valid report fields and an addressed co-simulation transcript. This grade is pre-silicon parity; no physical deployment or power claim is established.

Source code in src/sc_neurocore/federation/attestation.py
Python
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
def regrade_fpga(unit: Mapping[str, Any]) -> str:
    """Recompute the FPGA grade from the signed unit.

    ``reference-validated`` requires source-rechecked, measured simulator evidence,
    valid report fields and an addressed co-simulation transcript. This grade is
    pre-silicon parity; no physical deployment or power claim is established.
    """
    valid = (
        unit.get("schema") == FPGA_DEPLOYMENT_SCHEMA
        and unit.get("studio") == STUDIO_ID
        and unit.get("substrate") == "simulator"
        and unit.get("evidence_kind") == "measured"
        and unit.get("freshness") == Freshness.VERIFIED_AT_SOURCE.value
        and isinstance(unit.get("device"), str)
        and bool(unit["device"].strip())
        and unit.get("cosim_bit_exact") is True
        and all(_wire_count(unit.get(key)) for key in ("lut_used", "ff_used"))
        and _finite_wire_number(unit.get("worst_negative_slack_ns"))
        and _finite_wire_number(unit.get("clock_mhz"), positive=True)
        and _valid_digest(unit.get("result_digest"))
        and _has_cosim_transcript(unit)
    )
    if valid:
        return _REFERENCE_VALIDATED
    return _VALIDATION_GAP

regrade_sc_inference(unit)

Recompute the sc-inference grade from the signed unit.

reference-validated requires a complete measured unit, explicit source re-check and exact string zero error against NumPy. Missing, legacy or malformed evidence stays bounded-model. The signed claim_status is not trusted.

Source code in src/sc_neurocore/federation/attestation.py
Python
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
def regrade_sc_inference(unit: Mapping[str, Any]) -> str:
    """Recompute the sc-inference grade from the signed unit.

    ``reference-validated`` requires a complete measured unit, explicit source
    re-check and exact string zero error against NumPy. Missing, legacy or malformed
    evidence stays ``bounded-model``. The signed ``claim_status`` is not trusted.
    """
    length = unit.get("bitstream_length")
    valid = (
        unit.get("schema") == SC_INFERENCE_SCHEMA
        and unit.get("studio") == STUDIO_ID
        and unit.get("evidence_kind") == "measured"
        and unit.get("freshness") == Freshness.VERIFIED_AT_SOURCE.value
        and unit.get("active_backend") in ("numpy", "rust")
        and unit.get("reference_backend") == "numpy"
        and _wire_count(length)
        and length > 0
        and _valid_digest(unit.get("input_digest"))
        and _valid_digest(unit.get("result_digest"))
        and isinstance(unit.get("max_abs_error"), str)
        and unit.get("max_abs_error") in ("0", "0.0")
    )
    return _REFERENCE_VALIDATED if valid else _BOUNDED_MODEL

seal_sc_inference(result, *, signer, freshness=None)

Seal an sc-inference result in recompute mode (no attestation).

Parameters

result The path-free stochastic-computing inference result. signer The studio's :class:~scpn_studio_platform.seal.keys.Signer. freshness Actual source re-check status. Bit-identical results require VERIFIED_AT_SOURCE; the value is part of the signed unit.

Returns

HonestyEnvelope A recompute-verifiable envelope: the WASM/NumPy kernel re-derives the result and its digest must match.

Raises

ValueError If bit-identical evidence has not been re-checked at source.

Source code in src/sc_neurocore/federation/attestation.py
Python
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
def seal_sc_inference(
    result: ScInferenceResult, *, signer: Signer, freshness: Freshness | None = None
) -> HonestyEnvelope:
    """Seal an sc-inference result in **recompute** mode (no attestation).

    Parameters
    ----------
    result
        The path-free stochastic-computing inference result.
    signer
        The studio's :class:`~scpn_studio_platform.seal.keys.Signer`.
    freshness
        Actual source re-check status. Bit-identical results require
        ``VERIFIED_AT_SOURCE``; the value is part of the signed unit.

    Returns
    -------
    HonestyEnvelope
        A recompute-verifiable envelope: the WASM/NumPy kernel re-derives the result and
        its digest must match.

    Raises
    ------
    ValueError
        If bit-identical evidence has not been re-checked at source.
    """
    _require_source_recheck(result.max_abs_error == 0.0, freshness)
    return seal(
        _sc_inference_unit(result, freshness),
        signer=signer,
        grader=GRADER,
        verifiability_mode="recompute",
        exactness_class="bit-exact",
    )

verify_envelope(envelope, rendered_grade, *, keyring)

Verify a SC-NeuroCore honesty envelope, dispatching the regrade by schema.

Parameters

envelope The :meth:HonestyEnvelope.to_dict wire form on the page, or None when the page carries no seal. rendered_grade The grade the page displays for the claim, or None. keyring The trust anchor mapping key_id → public verifier.

Returns

Verdict :data:~scpn_studio_platform.seal.verdict.Verdict.VERIFIED only when the signature is valid and the rendered grade equals the grade recomputed from the signed unit; otherwise STRIPPED / FORGED / UNGRADED.

Source code in src/sc_neurocore/federation/attestation.py
Python
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
def verify_envelope(
    envelope: Mapping[str, Any] | None,
    rendered_grade: str | None,
    *,
    keyring: Keyring,
) -> Verdict:
    """Verify a SC-NeuroCore honesty envelope, dispatching the regrade by schema.

    Parameters
    ----------
    envelope
        The :meth:`HonestyEnvelope.to_dict` wire form on the page, or ``None`` when the
        page carries no seal.
    rendered_grade
        The grade the page displays for the claim, or ``None``.
    keyring
        The trust anchor mapping ``key_id`` → public verifier.

    Returns
    -------
    Verdict
        :data:`~scpn_studio_platform.seal.verdict.Verdict.VERIFIED` only when the
        signature is valid and the rendered grade equals the grade recomputed from the
        signed unit; otherwise ``STRIPPED`` / ``FORGED`` / ``UNGRADED``.
    """
    schema: object = None
    if isinstance(envelope, Mapping):
        unit = envelope.get("unit")
        if isinstance(unit, Mapping):
            schema = unit.get("schema")
    regrade = regrade_fpga if schema == FPGA_DEPLOYMENT_SCHEMA else regrade_sc_inference
    return verify(envelope, rendered_grade, keyring=keyring, regrade=regrade)

fpga_deployment_evidence(result, *, operator, studio_version, started, ended, host=None, freshness=None)

Build the studio.fpga-deployment.v1 pre-silicon measurement bundle.

RTL is co-simulated against the Q8.8 fixed-point reference on the simulator substrate. The claim is reference-validated only when that co-simulation is bit-exact and re-checked; a mismatch becomes validation-gap.

Parameters

result The path-free synthesis/deployment result. operator Opaque identity of the operator/tenant. studio_version Version of the SC-NeuroCore studio that produced the result. started, ended ISO-8601 start/end timestamps (passed in; no hidden clock). host Optional host descriptor the synthesis ran on. freshness Source re-check status supplied by the producer. Bit-exact co-simulation requires VERIFIED_AT_SOURCE; a retained report alone is not a re-check.

Returns

EvidenceBundle A measured bundle on the simulator substrate, without a board claim.

Raises

ValueError If a bit-exact co-simulation lacks a verified-at-source re-check.

Source code in src/sc_neurocore/federation/evidence.py
Python
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
def fpga_deployment_evidence(
    result: FpgaDeploymentResult,
    *,
    operator: str,
    studio_version: str,
    started: str,
    ended: str,
    host: str | None = None,
    freshness: Freshness | None = None,
) -> EvidenceBundle:
    """Build the ``studio.fpga-deployment.v1`` pre-silicon measurement bundle.

    RTL is co-simulated against the Q8.8 fixed-point reference on the
    ``simulator`` substrate. The claim is ``reference-validated`` only when that
    co-simulation is bit-exact and re-checked; a mismatch becomes ``validation-gap``.

    Parameters
    ----------
    result
        The path-free synthesis/deployment result.
    operator
        Opaque identity of the operator/tenant.
    studio_version
        Version of the SC-NeuroCore studio that produced the result.
    started, ended
        ISO-8601 start/end timestamps (passed in; no hidden clock).
    host
        Optional host descriptor the synthesis ran on.
    freshness
        Source re-check status supplied by the producer. Bit-exact co-simulation
        requires ``VERIFIED_AT_SOURCE``; a retained report alone is not a re-check.

    Returns
    -------
    EvidenceBundle
        A ``measured`` bundle on the ``simulator`` substrate, without a board claim.

    Raises
    ------
    ValueError
        If a bit-exact co-simulation lacks a verified-at-source re-check.
    """
    _require_source_recheck(result.cosim_bit_exact, freshness)
    entity = ProvEntity(
        entity_id=f"{STUDIO_ID}/fpga-deployment/{result.result_digest}", digest=result.result_digest
    )
    activity = ProvActivity(
        verb="synthesise", studio=STUDIO_ID, started=started, ended=ended, host=host
    )
    agent = ProvAgent(studio_version=studio_version, operator=operator)
    cosim = CaseResult(
        operation_family="cosim-bit-exact",
        dimension=1,
        status="pass" if result.cosim_bit_exact else "fail",
        error=0.0 if result.cosim_bit_exact else None,
    )
    physical = PhysicalContract(
        units={"lut": "count", "ff": "count", "wns": "ns", "clock": "MHz"},
        grid={
            "device": result.device,
            "lut_used": result.lut_used,
            "ff_used": result.ff_used,
        },
    )
    claim = ClaimBoundary(
        status=ClaimStatus.REFERENCE_VALIDATED
        if result.cosim_bit_exact
        else ClaimStatus.VALIDATION_GAP,
        admission=AdmissionDecision.ADMITTED
        if result.cosim_bit_exact
        else AdmissionDecision.REJECTED,
        validity_domain=ValidityDomain(
            note=(
                "Bit-exact Q8.8 reference vs RTL co-simulation for the named synthesis "
                "target. Pre-silicon measurement only; physical device execution, power "
                "and general floating-point accuracy are not established."
            )
        ),
    )
    return EvidenceBundle(
        schema=FPGA_DEPLOYMENT_SCHEMA,
        entity=entity,
        activity=activity,
        agent=agent,
        evidence_level=EvidenceLevel.ENGINEERING_VERIFIED,
        evidence_kind=EvidenceKind.MEASURED,
        claim_boundary=claim,
        freshness=freshness,
        substrate=Substrate.SIMULATOR,
        cases=(cosim,),
        physical_contract=physical,
    )

sc_inference_evidence(result, *, operator, studio_version, started, ended, host=None, freshness=None)

Build the studio.sc-inference.v1 bundle (measured software result).

Parameters

result The path-free inference result. operator Opaque identity of the operator/tenant. studio_version Version of the SC-NeuroCore studio that produced the result. started, ended ISO-8601 start/end timestamps (passed in; no hidden clock). host Optional host descriptor the run executed on. freshness Source re-check status supplied by the producer. A bit-identical result requires VERIFIED_AT_SOURCE; parity alone never establishes freshness.

Returns

EvidenceBundle A measured bundle that renders as validated only when the accelerated backend is bit-identical to the NumPy floor.

Raises

ValueError If a bit-identical result lacks a verified-at-source re-check.

Source code in src/sc_neurocore/federation/evidence.py
Python
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
def sc_inference_evidence(
    result: ScInferenceResult,
    *,
    operator: str,
    studio_version: str,
    started: str,
    ended: str,
    host: str | None = None,
    freshness: Freshness | None = None,
) -> EvidenceBundle:
    """Build the ``studio.sc-inference.v1`` bundle (measured software result).

    Parameters
    ----------
    result
        The path-free inference result.
    operator
        Opaque identity of the operator/tenant.
    studio_version
        Version of the SC-NeuroCore studio that produced the result.
    started, ended
        ISO-8601 start/end timestamps (passed in; no hidden clock).
    host
        Optional host descriptor the run executed on.
    freshness
        Source re-check status supplied by the producer. A bit-identical result
        requires ``VERIFIED_AT_SOURCE``; parity alone never establishes freshness.

    Returns
    -------
    EvidenceBundle
        A ``measured`` bundle that renders as validated only when the accelerated
        backend is bit-identical to the NumPy floor.

    Raises
    ------
    ValueError
        If a bit-identical result lacks a verified-at-source re-check.
    """
    bit_identical = result.max_abs_error == 0.0
    _require_source_recheck(bit_identical, freshness)
    entity = ProvEntity(
        entity_id=f"{STUDIO_ID}/sc-inference/{result.result_digest}", digest=result.result_digest
    )
    activity = ProvActivity(
        verb="simulate", studio=STUDIO_ID, started=started, ended=ended, host=host
    )
    agent = ProvAgent(studio_version=studio_version, operator=operator)
    numeric = NumericProvenance(
        active_backend=result.active_backend, reference_backend=result.reference_backend
    )
    claim = ClaimBoundary(
        status=ClaimStatus.REFERENCE_VALIDATED if bit_identical else ClaimStatus.BOUNDED_MODEL,
        admission=AdmissionDecision.ADMITTED if bit_identical else AdmissionDecision.REJECTED,
        validity_domain=ValidityDomain(
            note=(
                "Stochastic-computing forward pass; reference-validated only against the "
                "bit-true NumPy floor for a fixed seed, not against a third-party SNN simulator."
            )
        ),
    )
    return EvidenceBundle(
        schema=SC_INFERENCE_SCHEMA,
        entity=entity,
        activity=activity,
        agent=agent,
        evidence_level=EvidenceLevel.ENGINEERING_VERIFIED,
        evidence_kind=EvidenceKind.MEASURED,
        claim_boundary=claim,
        freshness=freshness,
        numeric_provenance=numeric,
    )

build_manifest(*, studio_version=STUDIO_VERSION)

Build the SC-NeuroCore studio's capability manifest.

Parameters

studio_version The studio version to stamp; defaults to :data:STUDIO_VERSION (the source sc-neurocore version).

Returns

CapabilityManifest The schema-A manifest, with a content digest over :func:declared_surface.

Source code in src/sc_neurocore/federation/manifest.py
Python
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
def build_manifest(*, studio_version: str = STUDIO_VERSION) -> CapabilityManifest:
    """Build the SC-NeuroCore studio's capability manifest.

    Parameters
    ----------
    studio_version
        The studio version to stamp; defaults to :data:`STUDIO_VERSION` (the
        source ``sc-neurocore`` version).

    Returns
    -------
    CapabilityManifest
        The schema-A manifest, with a content digest over :func:`declared_surface`.
    """
    return CapabilityManifest(
        contract_era="v2",
        studio=STUDIO_ID,
        studio_version=studio_version,
        platform_sdk=PLATFORM_SDK_RANGE,
        content_digest=content_digest(declared_surface()),
        protocol_version=PROTOCOL_VERSION,
        transport_profile=TransportProfile.LOCAL_FIRST,
        verbs=NEUROCORE_VERBS,
        evidence_types=evidence_schemas(),
        ui_module=None,
    )

declared_surface()

Return the content-addressable declared surface of the SC-NeuroCore studio.

The surface is the canonical JSON of each advertised verb plus the evidence schema list, keyed by a stable logical path. Hashing surface content (not git state) is what makes the digest reproducible across checkouts.

Returns

dict[str, bytes] Mapping of logical path to canonical-JSON bytes, suitable for :func:scpn_studio_platform.manifest.content_digest.

Source code in src/sc_neurocore/federation/manifest.py
Python
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
def declared_surface() -> dict[str, bytes]:
    """Return the content-addressable declared surface of the SC-NeuroCore studio.

    The surface is the canonical JSON of each advertised verb plus the evidence
    schema list, keyed by a stable logical path. Hashing surface *content* (not git
    state) is what makes the digest reproducible across checkouts.

    Returns
    -------
    dict[str, bytes]
        Mapping of logical path to canonical-JSON bytes, suitable for
        :func:`scpn_studio_platform.manifest.content_digest`.
    """
    surface: dict[str, bytes] = {
        f"verb/{verb.name}": json.dumps(
            verb.to_dict(), sort_keys=True, separators=(",", ":")
        ).encode("utf-8")
        for verb in NEUROCORE_VERBS
    }
    surface["evidence/schemas"] = json.dumps(
        list(evidence_schemas()), sort_keys=True, separators=(",", ":")
    ).encode("utf-8")
    return surface

core_verbs()

Return the SC-NeuroCore verbs drawn from the shared core spine.

Returns

tuple[Verb, ...] The subset of :data:NEUROCORE_VERBS whose names are in the platform :data:scpn_studio_platform.verbs.CORE_VERBS.

Source code in src/sc_neurocore/federation/verbs.py
Python
147
148
149
150
151
152
153
154
155
156
def core_verbs() -> tuple[Verb, ...]:
    """Return the SC-NeuroCore verbs drawn from the shared core spine.

    Returns
    -------
    tuple[Verb, ...]
        The subset of :data:`NEUROCORE_VERBS` whose names are in the platform
        :data:`scpn_studio_platform.verbs.CORE_VERBS`.
    """
    return tuple(verb for verb in NEUROCORE_VERBS if verb.is_core)

domain_verbs()

Return the SC-NeuroCore verbs distinctive to a neuromorphic studio.

Returns

tuple[Verb, ...] The subset of :data:NEUROCORE_VERBS not present in the platform core spine (encode, deploy).

Source code in src/sc_neurocore/federation/verbs.py
Python
159
160
161
162
163
164
165
166
167
168
def domain_verbs() -> tuple[Verb, ...]:
    """Return the SC-NeuroCore verbs distinctive to a neuromorphic studio.

    Returns
    -------
    tuple[Verb, ...]
        The subset of :data:`NEUROCORE_VERBS` not present in the platform core
        spine (``encode``, ``deploy``).
    """
    return tuple(verb for verb in NEUROCORE_VERBS if not verb.is_core)

evidence_schemas()

Return the distinct evidence schemas every SC-NeuroCore verb emits.

Returns

tuple[str, ...] The sorted, de-duplicated union of each verb's produces schemas.

Source code in src/sc_neurocore/federation/verbs.py
Python
171
172
173
174
175
176
177
178
179
180
def evidence_schemas() -> tuple[str, ...]:
    """Return the distinct evidence schemas every SC-NeuroCore verb emits.

    Returns
    -------
    tuple[str, ...]
        The sorted, de-duplicated union of each verb's ``produces`` schemas.
    """
    schemas = {schema for verb in NEUROCORE_VERBS for schema in verb.produces}
    return tuple(sorted(schemas))