D1 kernel invariants and provider control-plane contract
Contract status: Accepted by the architecture decision owner.
Implementation status: Not started. This document does not implement a provider framework.
This is node D1 from ARCH-29 policy-owning provider microkernel. It defines the kernel invariants and control-plane semantics that the isolation, primary-memory, and context contracts must specialize. It deliberately does not define any provider kind's domain operations.
Quick orientation
- Read this if: you are defining a provider-kind contract, registration path, configuration binding, lifecycle, health model, selection rule, operation binding, or conformance gate.
- Skip this if: you need the operations of isolation, memory, or context; those belong to I0, M0, and C0 after this contract is accepted.
- Go deeper: start with ARCH-29, then compare Gateway plugins, Memory, and Sandbox and policy.
Why D1 exists
Tyrum already uses the word “provider” for several unrelated seams. None is the shared provider control plane defined here.
| Existing seam | Current truth | D1 consequence |
|---|---|---|
| Model provider accounts | Provider keys, auth profiles, model catalog entries, and conversation pins describe model access and credential selection. | Do not reuse the model-account schema as a universal provider descriptor or binding. |
| Gateway plugins | Manifests, lock integrity, filesystem trust checks, and registration callbacks load trusted code contributions. | Plugins remain packaging and code-loading. A plugin-delivered provider still enters its provider-kind admission path. |
| Secret provider | A narrow concrete interface resolves, stores, revokes, and lists secret handles. | Secret values remain behind kernel-owned projection; the current interface is not the generic control plane. |
| Process confinement | local_spawn reports a truthful baseline-only capability with no hardened backend. | I0 must represent that behavior as a built-in isolation provider without changing its claims. |
| MCP memory tools | Ordered tool metadata drives hydration and context roles. | MCP remains an optional transport/capability boundary, not primary-memory provider admission. |
The control plane normalizes only semantics that these future typed contracts prove they share: identity, registration, configuration references, compatibility, lifecycle state, health, deterministic selection, immutable binding, and conformance.
Normative boundary
The terms must, must not, should, and may are normative within this draft.
The provider control plane owns:
- provider-kind and implementation identity;
- registration and catalog admission;
- descriptor, contract-version, configuration, trust, and deployment validation;
- lifecycle and status normalization;
- deterministic selection and cardinality enforcement;
- immutable operation bindings and exact recovery identity;
- common error translation, correlation, and canonical audit creation;
- common and provider-kind conformance gates.
It does not own:
- a universal
Providerdomain interface; - a universal
execute,run,read,write, orcontributeoperation; - the conversation-turn state machine;
- provider-kind request, result, consistency, retry, or composition semantics;
- plugin installation or MCP transport semantics;
- a provider marketplace, hot reload, fleet registry, or distributed scheduler;
- a new database registry or migration family.
A control-plane implementation may expose internal host functions for registration, activation, status, binding, and shutdown. Those functions must not accept arbitrary domain requests.
Canonical identity model
Stable catalog identities use lowercase namespaced IDs. Versions use semantic version format. Runtime instances and bindings use kernel-issued UUIDs. Human labels are never identities.
| Identity | Meaning | Stability rule |
|---|---|---|
ProviderKindId | A typed contract family, for example tyrum.provider.process-isolation. | Namespaced and stable across implementations; never inferred from a class or package name. |
ProviderContractVersion | The semantic version of one provider-kind contract. | Deterministically negotiated by the kernel and persisted in each binding. |
ProviderImplementationId | One implementation within one kind, for example tyrum.provider.process-isolation.local-spawn. | Namespaced, globally unambiguous within Tyrum, and immutable across incompatible implementations. |
ProviderImplementationVersion | The implementation's semantic release version. | Changes whenever descriptor, protocol, configuration, recovery, or behavior compatibility changes. |
ProviderReleaseId | Immutable verified delivery identity for the executable artifact or authenticated service release. | A digest or trusted release attestation; changed release content requires a new implementation version. |
ProviderConfigurationRevision | A kernel-issued immutable reference to validated configuration and secret references. | Never contains resolved secret values; an update creates a new revision. |
ProviderConformanceEvidenceId | A kernel/release-owned record proving the exact admitted release passed the required suites. | Bound to suite, contract, implementation, release, and deployment identities; never self-assigned. |
ProviderActivationId | One lifecycle attempt for an exact implementation release and configuration revision. | Kernel-issued UUID; terminal after stop or failure and never reused. |
ProviderBindingId | The selected implementation identity attached to one canonical operation or durable resource. | Kernel-issued UUID; immutable for that operation or resource lifetime. |
ID segments must follow Tyrum's existing lowercase dotted-namespace style: [a-z][a-z0-9-]* segments separated by dots. A third party uses its own stable namespace, for example acme.provider.process-isolation.firecracker. Registering the same implementation ID and version with different descriptor or verified release content is a collision and must be rejected.
A provider implementation that supports multiple kinds registers a distinct descriptor and implementation identity for each kind. Multi-kind registration does not create a universal domain interface.
Implementation descriptor
A descriptor is static, non-secret catalog metadata. It is not configuration, runtime status, or proof of health.
| Field | Required meaning |
|---|---|
| Kind identity | ProviderKindId plus the supported ProviderContractVersion range. |
| Implementation identity | ProviderImplementationId and ProviderImplementationVersion. |
| Display metadata | Operator-facing name, description, and documentation reference; never used for selection. |
| Delivery provenance | Built-in artifact, verified plugin/package, local service, or remote service identity. |
| Delivery release | Immutable ProviderReleaseId derived from verified integrity evidence or a trusted service attestation. |
| Trust and deployment support | The modes the implementation can operate under; admission may allow only a subset. |
| Configuration schema | Versioned non-secret configuration schema plus named secret-reference slots. |
| Kind capabilities | A provider-kind-specific capability document validated by that kind's schema. |
| Lifecycle features | Whether activation is eager/lazy, shared/per-binding, recoverable, and stateful, using D1 vocabulary. |
| Protocol identity | Required out of process: protocol name/version and authenticated peer identity requirements. |
Descriptors must not contain resolved credentials, mutable health, self-assigned priority, policy exceptions, or provider-authored audit outcomes.
Registration and admission
Built-in and external implementations use the same provider registration, descriptor validation, compatibility, configuration, selection, binding, and conformance semantics. Delivery-specific trust checks occur before this common path and may be stricter for external code.
- Verify delivery. The owning delivery mechanism verifies origin, immutable release identity, integrity/attestation, ownership, path safety, and permitted code-loading mode before provider registration. Provider admission cannot make untrusted in-process code safe after import.
- Parse the descriptor. The kernel validates strict schema, canonical IDs, semantic versions, declared kind, deployment modes, release identity, and absence of secret values.
- Reject collisions. One implementation identity/version cannot resolve to multiple descriptors, delivery origins, or release identities.
- Record catalog registration. A descriptor and release that pass delivery, schema, identity, and collision admission become
registered. Registration is global catalog truth; the implementation may independently remain unconfigured or incompatible for every selection scope. - Evaluate compatibility. For a selection scope, the kernel chooses the highest mutually supported stable semantic version from exact versions supported by both sides. A prerelease requires an exact operator-authored prerelease selection. Structural duck typing is not compatibility.
- Evaluate configuration. The kernel validates non-secret configuration and named secret handles against the descriptor and kind contract without resolving values. It materializes the exact implementation version and
ProviderReleaseIdinto a new immutable configuration revision. - Apply trust and policy admission. The kernel evaluates operator configuration, delivery trust, deployment mode, requested permissions, and the provider kind's trust floor for the selection scope.
- Verify conformance evidence. A kernel/release-owned verifier accepts only evidence bound to the exact implementation ID/version, negotiated contract version, descriptor and
ProviderReleaseId, deployment mode, and conformance-suite version. Provider self-report is insufficient. - Activate deliberately. Lifecycle activation occurs only after registration and every independent eligibility axis, policy gate, and conformance gate succeeds.
A built-in descriptor may be compiled into Tyrum, but it still passes steps 2 through 9 and the same common/provider-kind conformance suites. “Built-in” supplies provenance; it does not grant a bypass.
Plugin registration and provider registration are separate events. A trusted plugin may call a provider-kind registration API only for contribution types declared and permitted by its manifest and Tyrum policy.
Independent state axes
Present, registered, configured, compatible, conforming, ready, healthy, and capable are independent axes. The kernel must never collapse them into one provider-supplied boolean.
| Axis | Canonical states | Kernel-owned meaning |
|---|---|---|
| Presence | absent, present | The delivery source is available to the kernel. A built-in is present; an external package/service may become absent. |
| Registration | rejected, registered | Delivery, descriptor, identity, and collision admission either failed for that release or entered the catalog. |
| Configuration | unconfigured, invalid, configured | A referenced immutable configuration revision is absent, rejected, or valid for the descriptor and kind contract. |
| Compatibility | incompatible, compatible | The kernel did or did not negotiate an admitted contract version and deployment mode. |
| Conformance | unverified, rejected, verified | Trusted evidence for the exact implementation release and admitted deployment is absent, rejected, or accepted. |
| Lifecycle | inactive, starting, ready, stopping, stopped, failed | The kernel's state for one ProviderActivationId; health is not encoded here. |
| Health | unknown, healthy, degraded, unhealthy | A time-bounded kernel-normalized assessment based on provider signals and kernel observation. |
| Capability | unknown, available, unavailable per kind-specific capability | Whether the active binding candidate truthfully satisfies a typed requirement now. |
Provider signals are evidence, not canonical state transitions. The kernel owns transition timestamps, reason codes, freshness, and the derived availability result.
An implementation is eligible for a new binding only when:
- it is present and registered;
- its selected configuration revision is configured;
- its contract, trust mode, and deployment mode are compatible;
- exact-release conformance evidence is verified;
- its activation is ready when the kind requires pre-activation;
- health freshness and minimum health satisfy the provider-kind contract;
- every required typed capability is available;
- policy and operator selection allow it for the requested scope.
degraded is not implicitly eligible or ineligible. Each provider-kind contract defines which operations, if any, may bind while degraded.
Lifecycle transitions
Health changes do not rewrite lifecycle history. A ready activation can be unhealthy; an inactive implementation can have unknown health. A retry or durable recovery creates a new ProviderActivationId; a failed or stopped activation never re-enters starting.
Configuration and secret projection
Configuration is operator-authored at an explicit provider-kind selection scope. The anchor contracts do not permit model-supplied provider selection or downgrade.
- The kernel validates configuration against both the implementation descriptor and provider-kind contract.
- Secret references are configuration; resolved secret values are not configuration and are never persisted in descriptors or bindings.
- The kernel resolves only admitted named secret slots after identity, authorization, policy, configuration, and binding checks.
- Projection is least privilege and limited to the activation or invocation lifetime defined by the provider-kind contract.
- Secret values never appear in descriptors, status, health, logs, metrics, error messages, or audit events.
- Providers cannot enumerate unrelated secret handles or ask the model to supply missing values.
- A configuration update creates a new
ProviderConfigurationRevision. Existing bindings retain their original revision until settlement. - Secret rotation at a stable handle is contract-specific. A provider kind that requires value immutability must bind a kernel-owned secret version reference without exposing the value.
Dynamic hot reload is not implied. A provider-kind contract must explicitly define whether a new configuration revision requires a new activation, applies only to new bindings, or is forbidden while resources remain active.
Trust and deployment modes
Trust, provider-code deployment, and the provider-kind's managed target are separate attributes.
| Attribute | Initial vocabulary | Meaning |
|---|---|---|
| Trust mode | kernel-trusted, operator-trusted, protocol-constrained | Code admitted as part of Tyrum, code explicitly trusted by an operator, or code constrained to an authenticated protocol boundary. |
| Deployment mode | in_process, local_service, remote_service | Where provider code executes relative to the gateway. |
protocol-constrained is invalid with in_process; all other combinations require explicit provider-kind admission. Every local_service and remote_service deployment must define and enforce authentication, channel protection, replay behavior, request identity and response correlation, deadlines, cancellation, and maximum message/resource bounds before admission. Trust mode must not waive these transport requirements. An unavailable or unverified requirement fails closed.
Provider code deployment is not the managed workload target. For I0, whether a process runs directly on a host OS, inside a container/VM boundary, or through a remote node is a typed isolation capability and target rule, not a D1 provider deployment mode. A remote provider service is not automatically isolated, and an out-of-process provider is not automatically trusted.
A provider descriptor declares requested permissions and deployment support. The kernel records the granted subset. Providers cannot expand their own trust mode or permissions after registration.
Deterministic kernel-owned selection
Selection consumes only kernel-owned inputs:
- provider kind and accepted contract version;
- explicit selection scope and operator-authored profile;
- required typed capabilities and truthful posture;
- minimum trust/deployment requirements;
- canonical operation identity, tenant, workspace, agent, and actor identity as applicable;
- current admitted state axes and policy outcome.
An operator-authored profile revision resolves an exact ProviderImplementationId, ProviderImplementationVersion, ProviderReleaseId, configuration revision, trust mode, and deployment mode before selection. Installing or discovering a newer release does not change that profile revision or any new binding derived from it; adopting the release requires a new validated profile/configuration revision.
Discovery order never affects selection. Provider self-priority, display names, filesystem order, network response order, and registration timing are not selectors.
The provider-kind contract supplies cardinality and composition rules:
- exclusive kinds bind the one implementation named by the resolved profile;
- ordered-many kinds use kernel-owned configured order and merge rules;
- additive and fan-out kinds use a kernel-owned admitted set;
- capability-routed kinds use deterministic kind-specific matching and tie-breaking.
A configured fallback list may be evaluated before a binding exists only when the provider-kind contract permits fallback. Security posture is a minimum filter, never a preference that may be downgraded.
Immutable operation binding
The kernel creates a binding only after selection and all governance checks succeed.
| Binding field | Requirement |
|---|---|
ProviderBindingId | Kernel-issued UUID. |
| Kind | ProviderKindId and negotiated ProviderContractVersion. |
| Implementation | Exact ProviderImplementationId, ProviderImplementationVersion, and immutable ProviderReleaseId. |
| Configuration | Exact ProviderConfigurationRevision and admitted secret-reference set. |
| Conformance | ProviderConformanceEvidenceId accepted for the exact contract, release, deployment, and suite version. |
| Runtime posture | Trust mode, deployment mode, and stable authenticated peer identity when applicable. |
| Scope | Canonical selection scope and provider-kind cardinality position/set membership. |
| Operation | Canonical operation/resource identity, actor identity reference, and correlation ID. |
| Requirements | Typed required capabilities and minimum posture used for selection. |
| Recovery | Provider-kind-specific typed recovery locator when durable recovery is supported. |
| Time | Creation time, deadline, and settlement state owned by the kernel. |
The binding is immutable for the operation or durable resource lifetime. Later configuration, discovery, priority, health, activation, or catalog changes do not rewrite it. Conflicting descriptor or release identity for the pinned implementation ID/version is a collision, never an update.
There is no silent fallback or rebinding after an external effect may have started. A provider-kind contract may permit a kernel-owned retry with a new binding only when idempotency, duplicate effects, ordering, policy, approval reuse, and audit linkage are explicit. The process-isolation contract must not retry into a weaker confinement posture.
Each invocation attempt records its ProviderActivationId in append-only lifecycle history linked to the binding; activation identity is not part of the immutable provider-selection tuple. A retry or recovery may create a new activation linked to the unchanged ProviderBindingId, but only for the exact pinned implementation release, configuration, trust/deployment posture, and peer identity.
For a durable operation, the kernel persists the exact binding and recovery identity at the contract-defined write-ahead point. Recovery uses that exact binding; it does not rerun current selection. If the implementation, release, configuration revision, authenticated peer, conformance evidence, or recovery locator is unavailable, recovery fails with a canonical binding-unavailable outcome rather than selecting another provider.
Lifecycle and resource ownership
Provider-kind contracts specialize these common lifecycle obligations:
- activation is kernel-initiated and receives only the admitted descriptor, configuration revision, projected identity, and permitted secret slots;
- every activation has an owner, deadline, cancellation path, shutdown behavior, and terminal state;
- retry or recovery after a terminal activation allocates a new activation ID and preserves the existing binding ID;
- shared activations use kernel-owned reference accounting so one binding cannot stop resources owned by another;
- per-binding activations are released when that binding reaches terminal settlement;
- providers acknowledge cancellation and release resources within kind-specific bounds; the kernel owns hard settlement after those bounds;
- gateway shutdown first rejects new bindings, then drains/cancels active bindings, then stops activations, and finally records unresolved cleanup truthfully;
- a provider must not create untracked durable processes, leases, subscriptions, or remote resources outside a kernel activation/binding record.
Lifecycle hooks are control-plane semantics, not a universal domain operation. In-process and out-of-process implementations may use different host adapters while producing the same canonical lifecycle outcomes.
Common error taxonomy
The control plane normalizes errors that occur before or around typed domain operations:
| Code | Meaning |
|---|---|
provider_not_present | The configured delivery source is absent. |
provider_registration_rejected | Descriptor, collision, integrity, trust, or registration validation failed. |
provider_configuration_invalid | Configuration or secret references failed schema/slot validation. |
provider_incompatible | No admitted contract/protocol/deployment version intersection exists. |
provider_not_trusted | Required trust or permission admission failed. |
provider_conformance_rejected | Exact-release conformance evidence is missing, invalid, stale, or revoked. |
provider_activation_failed | Startup or readiness failed within its deadline. |
provider_not_ready | No ready activation is available when readiness is required. |
provider_unhealthy | Health is too stale or below the kind's minimum. |
provider_capability_unavailable | A required typed capability is unknown or unavailable. |
provider_binding_unavailable | An exact binding or durable recovery identity cannot be restored. |
provider_protocol_violation | An implementation violated its admitted control/domain protocol. |
provider_shutdown_timeout | Cleanup or shutdown did not settle within the contract bound. |
Each canonical error includes phase, safe reason code, correlation, retryability classification, and affected identities. Provider-native messages are diagnostics only and must be redacted before they leave the kernel boundary.
The kernel owns retry and backoff decisions. A provider may return typed retry hints only when its provider-kind contract defines their meaning. No common error authorizes fallback, policy bypass, approval reuse, or rebinding.
Observability and canonical audit
Providers emit bounded telemetry and diagnostics. The kernel creates canonical audit events after validating and redacting provider evidence.
Minimum kernel events are:
- registration accepted/rejected;
- configuration revision validated/rejected;
- exact-release conformance evidence accepted/rejected/revoked;
- activation starting/ready/failed/stopping/stopped;
- normalized health transition;
- selection accepted/rejected with a safe reason code;
- binding created/released;
- durable binding recovery accepted/failed;
- protocol violation and forced settlement.
Every event carries the relevant kind, implementation, release, contract, conformance, configuration, activation, binding, operation, scope, actor, and correlation identities that exist at that phase. Events omit absent identities rather than inventing placeholders.
Provider-authored logs are not audit records. Provider health reports do not create canonical state transitions. Secret values, raw credentials, sensitive configuration, unbounded output, and provider-native stack traces never enter canonical audit payloads.
Persistence and recovery
D1 does not authorize a new provider database or registry migration.
- The catalog may be reconstructed from built-in descriptors and admitted delivery sources only when each descriptor resolves to the same verified
ProviderReleaseId. - Operator configuration uses existing owned configuration surfaces until a provider-kind contract proves another persistence requirement.
- Configuration revisions and durable binding records require stable kernel identity, but their concrete storage is selected only with the anchor contracts and S0 substrate design.
- Ephemeral operations may keep bindings in memory when their provider-kind contract needs no restart recovery.
- Durable operations persist exact binding, release, conformance, and recovery data according to their typed contract.
- Provider-native persistent state may be authoritative only where the provider-kind contract explicitly assigns source-of-truth, consistency, backup, migration, and rollback ownership.
A restarted kernel must never infer an old binding from the currently preferred provider.
Compatibility and descriptor evolution
Provider contract and implementation versions use semantic versioning:
- a major contract change may remove or redefine fields, operations, lifecycle, trust, consistency, or error semantics;
- a minor contract change is additive and optional for implementations that remain compatible;
- a patch clarifies or fixes behavior without changing the accepted shape;
- an implementation advertises an explicit supported contract range and one immutable implementation version;
- the kernel deterministically selects the highest exact mutually supported stable contract version; an exact operator-selected prerelease is the only prerelease exception;
- a validated operator profile/configuration revision pins one exact implementation ID, implementation version, and
ProviderReleaseIdbefore selection; - the kernel records the negotiated contract version and pinned release identity in each binding;
- incompatible implementations remain visible as unavailable with safe reasons but cannot activate or bind.
Changing descriptor or executable/service release content without changing implementation version is forbidden. A different ProviderReleaseId under the same implementation ID/version is a collision. Aliases and migrations, when needed, are explicit kernel-owned maps; the catalog does not guess identity from labels or package names.
Conformance gates
D1 requires two layers of evidence:
- Common conformance validates canonical IDs/versions, strict descriptors, collision rejection, delivery/admission separation, independent state axes, deterministic selection, immutable bindings, exact recovery identity, lifecycle deadlines, secret redaction, canonical errors, and audit ownership.
- Provider-kind conformance validates typed domain operations, cardinality, capabilities, consistency, failure/degraded behavior, cancellation, cleanup, and source-of-truth rules.
Built-in and external implementations run the same common conformance and provider-kind conformance suites. Delivery modes add tests; they do not remove shared tests. A built-in may use an in-process fixture and an external implementation a protocol fixture, but both must prove the same canonical outcomes.
The authoritative verifier is owned by the Tyrum release pipeline or an operator-administered trust policy, not by the provider. It creates a ProviderConformanceEvidenceId bound to the exact implementation ID/version, negotiated contract version, descriptor and ProviderReleaseId, admitted deployment mode, and common/provider-kind conformance-suite versions. For built-ins, the Tyrum release manifest binds CI evidence to the shipped artifact. For external releases, the operator trust policy accepts a signed/verified release record or a locally produced conformance record for that exact release.
The kernel verifies that record before every new activation and rejects missing, stale, revoked, mismatched, or self-produced evidence. Provider self-report is insufficient. This release-owned gate does not require a marketplace or online registry.
Kernel invariant matrix
Every invariant has one kernel enforcement point and observable evidence. Concrete module names remain deferred until S0 proves the shared substrate.
| Invariant | Kernel enforcement point | Required evidence |
|---|---|---|
| Native turn authority | Turn state machine and tool executor before provider dispatch. | A provider cannot advance a turn, grant tools, or commit kernel state. |
| Typed domain boundary | Provider-kind contract validation. | No universal operational provider method accepts arbitrary domain input. |
| One admission path | Catalog registration/admission coordinator. | Built-in bypass attempts fail the same checks as external registration. |
| Immutable release identity | Delivery verifier and collision gate. | One implementation ID/version cannot resolve to different descriptor or release bytes. |
| Contract compatibility | Version negotiator before activation. | Incompatible ranges remain unavailable and never invoke provider code. |
| Conformance activation gate | Release/operator evidence verifier before activation. | Exact release/deployment/suite evidence is verified independently of provider claims. |
| Deterministic selection | Kernel resolver using explicit profile and kind rules. | Reordered discovery/registration produces the same binding. |
| Immutable binding | Kernel binding coordinator and durable binding store when required. | Configuration/catalog changes cannot alter an active or recovered binding. |
| Identity propagation | Invocation envelope construction. | Provider receives only canonical projected scope and actor identity. |
| Authorization/policy/approval | Existing governance path before binding/invocation. | Provider cannot self-authorize, request a weaker posture, or reuse approval implicitly. |
| Secret projection | Kernel secret-reference resolver after admission. | Only named slots are projected; values never enter status or audit. |
| Truthful state | Kernel lifecycle/health normalizer. | Provider reports cannot directly set canonical ready/healthy/capable state. |
| Deadline/cancellation/shutdown | Kernel lifecycle coordinator. | Timeout and shutdown produce bounded canonical settlement and unresolved-cleanup truth. |
| Canonical audit | Kernel audit service. | Provider telemetry is validated/redacted before canonical event creation. |
| No silent downgrade | Selection and binding coordinator. | Unavailable requirements fail closed; retry/rebinding requires explicit kind semantics. |
| Exact durable recovery | Provider-kind binding persistence and recovery path. | Restart uses the exact recorded binding or returns binding unavailable. |
D1 acceptance and next work
D1 is accepted with these frozen boundaries:
- each invariant has an unambiguous kernel owner and observable enforcement point;
- identity, release, version, descriptor, state-axis, selection, binding, activation, conformance, lifecycle, error, audit, and recovery semantics are internally consistent;
- built-in parity is explicit without pretending delivery trust is identical;
- configuration and secret handling preserve least privilege and immutable bindings;
- no universal domain operation, marketplace, hot reload, distributed lifecycle, or new database registry has entered scope;
- I0, M0, and C0 can specialize the vocabulary without changing its common meaning.
Acceptance of this document authorizes contract design only. It does not authorize control-plane code. After acceptance, I0, M0, and C0 define their typed contracts. S0 may then extract only the shared types and machinery all three actually require.