Просмотр исходного кода

[src/contract/consensus] sk is non-resettable

ertosns 3 лет назад
Родитель
Сommit
7a98f5c273

+ 1 - 0
src/contract/consensus/proof/consensus_burn_v1.zk

@@ -39,6 +39,7 @@ circuit "ConsensusBurn_V1" {
 	constrain_instance(pub_x);
 	constrain_instance(pub_y);
 
+
 	# Coin hash	
 	C = poseidon_hash(
 		pub_x,

+ 10 - 5
src/contract/consensus/proof/consensus_proposal_v1.zk

@@ -23,10 +23,6 @@ witness "ConsensusProposal_V1" {
 	Uint32 leaf_pos,
 	# Merkle path to the coin
 	MerklePath path,
-	# x coordinate for the new coin's public key
-	Base output_pub_x,
-	# y coordinate for new coin's public key
-	Base output_pub_y,
 	# Random blinding factor for the value commitment of the new coin
 	Scalar output_value_blind,
 	# Random blinding factor for new coin
@@ -48,6 +44,7 @@ circuit "ConsensusProposal_V1" {
 	ZERO = witness_base(0);
 	SERIAL_PREFIX = witness_base(2);
 	SEED_PREFIX = witness_base(3);
+        SECRET_PREFIX = witness_base(4);
 
 	# =============
 	# Burn old coin
@@ -111,6 +108,14 @@ circuit "ConsensusProposal_V1" {
 
 	# The serial of the new coin is derived from the old coin
 	output_serial = poseidon_hash(SERIAL_PREFIX, input_secret_key, input_serial);
+
+        # output secret key derived from input key
+        output_secret_key = poseidon_hash(SECRET_PREFIX, input_secret_key);
+
+        output_pub = ec_mul_base(output_secret_key, NULLIFIER_K);
+	output_pub_x = ec_get_x(output_pub);
+	output_pub_y = ec_get_y(output_pub);
+        
 	# Poseidon hash of the new coin
 	# In here we set the new epoch as ZERO, thus removing a
 	# potentially existing timelock.
@@ -122,7 +127,7 @@ circuit "ConsensusProposal_V1" {
 		output_serial,
 		output_coin_blind,
 	);
-	constrain_instance(output_coin);
+       	constrain_instance(output_coin);
 
 	# ============================
 	# Constrain lottery parameters

+ 4 - 4
src/contract/consensus/src/client/proposal_v1.rs

@@ -128,6 +128,7 @@ pub struct ConsensusProposalCallBuilder {
 
 impl ConsensusProposalCallBuilder {
     pub fn build(&self) -> Result<ConsensusProposalCallDebris> {
+        let SECRET_PREFIX = pallas::Base::from(4);
         info!("Building Consensus::ProposalBurnV1 contract call");
         assert!(self.owncoin.note.value != 0);
 
@@ -147,8 +148,9 @@ impl ConsensusProposalCallBuilder {
         let output_reward_blind = pallas::Scalar::random(&mut OsRng);
         let output_value_blind = input.value_blind + output_reward_blind;
 
-        // We create a new random keypair for the output
-        let output_keypair = Keypair::random(&mut OsRng);
+        // derive output secret from old secret key.
+        let output_secret = poseidon_hash([SECRET_PREFIX, self.owncoin.secret.inner()]);
+        let output_keypair = Keypair::new(SecretKey::from(output_secret));
 
         // The output's serial is derived from the old serial
         let output_serial =
@@ -326,8 +328,6 @@ fn create_proposal_proof(
         Witness::Base(Value::known(input.note.coin_blind)),
         Witness::Uint32(Value::known(u64::from(input.leaf_position).try_into().unwrap())),
         Witness::MerklePath(Value::known(input.merkle_path.clone().try_into().unwrap())),
-        Witness::Base(Value::known(output_x)),
-        Witness::Base(Value::known(output_y)),
         Witness::Scalar(Value::known(output.value_blind)),
         Witness::Base(Value::known(output.coin_blind)),
         Witness::Base(Value::known(public_inputs.mu_y)),

+ 12 - 6
src/contract/consensus/src/client/unstake_request_v1.rs

@@ -28,15 +28,17 @@ use darkfi_money_contract::{
     model::{ConsensusInput, ConsensusOutput, ConsensusUnstakeReqParamsV1},
 };
 use darkfi_sdk::{
-    crypto::{note::AeadEncryptedNote, pasta_prelude::*, Keypair, MerkleTree, SecretKey},
+    crypto::{note::AeadEncryptedNote, pasta_prelude::*, Keypair, MerkleTree, SecretKey, poseidon_hash},
     pasta::pallas,
 };
 use log::{debug, info};
 use rand::rngs::OsRng;
 
-use crate::client::common::{
-    create_consensus_burn_proof, create_consensus_mint_proof, ConsensusBurnInputInfo,
-    ConsensusMintOutputInfo,
+use crate::{
+    client::common::{create_consensus_burn_proof, create_consensus_mint_proof, ConsensusBurnInputInfo, ConsensusMintOutputInfo},
+    model::{
+        SERIAL_PREFIX,
+    },
 };
 
 pub struct ConsensusUnstakeRequestCallDebris {
@@ -85,11 +87,15 @@ impl ConsensusUnstakeRequestCallBuilder {
         };
 
         debug!("Building Consensus::UnstakeRequestV1 anonymous output");
-        let output_serial = pallas::Base::random(&mut OsRng);
+        //let output_serial = pallas::Base::random(&mut OsRng);
+        // derive output secret from old secret key.
+        let output_secret = poseidon_hash([self.owncoin.secret.inner()]);
+        let output_keypair = Keypair::new(SecretKey::from(output_secret));
+        let output_serial = poseidon_hash([SERIAL_PREFIX, self.owncoin.secret.inner(), self.owncoin.note.serial]);
         let output_coin_blind = pallas::Base::random(&mut OsRng);
 
         // We create a new random keypair for the output
-        let output_keypair = Keypair::random(&mut OsRng);
+        //let output_keypair = Keypair::random(&mut OsRng);
 
         let output = ConsensusMintOutputInfo {
             value: self.owncoin.note.value,