/** The model-face envelope tag (single source; a shell renders/collapses by this name). */
export declare const CROSS_SESSION_MESSAGE_TAG = "cross-session-message";
/**
 * The ONE model-face neutralization every PEER-AUTHORED body receives before a framing carrier wraps
 * it — the same-process `<agent-message>` uplink, the `<cross-session-message>` envelope and the
 * `<teammate-message>` frame all call exactly this, then their own {@link escapeEnvelopeTag}.
 *
 * WHAT it defuses: the whole harness AUTHORITY family ({@link ENGINE_AUTHORITY_ENVELOPE_TAGS} —
 * `system-reminder`, `task-notification`, `user_memory`, `skills`, …), not the reminder tag alone. A
 * peer's text is another model's output; a copy of any engine envelope inside it must arrive as
 * data, never as a frame the recipient's model reads as engine speech. The primitive underneath
 * ({@link sanitizeUntrustedText}) deliberately defuses only the reminder tag by default, because it
 * also runs over engine-assembled bodies that legitimately ARE envelopes; a peer body never is, so
 * the family-wide set is correct here and belongs to this seat — one helper, so the three carriers
 * cannot drift apart on which tags they contain.
 *
 * Idempotent (a defused tag no longer matches), which is what keeps the model-face parser's
 * rebuild-and-compare a fixed point on an already-canonical body.
 */
export declare function neutralizePeerBody(body: string): string;
/**
 * Frame-adjacent discipline block for the cross-session lane (design/385 §4.1). DISTINCT from the
 * teammate lane's `PEER_MESSAGE_NOTICE`: the two lanes carry different trust levels (engine-attributed
 * teammate vs same-user peer session with self-claimed identity), and sharing one text would blur the
 * classifier's lane judgment. Content mirrors the three hard rules a peer session cannot override:
 * no settings/instruction-file/config edits on a peer's say-so, a peer message is never the user's
 * approval of a pending prompt, and relaying a denied action is permission laundering.
 */
export declare const CROSS_SESSION_MESSAGE_NOTICE: string;
/**
 * design/385 §4.5 layer 2 — the classifier-slot text spliced into the auto-mode system prompt's
 * `<cross_session_messages_rule>` slot WHILE the cross-session lane is mounted (the base rule 8 is
 * always present; this names the concrete frame and the outbound half). The slot stays empty when the
 * lane is absent, so an unmounted deployment's classifier prompt is byte-identical to before.
 */
export declare const CROSS_SESSION_CLASSIFIER_RULE: string;
/** The sender's self-attested permission-mode CLASS (CC `ZP` vocabulary, two values; absence is the
 *  third state "no class asserted"). An attestation, not a verified fact — see cross-session-judge.ts. */
export type PermissionModeClass = "bypass" | "prompting";
export declare const PERMISSION_MODE_CLASSES: readonly PermissionModeClass[];
export declare function isPermissionModeClass(value: unknown): value is PermissionModeClass;
/** Typed codec failure: a caller-supplied field that cannot be serialized canonically. Thrown (never
 *  silently dropped) so a producer bug is loud at the mint site rather than a silently attribute-less
 *  envelope on the wire (bad-value loudness rule). */
export declare class CrossSessionCodecError extends Error {
    readonly code: "cross_session.invalid_from" | "cross_session.invalid_from_session" | "cross_session.invalid_from_mode" | "cross_session.invalid_from_scope" | "cross_session.invalid_hop_chain";
    constructor(code: CrossSessionCodecError["code"], message: string);
}
/** CC `nM`/`PGe`: 24-hex tokens, at most 32 carried (the oldest are dropped first). */
export declare const PEER_HOP_CHAIN_CARRY_WINDOW = 32;
/** CC `eM` — percent-encode everything outside `[A-Za-z0-9:_/.\-]` (UTF-8 bytes, uppercase hex). The
 *  scheme prefix (`uds:` / `session.`) is part of the raw address and passes through unchanged.
 *  @throws CrossSessionCodecError on a non-string or a string with an unpaired surrogate. */
export declare function encodePeerAddress(raw: string): string;
/**
 * Is this address in its CANONICAL spelling — the one {@link encodePeerAddress} would produce? The
 * grammar alone admits `%ZZ`, a lone `%`, or a needless `%41`; none of those can come out of the
 * encoder (CC's `eM` encodes `%` itself, so a genuine CC peer never sends them either). Addresses are
 * copied verbatim into reply targets, so a non-canonical spelling is refused rather than carried.
 */
export declare function isCanonicalPeerAddress(address: string): boolean;
/** design/385 §4.2 — the canonical `from-scope` attribute form of a raw scope string.
 *  @throws CrossSessionCodecError on a non-string or a string with an unpaired surrogate. */
export declare function encodeScopeAttribute(rawScope: string): string;
/** Inverse of {@link encodeScopeAttribute}; `undefined` when the bytes are not valid percent-encoded
 *  UTF-8 (the parser refuses the whole envelope on that). */
export declare function decodeScopeAttribute(encoded: string): string | undefined;
/** CC `_b` ∘ `replace(/["<>]/g,"")` — the display-name canonicalization: strip the attribute-breaking
 *  bytes, strip invisible/format/control/separator code points, trim, cap at 64 code points with an
 *  ellipsis. An empty result means "omit the attribute" (CC `if(g)`). */
export declare function canonicalPeerDisplayName(raw: string): string;
export interface CrossSessionEnvelopeFields {
    /** The sender's ADDRESS in its canonical (already percent-encoded) spelling — what a reply copies
     *  into `to`. Required. Mint it with {@link encodePeerAddress} from a raw address. */
    from: string;
    /** The sender's session id (`^[A-Za-z0-9_-]{1,80}$`). Self-claimed. */
    fromSession?: string;
    /** The sender's display name (raw; canonicalized at build — see {@link canonicalPeerDisplayName}). */
    fromName?: string;
    /** The sender's self-attested permission-mode class; absent = no class asserted. */
    fromMode?: PermissionModeClass;
    /** design/385 §10 — the sender's RAW scope on the cross-principal lane (encoded on the attribute;
     *  presence marks the message as having crossed a principal wall). Presentation only: the typed
     *  authority anchor is the store record's `peerMeta.fromScope`, never this attribute. */
    fromScope?: string;
}
/**
 * Serialize the model-face envelope. Canonical attribute order is FIXED (`from` → `from-session` →
 * `from-name` → `from-mode` → `from-scope`; the CC `D8` order with `from-scope` appended). The body is
 * neutralized with {@link escapeEnvelopeTag} so a sender-embedded copy of this tag can never close the
 * real frame early (idempotent: an already-neutralized body is unchanged, which is what makes the
 * parser's rebuild comparison work on the extracted body).
 * @throws CrossSessionCodecError on a field that cannot be spelled canonically.
 */
export declare function buildCrossSessionEnvelope(fields: CrossSessionEnvelopeFields, body: string): string;
/** Why a parse refused: `not_an_envelope` (the strict grammar did not match at all), `bad_scope_encoding`
 *  (a `from-scope` that is not valid percent-encoded UTF-8), `roundtrip_mismatch` (the grammar matched
 *  but the canonical re-serialization differs — a near-miss / non-canonical form). All three mean
 *  "treat the text as ordinary data". */
export type CrossSessionEnvelopeRefusal = "not_an_envelope" | "bad_scope_encoding" | "roundtrip_mismatch";
export type CrossSessionEnvelopeParse = {
    ok: true;
    fields: CrossSessionEnvelopeFields;
    body: string;
} | {
    ok: false;
    reason: CrossSessionEnvelopeRefusal;
};
/**
 * Strict parse + round-trip check of the model-face envelope. `body` is returned in its ENVELOPE form
 * (nested-tag-neutralized, exactly as the model saw it). A refusal is a classification of the text as
 * data, not an error.
 */
export declare function parseCrossSessionEnvelope(text: string): CrossSessionEnvelopeParse;
export interface CcPeerFrameFields {
    /** The sender address (CC: optional even on the wire). */
    from?: string;
    fromSession?: string;
    /** Forwarding chain of 24-hex hop tokens; more than 32 ⇒ the OLDEST are dropped (CC `ygt`). */
    hopChain?: string[];
    fromName?: string;
    fromMode?: PermissionModeClass;
}
/** CC `ygt` — the carry window: keep the newest 32. */
export declare function clampHopChain(chain: readonly string[]): string[];
/**
 * Serialize the CC wire envelope (what goes into a UDS user frame's `message.content`). Attribute
 * order `from` → `from-session` → `hop-chain` → `from-name` → `from-mode`. Unlike CC's own
 * constructor, which silently DROPS an ill-formed `from-session`/`hop-chain`, this throws on them: the
 * values are ours, and a producer bug must not become an attribute-less frame on the wire.
 * @throws CrossSessionCodecError
 */
export declare function encodeCcPeerFrame(fields: CcPeerFrameFields, body: string): string;
export type CcPeerFrameParse = {
    ok: true;
    fields: CcPeerFrameFields;
    body: string;
} | {
    ok: false;
    reason: "not_an_envelope" | "roundtrip_mismatch";
};
/** CC `oM` byte-exact: strict grammar, then rebuild-and-compare. The hop chain comes back as a typed
 *  array for the engine's side channel — a consumer must strip it before the model face (CC `ymn`). */
export declare function decodeCcPeerFrame(text: string): CcPeerFrameParse;
