Implement a CLSAG algorithm extension which also does key images

Practically, this should be mergeable. There's little reason to do a 
CLSAG and not also a key image. Keeps them isolated for now.
This commit is contained in:
Luke Parker
2022-04-29 22:03:34 -04:00
parent 45559e14ee
commit 27396a6291
10 changed files with 213 additions and 103 deletions

View File

@@ -1,6 +1,6 @@
use rand::{RngCore, rngs::OsRng};
use curve25519_dalek::{constants::ED25519_BASEPOINT_TABLE, scalar::Scalar};
use curve25519_dalek::{constants::ED25519_BASEPOINT_TABLE, scalar::Scalar, edwards::EdwardsPoint};
use monero_serai::{random_scalar, Commitment, frost::MultisigError, key_image, clsag};
@@ -39,17 +39,27 @@ fn test_single() {
&vec![(
secrets[0],
clsag::Input::new(
image,
ring.clone(),
RING_INDEX,
Commitment::new(secrets[1], AMOUNT)
).unwrap()
).unwrap(),
image
)],
Scalar::zero()
).unwrap().swap_remove(0);
assert!(clsag::verify(&clsag, &msg, image, &ring, pseudo_out));
}
#[cfg(feature = "multisig")]
#[derive(Clone, Debug)]
struct Msg([u8; 32]);
#[cfg(feature = "multisig")]
impl clsag::Msg for Msg {
fn msg(&self, _: EdwardsPoint) -> [u8; 32] {
self.0
}
}
#[cfg(feature = "multisig")]
#[test]
fn test_multisig() -> Result<(), MultisigError> {
@@ -58,8 +68,6 @@ fn test_multisig() -> Result<(), MultisigError> {
let msg = [1; 32];
let image = key_image::generate(&group_private.0);
let randomness = random_scalar(&mut OsRng);
let mut ring = vec![];
for i in 0 .. RING_LEN {
@@ -79,13 +87,13 @@ fn test_multisig() -> Result<(), MultisigError> {
}
let mut algorithms = Vec::with_capacity(t);
for i in 1 ..= t {
for _ in 1 ..= t {
algorithms.push(
clsag::Multisig::new(
clsag::Input::new(image, ring.clone(), RING_INDEX, Commitment::new(randomness, AMOUNT)).unwrap()
clsag::InputMultisig::new(
clsag::Input::new(ring.clone(), RING_INDEX, Commitment::new(randomness, AMOUNT)).unwrap(),
Msg(msg)
).unwrap()
);
algorithms[i - 1].set_msg(msg);
}
let mut signatures = sign(algorithms, keys);

View File

@@ -41,13 +41,12 @@ impl Algorithm<Ed25519> for DummyAlgorithm {
fn context(&self) -> Vec<u8> { unimplemented!() }
fn process_binding(&mut self, _: &Scalar) { unimplemented!() }
fn sign_share(
&mut self,
_: &sign::ParamsView<Ed25519>,
_: EdwardsPoint,
_: Scalar,
_: Scalar,
_: &[u8],
) -> Scalar { unimplemented!() }

View File

@@ -9,7 +9,7 @@ use monero::{
use monero_serai::{
random_scalar,
transaction,
transaction::{self, SignableTransaction},
rpc::Rpc
};
@@ -48,9 +48,9 @@ pub async fn send() {
output = transaction::scan(&tx, view, spend_pub).swap_remove(0);
// Test creating a zero change output and a non-zero change output
amount = output.commitment.amount - fee - u64::try_from(i).unwrap();
let tx = transaction::send(
&mut OsRng, &rpc, &spend, &vec![output], &vec![(addr, amount)], addr, fee_per_byte
).await.unwrap();
let tx = SignableTransaction::new(
vec![output], vec![(addr, amount)], addr, fee_per_byte
).sign(&mut OsRng, &rpc, &spend).await.unwrap();
rpc.publish_transaction(&tx).await.unwrap();
}
}