Technik › Netzwerk

Aufbau einer Transaktion

Was in den Bytes einer Monero-Transaktion steckt: Präfix, RingCT-Signatur und der prunable Teil

Kurz gesagt

Eine Transaktion = ein Präfix (Version, Inputs, Outputs, Extra) + die RingCT-Basis (Typ, Gebühr, verschlüsselte Beträge, Output-Commitments) + der prunable Teil (Bulletproofs+, CLSAG, Pseudo-Outputs). Der Transaktions-Hash wird aus den Hashes der drei Teile gebildet, sodass alte Nodes den prunable Teil verwerfen können (Pruning), während er überprüfbar bleibt.

Präfix

version        = 2
unlock_time    = 0                       // altes Feld, heute immer 0
vin[]:                                   // Inputs
  txin_to_key:
    amount       = 0                     // Beträge sind in RingCT verborgen
    key_offsets  = [g₀, Δ₁, …, Δ₁₅]      // 16 globale Indizes, als relative Offsets
    k_image      = I                     // Key Image, 32 Bytes
vout[]:                                  // Outputs
  amount = 0
  target: txout_to_tagged_key
    key      = P                         // Einmalschlüssel, 32 Bytes
    view_tag = 1 byte
extra          = [0x01 ‖ R, …]           // Transaktionsschlüssel und mehr

key_offsets werden als Differenzen gespeichert: Der erste ist der absolute Index des Outputs, die übrigen sind Abstände zum jeweils vorherigen. Kleine Zahlen brauchen als Varints weniger Bytes.

RingCT-Basis

type       = 6                           // RCTTypeBulletproofPlus
txnFee     = fee in atomic units (varint)
ecdhInfo[] = encrypted amount, 8 bytes per output
outPk[]    = commitment C, 32 bytes per output

Prunable Teil

bulletproofs_plus[] = one aggregated proof
CLSAGs[]            = { s[16], c1, D } per input
pseudoOuts[]        = C̃, 32 bytes per input

Transaktions-Hash

txid = Keccak( H(prefix) ‖ H(RingCT base) ‖ H(prunable) )

Dieser „Baum aus drei Hashes“ erlaubt es einem prunenden Node, die schweren Beweise alter Transaktionen zu verwerfen (und den Hash zu behalten), während sich die Txid weiterhin berechnen lässt.

Gebühren

Die Gebühr hängt vom Gewicht der Transaktion ab (≈ Größe in Bytes, angepasst für Bulletproofs+, damit Transaktionen mit vielen Outputs nicht unverhältnismäßig billig sind) und von einer Prioritätsstufe. Der Grundpreis pro Byte passt sich an die Median-Blockgröße an – siehe dynamische Blockgröße.

Was sich mit FCMP++ ändert

  • Statt key_offsets – ein Verweis auf den Block, gegen dessen Baumzustand der Beweis gebaut wird.
  • Statt CLSAG – ein Mitgliedschaftsbeweis und SA+L; das Key Image bleibt.
  • Output-Format – Carrot (3-Byte-View-Tags, Janus-Anker).