The Trust Code is a short human-verifiable value derived from the cryptographic proof.
It is not the primary authentication secret.
Inputs:
signature
rp_id
nonce
epoch
digits
amount_minor, optional
Steps:
1. Build salt:
salt = SHA256(rp_id || 0x00 || nonce || 0x00 || uint64_be(epoch))
2. Derive OKM:
OKM = HKDF-SHA256(signature, salt, "PPS/trust/v1", 32)
3. Derive decimal digits using rejection sampling.
4. Append AmountMark if present.
Default Trust Code length:
8 digits
If AmountMark is present:
base digits = 6
AmountMark digits = 2
total digits = 8
amount_minor = 2500067
AmountMark = 67
base Trust Code = 493718
final Trust Code = 49371867
use Pps\Trust\TrustCodeGenerator;
$valid = TrustCodeGenerator::verify(
enteredCode: '49371867',
signature: $signature,
rpId: 'example.com',
nonceBinary: $nonce,
epoch: $epoch,
amountMinor: 2500067
);
The Trust Phrase is an optional three-word phrase.
use Pps\Trust\TrustPhraseGenerator;
$phrase = TrustPhraseGenerator::generate(
signature: $signature,
rpId: 'example.com',
nonceBinary: $nonce,
epoch: $epoch
);
Example:
river bronze lantern
Short human-enterable codes have limited entropy.
Approximate entropy:
6 digits = 19.9 bits
8 digits = 26.6 bits
10 digits = 33.2 bits
12 digits = 39.9 bits
Therefore: