TimeChain Explorer
Open any Montana coin transfer by its id or its confirmation link and check it yourself. The record is read from the nodes; its hash, its post-quantum signature and its key's balance — folded from the key's whole chain — are verified here, in your browser.
Reported network checkpoint
Recent transfers
The newest records on each node. Every row is checked here as it is listed: its hash, its signature and its place on its key's chain.
How to verify independently
A transfer is one record, signed by the sender's seed and laid on its key's chain, on the node its key chooses; the log only grows: a record is never replaced or deleted. Integers are little-endian.
The record's layout follows, with its signature, id and sender's address in Python's notation (a slice [a:b] takes bytes a to b − 1).
The record — 5443 bytes
A record carries its kind and the fields its kind uses; a field a kind does not use is zero. SEND: pair is the pair tag, to = SHA-256(mt-coin-to ‖ from of the receiver ‖ blind), where blind = HMAC-SHA-256 under the pair's secret over mt-coin-blind ‖ nonce, and t0 is the part of the amount that was announced rather than minted. RECV: to carries the blind, ref the SEND it receives, t0 the same announced part. REFUND: ref names the sender's own SEND. MINT: t0 and t1 bound the minted seconds. GENESIS: the balance the key's wallet announced when its chain opened.
| Offset | Bytes | Field | Content |
|---|---|---|---|
| 0 | 4 | magic | ASCII MTTX |
| 4 | 1 | version | 0x03 |
| 5 | 1 | kind | 1 SEND, 2 RECV, 3 MINT, 4 REFUND, 5 GENESIS |
| 6 | 8 | amount | u64, coins, 1 or more |
| 14 | 8 | birth | u64, milliseconds since 1970-01-01 UTC, the sender's clock |
| 22 | 16 | nonce | random |
| 38 | 32 | prev | the id of the key's previous record on its chain; 32 zero bytes for the first |
| 70 | 32 | pair | HMAC-SHA-256 under the pair's secret over ASCII mt-coin-pair-v1 |
| 102 | 32 | to | SEND: the receiver's commitment; RECV: the blind that opens it |
| 134 | 32 | ref | RECV, REFUND: the id of the SEND they settle |
| 166 | 8 | t0 | MINT: the first minted second (node seconds since 1970); SEND, RECV: the announced part of the amount |
| 174 | 8 | t1 | MINT: the second after the last minted one |
| 182 | 1952 | pubkey | the sender's ML-DSA-65 public key |
| 2134 | 3309 | sig | ML-DSA-65 signature |
msg = b"mt-coin-tx-v3" + record[0:2134]
pk = record[182:2134]
sig = record[2134:5443]
valid = ML-DSA-65.Verify(pk, msg, sig, ctx=b"") # FIPS 204
id = SHA-256(record).hex()
from = SHA-256(pk).hex()
prev = record[38:70].hex() # 64 zeros: the key's first record
chain = ["montana.quest", "montana.xxx"][SHA-256(pk)[0] % 2] # the node whose word countsA key's chain lives on one node of the protocol's fixed table of chain nodes, sorted by name (the formula above): the one at index from[0] mod n, where from[0] is the first byte of the sender's address. That node takes a record only on top of the key's head, so of two records on one predecessor only one ever stands. Follow prev from record to record to walk a key's chain back to its first record; this page links each record to the one before it.
A key's balance is the fold of its chain from its first record: MINT adds at most 2 × min(13, max(1, bit_length(s) − 1)) coins for the s-th second since the key's first record, over an interval of at least 60 seconds that starts where the last one ended; SEND subtracts, the minted part first, and may not go below zero; RECV adds a SEND whose to opens to this key with its blind; REFUND adds back the key's own SEND after a day if nobody received it. A SEND laid before its receiver's key was known names no receiver: it subtracts the same way, and the receiver's wallet carries the coins into its own chain by a MINT within its own time. The SEND's chain node settles each SEND once: received or refunded, never both.
The signature is ML-DSA-65 of FIPS 204 with an empty context, so any implementation of the standard checks it. This page verifies it with Montana's core compiled to WebAssembly — the module Montana's web app runs — and computes SHA-256 with your browser's Web Crypto.
The pair tag is known to the two ends of the conversation and to no one else: anyone sees that the address paid a pair, never who the pair is.
Every node verifies the signature with Montana's core before it takes a record, and every reader checks it again before believing it — the wallet before a credit, this page before it says valid. Read a record yourself from either node; the command prints the record's length, its id and the sender's address:
curl -s -H 'Content-Type: application/json' -d '{"id":"{id}"}' https://montana.xxx/pushwake/tx-get | python3 -c 'import sys,json,base64,hashlib; r=base64.b64decode(json.load(sys.stdin)["rec"]); k={1:(69,2021),2:(101,2053),3:(182,2134)}[r[4]]; print(len(r), hashlib.sha256(r).hexdigest(), hashlib.sha256(r[k[0]:k[1]]).hexdigest())'
curl -s -H 'Content-Type: application/json' -d '{"id":"{id}"}' https://montana.xxx/pushwake-msk/tx-get | python3 -c 'import sys,json,base64,hashlib; r=base64.b64decode(json.load(sys.stdin)["rec"]); k={1:(69,2021),2:(101,2053),3:(182,2134)}[r[4]]; print(len(r), hashlib.sha256(r).hexdigest(), hashlib.sha256(r[k[0]:k[1]]).hexdigest())'What a record proves. Every move of a key's balance is a record of its chain: coins enter only by MINT (no more than the time the key has lived allows), RECV (opening a transfer addressed to this key) or REFUND (a transfer nobody received within a day), and leave only by SEND. The chain's node refuses a SEND above what the chain holds, every node and every phone that keeps a copy folds the same chain, and this page folds it again in your browser.
The confirmation link of a transfer is https://montana.xxx/explorer/#tx= followed by its id.
Format: the Montana coin record (MTTX).
