syntax = "proto2"; package hw.trezor.messages.monero; // Sugar for easier handling in Java option java_package = "com.satoshilabs.trezor.lib.protobuf"; option java_outer_classname = "TrezorMessageMonero"; enum MoneroNetworkType { MAINNET = 0; TESTNET = 1; STAGENET = 2; FAKECHAIN = 3; } /** * Structure representing Monero transaction source entry, UTXO * @embed */ message MoneroTransactionSourceEntry { repeated MoneroOutputEntry outputs = 1; // all outputs including decoys (forms the ring) optional uint64 real_output = 2; // index denoting which item in `outputs` is our real output (not a decoy) optional bytes real_out_tx_key = 3; // tx key located in the real output's tx repeated bytes real_out_additional_tx_keys = 4; // additional tx keys if applicable optional uint64 real_output_in_tx_index = 5; // index of our real output in the tx (aka which output was it in the transaction) optional uint64 amount = 6; optional bool rct = 7; // is RingCT used (true for newer UTXOs) optional bytes mask = 8; optional MoneroMultisigKLRki multisig_kLRki = 9; optional uint32 subaddr_minor = 10; // minor subaddr index UTXO was sent to message MoneroOutputEntry { optional uint64 idx = 1; optional MoneroRctKeyPublic key = 2; message MoneroRctKeyPublic { required bytes dest = 1; required bytes commitment = 2; } } message MoneroMultisigKLRki { optional bytes K = 1; optional bytes L = 2; optional bytes R = 3; optional bytes ki = 4; } } /** * Structure representing Monero transaction destination entry * @embed */ message MoneroTransactionDestinationEntry { optional uint64 amount = 1; optional MoneroAccountPublicAddress addr = 2; optional bool is_subaddress = 3; optional bytes original = 4; optional bool is_integrated = 5; /** * Structure representing Monero public address */ message MoneroAccountPublicAddress { optional bytes spend_public_key = 1; optional bytes view_public_key = 2; } } /** * Range sig parameters / data. * @embed */ message MoneroTransactionRsigData { optional uint32 rsig_type = 1; // range signature (aka proof) type optional uint32 offload_type = 2; repeated uint64 grouping = 3; // aggregation scheme for BP optional bytes mask = 4; // mask vector optional bytes rsig = 5; // range sig data, all of it or partial (based on rsig_parts) repeated bytes rsig_parts = 6; optional uint32 bp_version = 7; // Bulletproof version } /** * Request: Ask device for public address derived from seed and address_n * @start * @next MoneroAddress * @next Failure */ message MoneroGetAddress { repeated uint32 address_n = 1; // BIP-32 path to derive the key from master node optional bool show_display = 2; // Optionally show on display before sending the result optional MoneroNetworkType network_type = 3 [default=MAINNET]; // Network type optional uint32 account = 4; // Major subaddr index optional uint32 minor = 5; // Minor subaddr index optional bytes payment_id = 6; // Payment ID for integrated address } /** * Response: Contains Monero watch-only credentials derived from device private seed * @end */ message MoneroAddress { optional bytes address = 1; } /** * Request: Ask device for watch only credentials * @start * @next MoneroWatchKey * @next Failure */ message MoneroGetWatchKey { repeated uint32 address_n = 1; // BIP-32 path to derive the key from master node optional MoneroNetworkType network_type = 2 [default=MAINNET]; // Network type } /** * Response: Contains Monero watch-only credentials derived from device private seed * @end */ message MoneroWatchKey { optional bytes watch_key = 1; optional bytes address = 2; } /** * Request: Sub request of MoneroTransactionSign. Initializes transaction signing. * @start * @next MoneroTransactionInitAck */ message MoneroTransactionInitRequest { optional uint32 version = 1; repeated uint32 address_n = 2; optional MoneroNetworkType network_type = 3 [default=MAINNET]; // Network type optional MoneroTransactionData tsx_data = 4; /** * Structure representing Monero initial transaction information */ message MoneroTransactionData { optional uint32 version = 1; optional bytes payment_id = 2; optional uint64 unlock_time = 3; repeated MoneroTransactionDestinationEntry outputs = 4; optional MoneroTransactionDestinationEntry change_dts = 5; optional uint32 num_inputs = 6; optional uint32 mixin = 7; optional uint64 fee = 8; optional uint32 account = 9; repeated uint32 minor_indices = 10; optional MoneroTransactionRsigData rsig_data = 11; repeated uint32 integrated_indices = 12; optional uint32 client_version = 13; // connected client version optional uint32 hard_fork = 14; // transaction hard fork number optional bytes monero_version = 15; // monero software version } } /** * Response: Response to transaction signing initialization. * @next MoneroTransactionSetInputRequest */ message MoneroTransactionInitAck { repeated bytes hmacs = 1; optional MoneroTransactionRsigData rsig_data = 2; } /** * Request: Sub request of MoneroTransactionSign. Sends one UTXO to device * @next MoneroTransactionSetInputAck */ message MoneroTransactionSetInputRequest { optional MoneroTransactionSourceEntry src_entr = 1; } /** * Response: Response to setting UTXO for signature. Contains sealed values needed for further protocol steps. * @next MoneroTransactionSetInputAck * @next MoneroTransactionInputViniRequest */ message MoneroTransactionSetInputAck { optional bytes vini = 1; // xmrtypes.TxinToKey optional bytes vini_hmac = 2; optional bytes pseudo_out = 3; optional bytes pseudo_out_hmac = 4; optional bytes pseudo_out_alpha = 5; optional bytes spend_key = 6; } /** * Request: Sub request of MoneroTransactionSign. Sends one UTXO to device together with sealed values. * @next MoneroTransactionInputViniAck */ message MoneroTransactionInputViniRequest { optional MoneroTransactionSourceEntry src_entr = 1; optional bytes vini = 2; // xmrtypes.TxinToKey optional bytes vini_hmac = 3; optional bytes pseudo_out = 4; optional bytes pseudo_out_hmac = 5; optional uint32 orig_idx = 6; // original sort index, before sorting by key-images } /** * Response: Response to setting UTXO to the device * @next MoneroTransactionInputViniRequest * @next MoneroTransactionAllInputsSetRequest */ message MoneroTransactionInputViniAck { } /** * Request: Sub request of MoneroTransactionSign. Sent after all inputs have been sent. Useful for rangeisg offloading. * @next MoneroTransactionAllInputsSetAck */ message MoneroTransactionAllInputsSetRequest { } /** * Response: Response to after all inputs have been set. * @next MoneroTransactionSetOutputRequest */ message MoneroTransactionAllInputsSetAck { optional MoneroTransactionRsigData rsig_data = 1; } /** * Request: Sub request of MoneroTransactionSign. Sends one transaction destination to device (HMACed) * @next MoneroTransactionSetOutputAck */ message MoneroTransactionSetOutputRequest { optional MoneroTransactionDestinationEntry dst_entr = 1; optional bytes dst_entr_hmac = 2; optional MoneroTransactionRsigData rsig_data = 3; optional bool is_offloaded_bp = 4; // Extra message, with offloaded BP. } /** * Response: Response to setting transaction destination. Contains sealed values needed for further protocol steps. * @next MoneroTransactionSetOutputRequest * @next MoneroTransactionAllOutSetRequest */ message MoneroTransactionSetOutputAck { optional bytes tx_out = 1; // xmrtypes.TxOut optional bytes vouti_hmac = 2; optional MoneroTransactionRsigData rsig_data = 3; optional bytes out_pk = 4; optional bytes ecdh_info = 5; } /** * Request: Sub request of MoneroTransactionSign. Sent after all outputs are sent. * @next MoneroTransactionAllOutSetAck */ message MoneroTransactionAllOutSetRequest { optional MoneroTransactionRsigData rsig_data = 1; } /** * Response: After all outputs are sent the initial RCT signature fields are sent. * @next MoneroTransactionSignInputRequest */ message MoneroTransactionAllOutSetAck { optional bytes extra = 1; optional bytes tx_prefix_hash = 2; optional MoneroRingCtSig rv = 4; // xmrtypes.RctSig optional bytes full_message_hash = 5; /* * Structure represents initial fields of the Monero RCT signature */ message MoneroRingCtSig { optional uint64 txn_fee = 1; optional bytes message = 2; optional uint32 rv_type = 3; } } /** * Request: Sub request of MoneroTransactionSign. Sends UTXO for the signing. * @next MoneroTransactionSignInputAck */ message MoneroTransactionSignInputRequest { optional MoneroTransactionSourceEntry src_entr = 1; optional bytes vini = 2; // xmrtypes.TxinToKey optional bytes vini_hmac = 3; optional bytes pseudo_out = 4; optional bytes pseudo_out_hmac = 5; optional bytes pseudo_out_alpha = 6; optional bytes spend_key = 7; optional uint32 orig_idx = 8; // original sort index, before sorting by key-images } /** * Response: Contains full MG signature of the UTXO + multisig data if applicable. * @next MoneroTransactionSignInputRequest * @next MoneroTransactionFinalRequest */ message MoneroTransactionSignInputAck { optional bytes signature = 1; optional bytes pseudo_out = 2; // updated pseudo-out after mask correction } /** * Request: Sub request of MoneroTransactionSign. Final message of the procol after all UTXOs are signed * @next MoneroTransactionFinalAck */ message MoneroTransactionFinalRequest { } /** * Response: Contains transaction metadata and encryption keys needed for further transaction operations (e.g. multisig, send proof). * @end */ message MoneroTransactionFinalAck { optional bytes cout_key = 1; optional bytes salt = 2; optional bytes rand_mult = 3; optional bytes tx_enc_keys = 4; optional bytes opening_key = 5; // enc master key to decrypt CLSAGs after protocol finishes correctly } /** * Request: Sub request of MoneroKeyImageSync. Initializing key image sync. * @start * @next MoneroKeyImageExportInitAck */ message MoneroKeyImageExportInitRequest { required uint64 num = 1; required bytes hash = 2; repeated uint32 address_n = 3; // BIP-32 path to derive the key from master node optional MoneroNetworkType network_type = 4 [default=MAINNET]; // network type repeated MoneroSubAddressIndicesList subs = 5; /** * Structure representing Monero list of sub-addresses */ message MoneroSubAddressIndicesList { required uint32 account = 1; repeated uint32 minor_indices = 2; } } /** * Response: Response to key image sync initialization. * @next MoneroKeyImageSyncStepRequest */ message MoneroKeyImageExportInitAck { } /** * Request: Sub request of MoneroKeyImageSync. Contains batch of the UTXO to export key image for. * @next MoneroKeyImageSyncStepAck */ message MoneroKeyImageSyncStepRequest { repeated MoneroTransferDetails tdis = 1; /** * Structure representing Monero UTXO for key image sync */ message MoneroTransferDetails { required bytes out_key = 1; required bytes tx_pub_key = 2; repeated bytes additional_tx_pub_keys = 3; required uint64 internal_output_index = 4; optional uint32 sub_addr_major = 5; optional uint32 sub_addr_minor = 6; } } /** * Response: Response to key image sync step. Contains encrypted exported key image. * @next MoneroKeyImageSyncStepRequest * @next MoneroKeyImageSyncFinalRequest */ message MoneroKeyImageSyncStepAck { repeated MoneroExportedKeyImage kis = 1; /** * Structure representing Monero encrypted exported key image */ message MoneroExportedKeyImage { optional bytes iv = 1; optional bytes blob = 3; } } /** * Request: Sub request of MoneroKeyImageSync. Final message of the sync protocol. * @next MoneroKeyImageSyncFinalAck */ message MoneroKeyImageSyncFinalRequest { } /** * Response: Response to key image sync step. Contains encryption keys for exported key images. * @end */ message MoneroKeyImageSyncFinalAck { optional bytes enc_key = 1; } /** * Request: Decrypt tx private keys blob * @next MoneroGetTxKeyAck */ message MoneroGetTxKeyRequest { repeated uint32 address_n = 1; // BIP-32 path to derive the key from master node optional MoneroNetworkType network_type = 2 [default=MAINNET]; // network type required bytes salt1 = 3; required bytes salt2 = 4; required bytes tx_enc_keys = 5; required bytes tx_prefix_hash = 6; optional uint32 reason = 7; // reason to display for user. e.g., tx_proof optional bytes view_public_key = 8; // addr for derivation } /** * Response: Response with the re-encrypted private keys and derivations blob under view key * @end */ message MoneroGetTxKeyAck { optional bytes salt = 1; optional bytes tx_keys = 2; optional bytes tx_derivations = 3; } /** * Request: Starts live refresh flow. Asks user permission, switches state * @next MoneroLiveRefreshStartAck */ message MoneroLiveRefreshStartRequest { repeated uint32 address_n = 1; // BIP-32 path to derive the key from master node optional MoneroNetworkType network_type = 2 [default=MAINNET]; // network type } /** * Response after user gave permission * @next MoneroLiveRefreshStepRequest * @next MoneroLiveRefreshFinalRequest */ message MoneroLiveRefreshStartAck { } /** * Request: Request to compute a single key image during live sync * @next MoneroLiveRefreshStepAck */ message MoneroLiveRefreshStepRequest { required bytes out_key = 1; required bytes recv_deriv = 2; required uint64 real_out_idx = 3; required uint32 sub_addr_major = 4; required uint32 sub_addr_minor = 5; } /** * Response: Response with the encrypted key image + signature * @next MoneroLiveRefreshStepRequest * @next MoneroLiveRefreshFinishedRequest */ message MoneroLiveRefreshStepAck { optional bytes salt = 1; optional bytes key_image = 2; } /** * Request: Request terminating live refresh mode. * @next MoneroLiveRefreshFinishedAck */ message MoneroLiveRefreshFinalRequest { } /** * Response: Response on termination of live refresh mode. * @end */ message MoneroLiveRefreshFinalAck { } /** * Request: Universal Monero protocol implementation diagnosis request. * @start * @next DebugMoneroDiagAck */ message DebugMoneroDiagRequest { optional uint64 ins = 1; optional uint64 p1 = 2; optional uint64 p2 = 3; repeated uint64 pd = 4; optional bytes data1 = 5; optional bytes data2 = 6; } /** * Response: Response to Monero diagnosis protocol. * @end */ message DebugMoneroDiagAck { optional uint64 ins = 1; optional uint64 p1 = 2; optional uint64 p2 = 3; repeated uint64 pd = 4; optional bytes data1 = 5; optional bytes data2 = 6; }