Skip to content

Commit

Permalink
Parse keys and certs from file in JSON format
Browse files Browse the repository at this point in the history
  • Loading branch information
iquerejeta authored and jpraynaud committed Sep 23, 2022
1 parent ede0dbe commit 85082d4
Show file tree
Hide file tree
Showing 7 changed files with 83 additions and 24 deletions.
2 changes: 1 addition & 1 deletion mithril-common/src/crypto_helper/mod.rs
Expand Up @@ -3,7 +3,7 @@
mod codec;
mod conversions;
mod genesis;
mod opcerts;
mod shelley_types;
pub mod tests_setup;
mod types;

Expand Down
@@ -1,7 +1,43 @@
use ed25519_dalek::{PublicKey as EdPublicKey, Signature as EdSignature, Verifier};
use hex::FromHex;
use kes_summed_ed25519::common::PublicKey as KesPublicKey;
use mithril::RegisterError;
use serde::de::DeserializeOwned;
use serde::{Deserialize, Serialize};
use std::fs;
use std::path::Path;

/// Parse error
#[derive(Debug)]
pub enum ParseError {
Path(std::io::Error),
JsonFormat(serde_json::Error),
CborData,
}

/// Fields for a shelley formatted file (holds for vkeys, skeys or certs)
#[derive(Clone, Debug, Default, Serialize, Deserialize)]
struct ShelleyFileFormat {
#[serde(rename = "type")]
file_type: String,
description: String,
#[serde(rename = "cborHex")]
cbor_hex: String,
}

pub(crate) trait FromShelleyFile {
fn from_file<R: DeserializeOwned, P: AsRef<Path>>(path: P) -> Result<R, ParseError> {
let data = fs::read_to_string(path).map_err(ParseError::Path)?;

let file: ShelleyFileFormat =
serde_json::from_str(&data).map_err(ParseError::JsonFormat)?;

let hex_vector = Vec::from_hex(file.cbor_hex).map_err(|_| ParseError::CborData)?;

let a: R = serde_cbor::from_slice(&hex_vector).map_err(|_| ParseError::CborData)?;
Ok(a)
}
}

/// Raw Fields of the operational certificates (without incluiding the cold VK)
#[derive(Clone, Debug, Deserialize, PartialEq, Eq, Serialize)]
Expand All @@ -16,6 +52,8 @@ struct RawFields(
#[derive(Clone, Debug, Deserialize, PartialEq, Eq, Serialize)]
struct RawOpCert(RawFields, EdPublicKey);

impl FromShelleyFile for RawOpCert {}

/// Parsed Operational Certificate
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct OpCert {
Expand All @@ -28,9 +66,9 @@ pub struct OpCert {

impl OpCert {
/// Parse raw bytes into an Operational Certificate
pub fn parse(bytes: &[u8]) -> Result<Self, RegisterError> {
pub fn from_file<P: AsRef<Path>>(path: P) -> Result<Self, RegisterError> {
let a: RawOpCert =
serde_cbor::from_slice(bytes).map_err(|_| RegisterError::SerializationError)?;
RawOpCert::from_file(path).map_err(|_| RegisterError::SerializationError)?;

Ok(Self {
kes_vk: KesPublicKey::from_bytes(&a.0 .0)
Expand Down Expand Up @@ -61,12 +99,10 @@ impl OpCert {
#[cfg(test)]
mod tests {
use super::*;
use hex::FromHex;

#[test]
fn test_vector_op_cert() {
let cbor_bytes = Vec::from_hex("8284582067fd5ccf770c0182a34d2b3d2011ca3a853ba947e17cae7543e668bc7687eb6a0000584050592bef1c630f2df499161d78bfadb44cc76cfd24048993ace4a45dade37b4f29e95172fde4e63581a93552f6986985616b70f61062a1db2ee0d3d8e671440e58202abf3ff537a2080f53fa38615906fa6094d44860902f2b2dffdbb41b811ff39f").expect("Invalid Hex String");
let cert = OpCert::parse(&cbor_bytes).unwrap();
let cert = OpCert::from_file("./test-data/node1.cert").unwrap();

assert!(cert.validate().is_ok())
}
Expand Down
39 changes: 21 additions & 18 deletions mithril-common/src/crypto_helper/types.rs
@@ -1,4 +1,4 @@
use crate::crypto_helper::opcerts::OpCert;
use crate::crypto_helper::shelley_types::{FromShelleyFile, OpCert, ParseError};
use blake2::{
digest::consts::{U28, U32},
Blake2b, Digest,
Expand All @@ -15,6 +15,7 @@ use mithril::{AggregationError, RegisterError};
use rand_core::{CryptoRng, RngCore};
use serde::{Deserialize, Serialize};
use std::collections::HashMap;
use std::path::Path;

/// A protocol version
pub type ProtocolVersion<'a> = &'a str;
Expand Down Expand Up @@ -106,6 +107,8 @@ impl ProtocolClerk {
}
}

impl FromShelleyFile for Sum6Kes {}

impl ProtocolInitializer {
/// Old setup. todo: remove
pub fn setup<R: RngCore + CryptoRng>(params: StmParameters, stake: Stake, rng: &mut R) -> Self {
Expand All @@ -117,21 +120,21 @@ impl ProtocolInitializer {
/// Builds an `StmInitializer` that is ready to register with the key registration service.
/// This function generates the signing and verification key with a PoP, signs the verification
/// key with a provided KES signing key, and initialises the structure.
pub fn setup_new<R: RngCore + CryptoRng>(
pub fn setup_new<R: RngCore + CryptoRng, P: AsRef<Path>>(
params: StmParameters,
kes_sk: &[u8],
kes_sk_path: P,
kes_period: usize,
stake: Stake,
rng: &mut R,
) -> Self {
) -> Result<Self, ParseError> {
let stm_initializer = StmInitializer::setup(params, stake, rng);
let kes_sk: Sum6Kes = serde_cbor::from_slice(kes_sk).expect("Invalid KES key provided"); // todo: handle this
let kes_sk: Sum6Kes = Sum6Kes::from_file(kes_sk_path)?;
let kes_signature = kes_sk.sign(kes_period, &stm_initializer.verification_key().to_bytes());

Self {
Ok(Self {
stm_initializer,
kes_signature: Some(kes_signature),
}
})
}

/// Extract the verification key.
Expand Down Expand Up @@ -199,14 +202,14 @@ impl NewProtocolKeyRegistration {
/// Register a new party. For a successful registration, the registrar needs to
/// provide the OpCert (in cbor form), the cold VK, a KES signature, and a
/// Mithril key (with its corresponding Proof of Possession).
pub fn register(
pub fn register<P: AsRef<Path>>(
&mut self,
opcert: &[u8],
opcert_path: P,
kes_sig: Sum6KesSig,
kes_period: usize,
pk: ProtocolSignerVerificationKey,
) -> Result<(), RegisterError> {
let cert = OpCert::parse(opcert)?;
let cert = OpCert::from_file(opcert_path)?;

cert.validate().map_err(|_| RegisterError::InvalidOpCert)?;
kes_sig
Expand Down Expand Up @@ -293,24 +296,24 @@ mod test {
);
let mut key_reg = NewProtocolKeyRegistration::init(&[(pool_id_1, 10), (pool_id_2, 3)]);

let sk_bytes_1 = Vec::from_hex("590260fe77acdfa56281e4b05198f5136018057a65f425411f0990cac4aca0f2917aa00a3d51e191f6f425d870aca3c6a2a41833621f5729d7bc0e3dfc3ae77d057e5e1253b71def7a54157b9f98973ca3c49edd9f311e5f4b23ac268b56a6ac040c14c6d2217925492e42f00dc89a2a01ff363571df0ca0db5ba37001cee56790cc01cd69c6aa760fca55a65a110305ea3c11da0a27be345a589329a584ebfc499c43c55e8c6db5d9c0b014692533ee78abd7ac1e79f7ec9335c7551d31668369b4d5111db78072f010043e35e5ca7f11acc3c05b26b9c7fe56f02aa41544f00cb7685e87f34c73b617260ade3c7b8d8c4df46693694998f85ad80d2cbab0b575b6ccd65d90574e84368169578bff57f751bc94f7eec5c0d7055ec88891a69545eedbfbd3c5f1b1c1fe09c14099f6b052aa215efdc5cb6cdc84aa810db41dbe8cb7d28f7c4beb75cc53915d3ac75fc9d0bf1c734a46e401e15150c147d013a938b7e07cc4f25a582b914e94783d15896530409b8acbe31ef471de8a1988ac78dfb7510729eff008084885f07df870b65e4f382ca15908e1dcda77384b5c724350de90cec22b1dcbb1cdaed88da08bb4772a82266ec154f5887f89860d0920dba705c45957ef6d93e42f6c9509c966277d368dd0eefa67c8147aa15d40a222f7953a4f34616500b310d00aa1b5b73eb237dc4f76c0c16813d321b2fc5ac97039be25b22509d1201d61f4ccc11cd4ff40fffe39f0e937b4722074d8e073a775d7283b715d46f79ce128e3f1362f35615fa72364d20b6db841193d96e58d9d8e86b516bbd1f05e45b39823a93f6e9f29d9e01acf2c12c072d1c64e0afbbabf6903ef542e").unwrap();
let initializer_1 = ProtocolInitializer::setup_new(params, &sk_bytes_1, 0, 10, &mut rng);
let initializer_1 =
ProtocolInitializer::setup_new(params, "./test-data/kes1.skey", 0, 10, &mut rng)
.unwrap();

let cbor_bytes_1 = Vec::from_hex("82845820f89d3fa14cabafa151638743b297379d3c3767902e36ae53b02b3a64bddda19d00005840e472042f7e78e3cfc4c2ac99a658a626be0e9d69e7072dc300cb28ce8178c329beb1d2cf4c7a7ce30d6c528ffad9e8d685fd9d58379758924a010ef317290b0e58207acec462970b819f5f7951e5c84eb87c8e7c4f1aceac01e1c1d97f2e25eb6005").expect("Invalid Hex String");
let key_registration_1 = key_reg.register(
&cbor_bytes_1,
"./test-data/node1.cert",
initializer_1.kes_signature.unwrap(),
0,
initializer_1.stm_initializer.verification_key(),
);
assert!(key_registration_1.is_ok());

let sk_bytes_2 = Vec::from_hex("590260d12460c331c7b978887899e2ccb119df7c4fa1e6f396778518f64a58f3d2232bf6481fba48fef9dc796f604b622cf0b41230c1662c221b448142bfddf8170865f1deec4232322acffb7d9001f21a4985c4acb4ca6af8906aefd9a7de6bc360acb59812a12ebd5b36a5603b497061f983921cdce59c836ccd2172f40dd62902809316c9a10cf8c44d5a22606fbdea4e210ec1540c6f5c9c1269b2af47d76aae7b009936bf4b62d0716bedf39e589b82381013c5dd68bae7496c4c726b4ae3992c188f1055ab61ef4ce9858958040147d02cec38b058919f0fcebbb9e48c25561634b58dc2d168994e2e22926f4d9d073d0c333db92d19a0c08617e03091b66f7574275db8f2fed75c21a539afedb85b1f163589eb8950ceeb6fb06f022fe544329df46fee5eb495e514846e341f0dafb8cf0d216c0ef3f18ceba6cad155694b74ae39d05a0a4729e595c1bfefa110199ec90a62e79a69c7dca595088e1a9fa1dd4f12be8e6f9e69178478d857d18f1abfc6bf567f5fcfd19bdfcb41c9a65879940a336d41a22ca66c84ccee0afd88aa237e48cb4f6115847eff96c095a7a6672e7b712d9acb8eb59dd9a1ce0ca1bc720ee1613b6e159d8b903694621f095319ba2292760ea0b975f17b3a48fb251b722ef190aa23385d05de93b3a21ef563f64e6e66e6e199267141e417e5b8a74a80f8ae6e69a4d9e778e9b7ca79f04d992b3851dbf703cd69829c837339d831b60273610d002454060bc9e1637358cd1a593166fe328dad39b8fa412b81841429ae022e26c452dce5bcd6500d48bd22af4ff94264978c1874946ce4ad53afcf9bde71973ef744823179dd98e24cd40d9498c1").unwrap();
let initializer_2 = ProtocolInitializer::setup_new(params, &sk_bytes_2, 0, 10, &mut rng);
let initializer_2 =
ProtocolInitializer::setup_new(params, "./test-data/kes2.skey", 0, 10, &mut rng)
.unwrap();

let cbor_bytes_2 = Vec::from_hex("82845820485981d05d157875fb5a69bbea8f6fc0c09c3da1754fb42a313d6f7a485ae2070000584024d23fed6746db342232e0ddab087879ade2bd936842af00b9c02f563d752cde583df1763283973ce527d118e79ae184c83a3a60a35898f23e9a441a2948240c5820ec91c9db4c0ffc5f39548b1eda07930b7a47510a0e1ce3cc621c6a3f9e899eda").expect("Invalid Hex String");
let key_registration_2 = key_reg.register(
&cbor_bytes_2,
"./test-data/node2.cert",
initializer_2.kes_signature.unwrap(),
0,
initializer_2.stm_initializer.verification_key(),
Expand Down
5 changes: 5 additions & 0 deletions mithril-common/test-data/kes1.skey
@@ -0,0 +1,5 @@
{
"type": "KesSigningKey_ed25519_kes_2^6",
"description": "KES Signing Key",
"cborHex": "590260fe77acdfa56281e4b05198f5136018057a65f425411f0990cac4aca0f2917aa00a3d51e191f6f425d870aca3c6a2a41833621f5729d7bc0e3dfc3ae77d057e5e1253b71def7a54157b9f98973ca3c49edd9f311e5f4b23ac268b56a6ac040c14c6d2217925492e42f00dc89a2a01ff363571df0ca0db5ba37001cee56790cc01cd69c6aa760fca55a65a110305ea3c11da0a27be345a589329a584ebfc499c43c55e8c6db5d9c0b014692533ee78abd7ac1e79f7ec9335c7551d31668369b4d5111db78072f010043e35e5ca7f11acc3c05b26b9c7fe56f02aa41544f00cb7685e87f34c73b617260ade3c7b8d8c4df46693694998f85ad80d2cbab0b575b6ccd65d90574e84368169578bff57f751bc94f7eec5c0d7055ec88891a69545eedbfbd3c5f1b1c1fe09c14099f6b052aa215efdc5cb6cdc84aa810db41dbe8cb7d28f7c4beb75cc53915d3ac75fc9d0bf1c734a46e401e15150c147d013a938b7e07cc4f25a582b914e94783d15896530409b8acbe31ef471de8a1988ac78dfb7510729eff008084885f07df870b65e4f382ca15908e1dcda77384b5c724350de90cec22b1dcbb1cdaed88da08bb4772a82266ec154f5887f89860d0920dba705c45957ef6d93e42f6c9509c966277d368dd0eefa67c8147aa15d40a222f7953a4f34616500b310d00aa1b5b73eb237dc4f76c0c16813d321b2fc5ac97039be25b22509d1201d61f4ccc11cd4ff40fffe39f0e937b4722074d8e073a775d7283b715d46f79ce128e3f1362f35615fa72364d20b6db841193d96e58d9d8e86b516bbd1f05e45b39823a93f6e9f29d9e01acf2c12c072d1c64e0afbbabf6903ef542e"
}
5 changes: 5 additions & 0 deletions mithril-common/test-data/kes2.skey
@@ -0,0 +1,5 @@
{
"type": "KesSigningKey_ed25519_kes_2^6",
"description": "KES Signing Key",
"cborHex": "590260d12460c331c7b978887899e2ccb119df7c4fa1e6f396778518f64a58f3d2232bf6481fba48fef9dc796f604b622cf0b41230c1662c221b448142bfddf8170865f1deec4232322acffb7d9001f21a4985c4acb4ca6af8906aefd9a7de6bc360acb59812a12ebd5b36a5603b497061f983921cdce59c836ccd2172f40dd62902809316c9a10cf8c44d5a22606fbdea4e210ec1540c6f5c9c1269b2af47d76aae7b009936bf4b62d0716bedf39e589b82381013c5dd68bae7496c4c726b4ae3992c188f1055ab61ef4ce9858958040147d02cec38b058919f0fcebbb9e48c25561634b58dc2d168994e2e22926f4d9d073d0c333db92d19a0c08617e03091b66f7574275db8f2fed75c21a539afedb85b1f163589eb8950ceeb6fb06f022fe544329df46fee5eb495e514846e341f0dafb8cf0d216c0ef3f18ceba6cad155694b74ae39d05a0a4729e595c1bfefa110199ec90a62e79a69c7dca595088e1a9fa1dd4f12be8e6f9e69178478d857d18f1abfc6bf567f5fcfd19bdfcb41c9a65879940a336d41a22ca66c84ccee0afd88aa237e48cb4f6115847eff96c095a7a6672e7b712d9acb8eb59dd9a1ce0ca1bc720ee1613b6e159d8b903694621f095319ba2292760ea0b975f17b3a48fb251b722ef190aa23385d05de93b3a21ef563f64e6e66e6e199267141e417e5b8a74a80f8ae6e69a4d9e778e9b7ca79f04d992b3851dbf703cd69829c837339d831b60273610d002454060bc9e1637358cd1a593166fe328dad39b8fa412b81841429ae022e26c452dce5bcd6500d48bd22af4ff94264978c1874946ce4ad53afcf9bde71973ef744823179dd98e24cd40d9498c1"
}
5 changes: 5 additions & 0 deletions mithril-common/test-data/node1.cert
@@ -0,0 +1,5 @@
{
"type": "NodeOperationalCertificate",
"description": "",
"cborHex": "82845820f89d3fa14cabafa151638743b297379d3c3767902e36ae53b02b3a64bddda19d00005840e472042f7e78e3cfc4c2ac99a658a626be0e9d69e7072dc300cb28ce8178c329beb1d2cf4c7a7ce30d6c528ffad9e8d685fd9d58379758924a010ef317290b0e58207acec462970b819f5f7951e5c84eb87c8e7c4f1aceac01e1c1d97f2e25eb6005"
}
5 changes: 5 additions & 0 deletions mithril-common/test-data/node2.cert
@@ -0,0 +1,5 @@
{
"type": "NodeOperationalCertificate",
"description": "",
"cborHex": "82845820485981d05d157875fb5a69bbea8f6fc0c09c3da1754fb42a313d6f7a485ae2070000584024d23fed6746db342232e0ddab087879ade2bd936842af00b9c02f563d752cde583df1763283973ce527d118e79ae184c83a3a60a35898f23e9a441a2948240c5820ec91c9db4c0ffc5f39548b1eda07930b7a47510a0e1ce3cc621c6a3f9e899eda"
}

0 comments on commit 85082d4

Please sign in to comment.