docs(nip-fi): close temporal, allocation, and denominator ambiguities

Three defects from the independent review lap, each fixed by making the
text impossible to read two ways:

DELEG evidence boundaries used 'live' (undefined) and declared equality
at either temporal boundary expired, which is incoherent for a lower
bound and contradicted core's own inclusive-nbf/exclusive-exp idiom.
State both comparisons explicitly, matching core: now < mandatory_expiry
and not_before <= now + skew.

The delegated lease deadline mixed a configured duration into a minimum
of absolute instants. Anchor it: lease issue instant plus the configured
delegated maximum.

EDGE allocated proof-transport codes 0x03/0x04 to Git and Blossom
profiles that do not exist, violating the table's own allocation rule
(a published stable specification with validation, binding, freshness,
replay, and vectors). Unassign both; the unassigned range now starts at
0x03.

Core's oracle table compressed six pairs of oracle IDs with slash
shorthand that has no consistent expansion rule: three pairs read
replace-last, three read keep-prefix, so no reader can infer the
grammar. Split all six into one row per literal ID. The table now lists
exactly 30 rows, one complete ID each, making the oracle set mechanically
enumerable as the mutation-adequacy denominator CONF will reference.
Every prose citation resolves to a table row; no shorthand remains.

Review findings: Wren (DELEG boundaries, delegated maximum, EDGE codes,
shorthand ambiguity), Dawn (denominator enumerability measurement).

Co-authored-by: Eva <011987e296fd5006292d2f930b574be47c7801048d1983c46c425d3c95f0cffd@buzz.block.builderlab.xyz>
Signed-off-by: Eva <011987e296fd5006292d2f930b574be47c7801048d1983c46c425d3c95f0cffd@buzz.block.builderlab.xyz>
This commit is contained in:
Eva
2026-08-17 15:44:18 -04:00
parent d123e4e0bb
commit ffc4e654c7
3 changed files with 17 additions and 12 deletions
+4 -3
View File
@@ -50,8 +50,9 @@ when their concrete encoding belongs to the supplying delegation protocol.
The evidence authenticates every field, has one unambiguous owner and delegate,
matches the server-owned domain and exact request or target, and has a finite
expiry. If present, `not_before` is live. Equality at either temporal boundary
is expired. The proven actor equals `delegate_key`. [FI-DELEG-EVIDENCE-CLOSED]
expiry satisfying `now < mandatory_expiry`; equality at an expiry is expired.
Optional `not_before` satisfies `not_before <= now + skew`, as core defines for
`nbf`. The proven actor equals `delegate_key`. [FI-DELEG-EVIDENCE-CLOSED]
A delegated request carries fresh request-appropriate Nostr proof and no
`Nostr-Federated-Identity` or profile provenance field. Mixed direct and
@@ -114,7 +115,7 @@ is no later than the minimum of:
- owner binding administrative bound, when applicable;
- current relationship bound;
- local policy bound;
- the configured delegated maximum; and
- the lease issue instant plus the configured delegated maximum; and
- any stronger owner-assertion bound the deployment requires.
Missing finite configuration denies. Equality is expired and arithmetic is
+1 -3
View File
@@ -192,9 +192,7 @@ requires confidentiality and integrity.
| `0x00` | Invalid; MUST deny. |
| `0x01` | NIP-42 connection proof. |
| `0x02` | NIP-98 HTTP proof. |
| `0x03` | Git smart-HTTP session proof profile. |
| `0x04` | Blossom proof profile. |
| `0x05``0x7f` | Unassigned; allocation requires a published stable specification. |
| `0x03``0x7f` | Unassigned; allocation requires a published stable specification. |
| `0x80``0xfe` | Private use under an explicit shared proxy/verifier contract only. |
| `0xff` | Reserved for a future extended encoding; invalid in HMAC-v2. |
+12 -6
View File
@@ -514,24 +514,30 @@ policy revision. NIP-FI-CONF defines evidence and mutation-adequacy rules.
| `FI-TRACE-TOKEN-CLASS` | An RFC 9068 `at+jwt` access token and a dedicated `nip-fi+jwt` assertion pass only their selected class. ID tokens, wrong/generic types outside a named compatibility policy, client-only audiences, absent or ambiguous `client_id`, resource-owner/client-subject ambiguity, and every attempted cross-class fallback deny. |
| `FI-TRACE-CONTRACT-IDENTITIES` | Mutate each assertion semantic, transport semantic, and mutable dependency independently: semantic mutations change only their owning contract ID; snapshot/binding/lifecycle/policy/resource/status mutations change neither ID but force current revalidation. |
| `FI-TRACE-VERIFIER-PARITY` | Equal authoritative input and policy produce the same canonical normalized result. |
| `FI-TRACE-JWKS-ADD` / `REMOVE` | Retained-key rotation can revalidate; removed-key evidence and leases deny. |
| `FI-TRACE-CURRENT-STATUS-REVOKED` / `STALE` | Revocation, including one racing final admission, closes authority within the advertised tested bound. Inactive/ambiguous status denies; expiry equality, outage, delayed events, and changed status versions cannot mint or extend a witness. |
| `FI-TRACE-JWKS-ADD` | Retained-key rotation revalidates successfully under the changed snapshot version. |
| `FI-TRACE-JWKS-REMOVE` | Evidence and leases under a removed key deny after snapshot change. |
| `FI-TRACE-CURRENT-STATUS-REVOKED` | Revocation, including one racing final admission, closes authority within the advertised tested bound. |
| `FI-TRACE-CURRENT-STATUS-STALE` | Inactive/ambiguous status denies; expiry equality, outage, delayed events, and changed status versions cannot mint or extend a witness. |
| `FI-TRACE-CAPABILITY-REVOCATION` | Removal of a revocation-bounded external capability projection from authoritative local policy closes prepared evidence and lease use within the declared bound; assertion-only projection cannot satisfy this oracle. |
| `FI-TRACE-BODY-BINDING` / `BOUNDS` | Exact complete relevant body passes; absent/duplicate/mutated/partial/transformed/oversized/quota variants deny without effects. |
| `FI-TRACE-BODY-BINDING` | Exact complete relevant body passes; absent/duplicate/mutated/partial/transformed payload variants deny without effects. |
| `FI-TRACE-BODY-BOUNDS` | Oversized, over-quota, and pre-EOF variants deny with bounded work, cleanup, and no effects. |
| `FI-TRACE-DOMAIN-SPOOF` | Client routing and forwarded authority cannot replace server-owned context. |
| `FI-TRACE-ASSERTION-KEY-MISMATCH` | Mismatch denies with no mutation and the private-state response. |
| `FI-TRACE-BINDING-CONFLICT` / `TOMBSTONE-REPLAY` | Conflicts and fresh evidence for retired/revoked state deny without replacement. |
| `FI-TRACE-BINDING-CONFLICT` | A binding conflict denies without replacing either existing binding. |
| `FI-TRACE-TOMBSTONE-REPLAY` | Fresh eligible evidence for a retired pair or revoked key denies without recreation. |
| `FI-TRACE-ASSERTION-REFRESH` | Fresh evidence reuses the same eligible durable binding after prior assertion expiry. |
| `FI-TRACE-PREPARED-STALE` | Changed identity-class witnesses or extended bounds deny; provenance-only rotation revalidates. |
| `FI-TRACE-CONCURRENT-ENROLLMENT` | Identical first use converges; conflicting first use commits at most one winner. |
| `FI-TRACE-FINAL-DENIAL-NO-MUTATION` | Every failed phase leaves all authoritative stores and effects unchanged. |
| `FI-TRACE-LIFECYCLE-AUTHORITY` | Unprivileged/stale transitions deny; authorized retirement/revocation/rotation is atomic. |
| `FI-TRACE-LEASE-BOUND` / `MULTI-KEY-SESSION` | Equality expires and one actor's lease never authorizes another. |
| `FI-TRACE-LEASE-BOUND` | A lease ends at its earliest bound; equality at any bound is expired. |
| `FI-TRACE-MULTI-KEY-SESSION` | One actor's lease never authorizes another key on the same connection. |
| `FI-TRACE-DENIAL-ORACLE` | Each private row produces its exact fixed bytes; all private-state rows compare byte-identical. |
| `FI-TRACE-DEPENDENCY-FAIL-CLOSED` | Each unreadable authoritative dependency denies. |
| `FI-TRACE-AUTHORITY-UNIFORM` | Every protected ingress reaches one current final-admission authority. |
| `FI-TRACE-CROSS-DOMAIN-COLLISION` | Equal subjects across issuers and equal pairs across domains remain distinct. |
| `FI-TRACE-PRIVACY-NONPUBLIC` / `DISCOVERY-PRIVATE` | Private identity does not enter public surfaces; complete discovery bytes remain identical across attested-key, TOFU, and companion enrollment modes. |
| `FI-TRACE-PRIVACY-NONPUBLIC` | Private identity does not enter public surfaces. |
| `FI-TRACE-DISCOVERY-PRIVATE` | Complete discovery bytes remain identical across attested-key, TOFU, and companion enrollment modes. |
| `FI-TRACE-TOFU-THEFT` | Stolen-assertion first use denies unless private TOFU is enabled and the attacker also proves its chosen key. |
## Security considerations