confidential_balance - [devnet]
此内容尚不支持你的语言。
Balance types for the confidential asset protocol.
A balances is chunked into vectors of -bit chunks such that where . Then, each chunk is encrypted as a tuple under an encryption key .
The pending balance has chunks while the available balance has such chunks. For Aptos, we need and .
CompressedBalance<T> and Balance<T> are parameterized by phantom markers Pending and Available.
use 0x1::option;use 0x1::ristretto255;use 0x1::vector;Constants
The number of chunks in an available balance.
const AVAILABLE_BALANCE_CHUNKS: u64 = 8;The number of bits in a single chunk.
const CHUNK_SIZE_BITS: u64 = 16;All chunks are < than this value
const CHUNK_UPPER_BOUND: u64 = 65536;Expected the P or R components to have the wrong number of chunks.
const E_WRONG_NUM_CHUNKS: u64 = 1;Expected the auditor R-component to be either empty or have the correct number of chunks.
const E_WRONG_NUM_CHUNKS_FOR_AUDITOR: u64 = 2;The number of chunks in a pending balance.
const PENDING_BALANCE_CHUNKS: u64 = 4;Structs
Pending
struct Pending has dropFields
-
dummy_field: bool
Available
struct Available has dropFields
-
dummy_field: bool
Functions
get_P
public(friend) fun get_P<T>(self: &confidential_balance::Balance<T>): &vector<ristretto255::RistrettoPoint>Implementation
public(friend) fun get_P<T>(self: &Balance<T>): &vector<RistrettoPoint> { &self.P }get_R
public(friend) fun get_R<T>(self: &confidential_balance::Balance<T>): &vector<ristretto255::RistrettoPoint>Implementation
public(friend) fun get_R<T>(self: &Balance<T>): &vector<RistrettoPoint> { &self.R }get_R_aud
public(friend) fun get_R_aud<T>(self: &confidential_balance::Balance<T>): &vector<ristretto255::RistrettoPoint>Implementation
public(friend) fun get_R_aud<T>(self: &Balance<T>): &vector<RistrettoPoint> { &self.R_aud }get_compressed_P
public(friend) fun get_compressed_P<T>(self: &confidential_balance::CompressedBalance<T>): &vector<ristretto255::CompressedRistretto>Implementation
public(friend) fun get_compressed_P<T>(self: &CompressedBalance<T>): &vector<CompressedRistretto> { &self.P }get_compressed_R
public(friend) fun get_compressed_R<T>(self: &confidential_balance::CompressedBalance<T>): &vector<ristretto255::CompressedRistretto>Implementation
public(friend) fun get_compressed_R<T>(self: &CompressedBalance<T>): &vector<CompressedRistretto> { &self.R }get_compressed_R_aud
public(friend) fun get_compressed_R_aud<T>(self: &confidential_balance::CompressedBalance<T>): &vector<ristretto255::CompressedRistretto>Implementation
public(friend) fun get_compressed_R_aud<T>(self: &CompressedBalance<T>): &vector<CompressedRistretto> { &self.R_aud }compress
public(friend) fun compress<T>(self: &confidential_balance::Balance<T>): confidential_balance::CompressedBalance<T>Implementation
public(friend) fun compress<T>(self: &Balance<T>): CompressedBalance<T> { CompressedBalance::V1 { P: self.P.map_ref(|p| p.point_compress()), R: self.R.map_ref(|r| r.point_compress()), R_aud: self.R_aud.map_ref(|r| r.point_compress()), }}decompress
public(friend) fun decompress<T>(self: &confidential_balance::CompressedBalance<T>): confidential_balance::Balance<T>Implementation
public(friend) fun decompress<T>(self: &CompressedBalance<T>): Balance<T> { Balance::V1 { P: self.P.map_ref(|p| p.point_decompress()), R: self.R.map_ref(|r| r.point_decompress()), R_aud: self.R_aud.map_ref(|r| r.point_decompress()), }}is_zero
public(friend) fun is_zero<T>(self: &confidential_balance::CompressedBalance<T>): boolImplementation
public(friend) fun is_zero<T>(self: &CompressedBalance<T>): bool { self.P.all(|p| p.is_identity()) && self.R.all(|r| r.is_identity())}add_mut_base
Element-wise P and R addition. R_aud is NOT touched.
public(friend) fun add_mut_base<T>(self: &mut confidential_balance::Balance<T>, rhs_P: &vector<ristretto255::RistrettoPoint>, rhs_R: &vector<ristretto255::RistrettoPoint>)Implementation
public(friend) fun add_mut_base<T>(self: &mut Balance<T>, rhs_P: &vector<RistrettoPoint>, rhs_R: &vector<RistrettoPoint>) { vector::range(0, rhs_P.length()).for_each(|i| { self.P[i].point_add_assign(&rhs_P[i]); self.R[i].point_add_assign(&rhs_R[i]); });}new_balance
fun new_balance<T>(p: vector<ristretto255::RistrettoPoint>, r: vector<ristretto255::RistrettoPoint>, r_aud: vector<ristretto255::RistrettoPoint>, expected_chunks: u64): confidential_balance::Balance<T>Implementation
fun new_balance<T>( p: vector<RistrettoPoint>, r: vector<RistrettoPoint>, r_aud: vector<RistrettoPoint>, expected_chunks: u64,): Balance<T> { assert_correct_num_chunks(&p, &r, &r_aud, expected_chunks); Balance::V1 { P: p, R: r, R_aud: r_aud }}new_compressed_balance
fun new_compressed_balance<T>(p: vector<ristretto255::CompressedRistretto>, r: vector<ristretto255::CompressedRistretto>, r_aud: vector<ristretto255::CompressedRistretto>, expected_chunks: u64): confidential_balance::CompressedBalance<T>Implementation
fun new_compressed_balance<T>( p: vector<CompressedRistretto>, r: vector<CompressedRistretto>, r_aud: vector<CompressedRistretto>, expected_chunks: u64,): CompressedBalance<T> { assert_correct_num_chunks(&p, &r, &r_aud, expected_chunks); CompressedBalance::V1 { P: p, R: r, R_aud: r_aud }}new_zero_compressed
fun new_zero_compressed<T>(num_chunks: u64): confidential_balance::CompressedBalance<T>Implementation
fun new_zero_compressed<T>(num_chunks: u64): CompressedBalance<T> { let identity = point_identity_compressed(); new_compressed_balance<T>( vector::range(0, num_chunks).map(|_| identity), vector::range(0, num_chunks).map(|_| identity), vector[], num_chunks )}new_pending_from_p_and_r
public(friend) fun new_pending_from_p_and_r(p: vector<ristretto255::RistrettoPoint>, r: vector<ristretto255::RistrettoPoint>): confidential_balance::Balance<confidential_balance::Pending>Implementation
public(friend) fun new_pending_from_p_and_r(p: vector<RistrettoPoint>, r: vector<RistrettoPoint>): Balance<Pending> { new_balance(p, r, vector[], PENDING_BALANCE_CHUNKS)}new_zero_pending_compressed
public(friend) fun new_zero_pending_compressed(): confidential_balance::CompressedBalance<confidential_balance::Pending>Implementation
public(friend) fun new_zero_pending_compressed(): CompressedBalance<Pending> { new_zero_compressed(PENDING_BALANCE_CHUNKS)}new_pending_u64_no_randomness
Creates a pending balance from a 64-bit amount with no randomness (R = identity).
public(friend) fun new_pending_u64_no_randomness(amount: u64): confidential_balance::Balance<confidential_balance::Pending>Implementation
public(friend) fun new_pending_u64_no_randomness(amount: u64): Balance<Pending> { let identity = point_identity(); new_pending_from_p_and_r( split_into_chunks((amount as u128), PENDING_BALANCE_CHUNKS).map(|chunk| chunk.basepoint_mul()), vector::range(0, PENDING_BALANCE_CHUNKS).map(|_| identity.point_clone()), )}add_assign_pending
Adds a pending balance to a compressed pending balance in place.
public(friend) fun add_assign_pending(balance: &mut confidential_balance::CompressedBalance<confidential_balance::Pending>, rhs: &confidential_balance::Balance<confidential_balance::Pending>): confidential_balance::CompressedBalance<confidential_balance::Pending>Implementation
public(friend) fun add_assign_pending(balance: &mut CompressedBalance<Pending>, rhs: &Balance<Pending>): CompressedBalance<Pending> { let decompressed = balance.decompress(); decompressed.add_mut_base(rhs.get_P(), rhs.get_R()); *balance = decompressed.compress(); *balance}get_num_pending_chunks
#[view]public fun get_num_pending_chunks(): u64Implementation
public fun get_num_pending_chunks(): u64 { PENDING_BALANCE_CHUNKS }new_available_from_p_r_r_aud
public(friend) fun new_available_from_p_r_r_aud(p: vector<ristretto255::RistrettoPoint>, r: vector<ristretto255::RistrettoPoint>, r_aud: vector<ristretto255::RistrettoPoint>): confidential_balance::Balance<confidential_balance::Available>Implementation
public(friend) fun new_available_from_p_r_r_aud( p: vector<RistrettoPoint>, r: vector<RistrettoPoint>, r_aud: vector<RistrettoPoint>): Balance<Available> { new_balance(p, r, r_aud, AVAILABLE_BALANCE_CHUNKS)}new_compressed_available_from_p_r_r_aud
public(friend) fun new_compressed_available_from_p_r_r_aud(p: vector<ristretto255::CompressedRistretto>, r: vector<ristretto255::CompressedRistretto>, r_aud: vector<ristretto255::CompressedRistretto>): confidential_balance::CompressedBalance<confidential_balance::Available>Implementation
public(friend) fun new_compressed_available_from_p_r_r_aud( p: vector<CompressedRistretto>, r: vector<CompressedRistretto>, r_aud: vector<CompressedRistretto>): CompressedBalance<Available> { new_compressed_balance(p, r, r_aud, AVAILABLE_BALANCE_CHUNKS)}new_zero_available_compressed
public(friend) fun new_zero_available_compressed(): confidential_balance::CompressedBalance<confidential_balance::Available>Implementation
public(friend) fun new_zero_available_compressed(): CompressedBalance<Available> { new_zero_compressed(AVAILABLE_BALANCE_CHUNKS)}new_compressed_available_from_bytes
Deserializes raw byte vectors into a CompressedBalance
public(friend) fun new_compressed_available_from_bytes(p_bytes: vector<vector<u8>>, r_bytes: vector<vector<u8>>, r_aud_bytes: vector<vector<u8>>): confidential_balance::CompressedBalance<confidential_balance::Available>Implementation
public(friend) fun new_compressed_available_from_bytes( p_bytes: vector<vector<u8>>, r_bytes: vector<vector<u8>>, r_aud_bytes: vector<vector<u8>>,): CompressedBalance<Available> { new_compressed_available_from_p_r_r_aud( deserialize_compressed_points(p_bytes), deserialize_compressed_points(r_bytes), deserialize_compressed_points(r_aud_bytes), )}set_available_R
Sets only the R component (EK component) of a compressed available balance.
public(friend) fun set_available_R(balance: &mut confidential_balance::CompressedBalance<confidential_balance::Available>, new_R: vector<ristretto255::CompressedRistretto>)Implementation
public(friend) fun set_available_R(balance: &mut CompressedBalance<Available>, new_R: vector<CompressedRistretto>) { assert!(new_R.length() == AVAILABLE_BALANCE_CHUNKS, error::invalid_argument(E_WRONG_NUM_CHUNKS)); balance.R = new_R;}add_assign_available_excluding_auditor
Adds a pending balance to an available balance in place. R_aud is NOT touched (stale after rollover).
public(friend) fun add_assign_available_excluding_auditor(self: &mut confidential_balance::CompressedBalance<confidential_balance::Available>, rhs: &confidential_balance::CompressedBalance<confidential_balance::Pending>)Implementation
public(friend) fun add_assign_available_excluding_auditor(self: &mut CompressedBalance<Available>, rhs: &CompressedBalance<Pending>) { let lhs_P = self.P.map_ref(|p| p.point_decompress()); let lhs_R = self.R.map_ref(|r| r.point_decompress()); let rhs_P = rhs.P.map_ref(|p| p.point_decompress()); let rhs_R = rhs.R.map_ref(|r| r.point_decompress());
vector::range(0, rhs_P.length()).for_each(|i| { lhs_P[i].point_add_assign(&rhs_P[i]); lhs_R[i].point_add_assign(&rhs_R[i]); });
self.P = lhs_P.map_ref(|p| p.point_compress()); self.R = lhs_R.map_ref(|r| r.point_compress());}get_num_available_chunks
#[view]public fun get_num_available_chunks(): u64Implementation
public fun get_num_available_chunks(): u64 { AVAILABLE_BALANCE_CHUNKS }get_chunk_size_bits
public(friend) fun get_chunk_size_bits(): u64Implementation
public(friend) fun get_chunk_size_bits(): u64 { CHUNK_SIZE_BITS }get_chunk_upper_bound
Every balance chunk is than this bound (i.e., ).
public(friend) fun get_chunk_upper_bound(): u64Implementation
public(friend) fun get_chunk_upper_bound(): u64 { CHUNK_UPPER_BOUND }split_into_chunks
Splits amount into num_chunks 16-bit chunks as Scalar values.
fun split_into_chunks(amount: u128, num_chunks: u64): vector<ristretto255::Scalar>Implementation
fun split_into_chunks(amount: u128, num_chunks: u64): vector<Scalar> { vector::range(0, num_chunks).map(|i| { new_scalar_from_u128(amount >> (i * CHUNK_SIZE_BITS as u8) & 0xffff) })}get_b_powers
Returns [B^0, B^1, …, B^{count-1}] where B = 2^chunk_size_bits.
public(friend) fun get_b_powers(count: u64): vector<ristretto255::Scalar>Implementation
public(friend) fun get_b_powers(count: u64): vector<Scalar> { let b = new_scalar_from_u128((CHUNK_UPPER_BOUND as u128)); let powers = vector[scalar_one()]; let prev = scalar_one(); for (i in 1..count) { prev = prev.scalar_mul(&b); powers.push_back(prev); }; powers}get_encryption_key_basepoint_compressed
Returns the compressed generator H used to derive the encryption key as EK = DK^(-1) * H.
public(friend) fun get_encryption_key_basepoint_compressed(): ristretto255::CompressedRistrettoImplementation
public(friend) fun get_encryption_key_basepoint_compressed(): CompressedRistretto { ristretto255::basepoint_H_compressed()}assert_correct_num_chunks
fun assert_correct_num_chunks<T>(p: &vector<T>, r: &vector<T>, r_aud: &vector<T>, expected_chunks: u64)Implementation
fun assert_correct_num_chunks<T>(p: &vector<T>, r: &vector<T>, r_aud: &vector<T>, expected_chunks: u64) { assert!(p.length() == expected_chunks, error::invalid_argument(E_WRONG_NUM_CHUNKS)); assert!(r.length() == expected_chunks, error::invalid_argument(E_WRONG_NUM_CHUNKS)); assert!(r_aud.is_empty() || r_aud.length() == expected_chunks, error::invalid_argument( E_WRONG_NUM_CHUNKS_FOR_AUDITOR ));}Enum CompressedBalance
enum CompressedBalance<T> has copy, drop, storeVariants
V1
Enum Balance
enum Balance<T> has drop