-
Notifications
You must be signed in to change notification settings - Fork 6
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Make better use of the type system #6
Make better use of the type system #6
Conversation
122cc7d
to
b4af743
Compare
This is helpful because we sometimes need to peek at the next value to deserialize the right thing.
The previous model was to flexible in that it allowed to express states that were not actually possible (like explicit value but confidential asset).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Half-review
tx: &crate::Transaction, | ||
index: usize, | ||
script_code: &bitcoin::Script, | ||
value: &crate::confidential::Value, | ||
value: &V, // TODO: Is this really the best way to do it? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ Should we introduce a ValueCommitment
type?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It actually exists. Should we use it here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well, you can use this function for confidential and non-confidential values. The new model system doesn't (yet) offer anything here.
use crate::issuance::AssetId; | ||
|
||
// TODO: Is `Default` really useful here? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ Why not? A null asset issuance is what I would expect when I need the rest of a transaction to be default.
|
||
impl ExplicitAssetIssuance { | ||
pub fn encoded_length(&self) -> usize { | ||
32 + 32 + self.amount.encoded_length() + self.inflation_keys.encoded_length() |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ Should we use a SECRET_KEY_LENGTH
sort of constant (that may already exist) instead of magic numbers?
pub struct NullAssetIssuance { | ||
/// Zero for a new asset issuance; otherwise a blinding factor for the input | ||
pub asset_blinding_nonce: [u8; 32], | ||
/// Freeform entropy field | ||
pub asset_entropy: [u8; 32], | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ Can you explain why a null asset issuance has any fields at all? Doesn't make sense to me given the name.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well, the data is still there I think, like I need to deserialize it. Will have to do some testing to see if this can be improved!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's just weird that there has to be any data at all if the transaction does not issue an asset. Unless this data is unrelated to asset issuances?
)] | ||
pub struct ConfidentialAssetIssuance { | ||
/// Zero for a new asset issuance; otherwise a blinding factor for the input | ||
pub asset_blinding_nonce: [u8; 32], |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ Have you thought about using SecretKey
for some of these fields? Would it make sense?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Haven't yet thought about it, wanted to get the big refactoring in first!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This looks really good to me! I would consider upstreaming this. The worst that can happen is that they say no and we just continue with our own version of it.
pub struct PeginData<'tx> { | ||
/// Reference to the pegin output on the mainchain | ||
pub outpoint: bitcoin::OutPoint, | ||
/// The value, in satoshis, of the pegin | ||
pub value: u64, | ||
/// Asset type being pegged in | ||
pub asset: confidential::Asset, | ||
pub asset: AssetId, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ Does this mean that this struct is always explicit?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes from my understanding yes!
derive(serde::Serialize, serde::Deserialize), | ||
serde(crate = "serde_crate") | ||
)] | ||
pub struct NullTxOut { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ When does elements use null txouts? Just curious.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't fully understand this yet :D
derive(serde::Serialize, serde::Deserialize), | ||
serde(crate = "serde_crate", transparent) | ||
)] | ||
pub struct ExplicitValue(pub u64); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
❓ Should we be using bitcoin::Amount
under the hood? Is that a horrible idea?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not a horrible idea because all tokens have the same decimal points :)
pub fn unblind(&self, blinding_key: SecretKey) -> Result<UnblindedTxOut, UnblindError> { | ||
let sender_ephemeral_pk = self.nonce.ok_or(UnblindError::MissingNonce)?.commitment(); | ||
let sender_ephemeral_pk = PublicKey::from_slice(&sender_ephemeral_pk) | ||
.map_err(|_| UnblindError::InvalidPublicKey)?; | ||
|
||
let (unblinded_asset, abf, vbf, value_out) = asset_unblind( | ||
sender_ephemeral_pk, | ||
blinding_key, | ||
&self.witness.rangeproof, | ||
self.value, | ||
&self.script_pubkey, | ||
self.asset, | ||
) | ||
.map_err(|_| UnblindError::Wally)?; | ||
|
||
Ok(UnblindedTxOut { | ||
asset: AssetId::from_slice(&unblinded_asset).unwrap(), | ||
original_asset: self.asset, | ||
asset_blinding_factor: abf, | ||
value_blinding_factor: vbf, | ||
value: value_out, | ||
}) | ||
} | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🎉 This makes it all worth it! Awesome work.
|
||
if !has_min { | ||
min_value | ||
} else if has_nonzero_range { | ||
bitcoin::consensus::deserialize::<u64>(&self.witness.rangeproof[2..10]) | ||
bitcoin::consensus::deserialize::<u64>(&witness.rangeproof[2..10]) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🤔 Imagine if we had a rangeproof struct.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is all possible :D
// assert_eq!( | ||
// tx.input[0].asset_issuance, | ||
// AssetIssuance { | ||
// asset_blinding_nonce: [0; 32], | ||
// asset_entropy: [0; 32], | ||
// amount: confidential::Value::Confidential( | ||
// 9, | ||
// [ | ||
// 0x81, 0x65, 0x4e, 0xb5, 0xcc, 0xd9, 0x92, 0x7b, 0x8b, 0xea, 0x94, 0x99, | ||
// 0x7d, 0xce, 0x4a, 0xe8, 0x5b, 0x3d, 0x95, 0xa2, 0x07, 0x00, 0x38, 0x4f, | ||
// 0x0b, 0x8c, 0x1f, 0xe9, 0x95, 0x18, 0x06, 0x38 | ||
// ], | ||
// ), | ||
// inflation_keys: confidential::Value::Null, | ||
// } | ||
// ); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🔧 I guess you meant to remove it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ups, no I didn't!
Will put it back!
See commit messages.