Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
19 commits
Select commit Hold shift + click to select a range
4e82e00
feature(aggregator): init new import/export commands for protocol con…
turmelclem Jul 15, 2026
ec93e25
feature(aggregator, protocol-config, common): implementing CBOR conve…
turmelclem Jul 17, 2026
730b7c4
feature(protocol-config, aggregator): introduce a Signed payload stru…
turmelclem Jul 21, 2026
7e4440d
feature(protocol-config): implement a dummy protocol configuration ad…
turmelclem Jul 21, 2026
03af381
feature(protocol-config): init protocol configuration builder, and a …
turmelclem Jul 21, 2026
ea9a8fb
feature(aggregator): implement dependency injection for ProtocolConfi…
turmelclem Jul 22, 2026
ab0a1c7
feature(protocol-config): implement a ConfigurationComputerFromMarker…
turmelclem Jul 23, 2026
0654986
feature(aggregator, common): implementing verification between user i…
turmelclem Jul 24, 2026
57fb6e5
feature(protocol-config, aggregator): use ciborium encoding/decoding for
turmelclem Jul 27, 2026
18165d7
feature(common, aggregator): check protocol parameters and configurat…
turmelclem Jul 27, 2026
2845a30
feature(aggregator): wiring on chain verification and datum size veri…
turmelclem Jul 27, 2026
65bc61b
feature(aggregator, protocol-config): cleanning builder adapter mecan…
turmelclem Jul 28, 2026
b343558
feature(protocol-config, aggregator): simplify PrototolConfigurationR…
turmelclem Jul 29, 2026
c13a4a7
refactor: move ciborium to workspace dependencies
turmelclem Jul 30, 2026
7182d4a
feature(aggregator): implement export protocol configurations command
turmelclem Jul 31, 2026
7141c8e
feature(aggregagor): add a default option for the export markers command
turmelclem Aug 3, 2026
4ca0494
refactor: rename ConfigurationComputerFromMarkers to ConfigurationRes…
turmelclem Aug 4, 2026
a4b4cb9
refactor(protocol-config): remove unused Deserialize, Serialize from …
turmelclem Aug 4, 2026
a134e72
refactor(aggregator) move HumanReadableProtocolConfiguration into tools
turmelclem Aug 5, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,7 @@ anyhow = "1.0.103"
async-recursion = "1.1.1"
async-trait = "0.1.89"
chrono = { version = "0.4.45", features = ["serde"] }
ciborium = "0.2.2"
clap = { version = "4.6.1", features = ["derive", "env"] }
config = "0.15.25"
digest = { version = "0.10.7", features = ["alloc"] }
Expand Down
8 changes: 7 additions & 1 deletion internal/mithril-protocol-config/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,19 @@ include = ["**/*.rs", "Cargo.toml", "README.md", ".gitignore"]
[dependencies]
anyhow = { workspace = true }
async-trait = { workspace = true }
ciborium = { workspace = true }
fixed = "1.31.0"
hex = { workspace = true }
mithril-aggregator-client = { path = "../mithril-aggregator-client" }
mithril-cardano-node-chain = { path = "../cardano-node/mithril-cardano-node-chain" }
mithril-common = { path = "../../mithril-common" }
serde = { workspace = true }
serde_json = { workspace = true }
slog = { workspace = true }
thiserror = { workspace = true }
tokio = { workspace = true }

[dev-dependencies]
httpmock = "0.8.3"
serde_json = { workspace = true }
slog-async = { workspace = true }
slog-term = { workspace = true }
223 changes: 223 additions & 0 deletions internal/mithril-protocol-config/src/cardano_chain/message.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,223 @@
//! Messages representing Protocol Configurations converted into CBOR HEX format, for Cardano chain datum

use anyhow::Context;
use fixed::types::U8F24;
use hex::FromHex;
use serde::{Deserialize, Serialize};
use std::collections::BTreeSet;
use thiserror::Error;

use mithril_common::{
StdError,
entities::{
BlockNumber, BlockNumberOffset, CardanoBlocksTransactionsSigningConfig,
CardanoTransactionsSigningConfig, Epoch, ProtocolParameters,
},
messages::SignedEntityTypeDiscriminantsMessage,
};

/// The CBOR HEX representation of a [ProtocolConfigurationForEpochMessage]
pub type CborHexProtocolConfigurationForEpochMessage = String;

/// Value object that represents a tag of Protocol Configuration.
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct ProtocolConfigurationMarker {
/// Epoch
pub epoch: Epoch,

/// Protocol parameters
pub configuration: CborHexProtocolConfigurationForEpochMessage,
}

impl ProtocolConfigurationMarker {
/// instantiate a new [ProtocolConfigurationMarker].
pub fn new(
epoch: Epoch,
protocol_configuration: CborHexProtocolConfigurationForEpochMessage,
) -> Self {
ProtocolConfigurationMarker {
epoch,
configuration: protocol_configuration,
}
}
}

/// Parse error
#[derive(Error, Debug)]
#[error("Codec parse error")]
pub struct ProtocolConfigurationForEpochMessageParseError(#[source] StdError);

/// Protocol cryptographic parameters Message
///
/// used for the CBOR HEX representation of [ProtocolConfigurationForEpochMessage]
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct ProtocolParametersMessage {
/// Quorum parameter
pub k: u64,

/// Security parameter (number of lotteries)
pub m: u64,

/// f in phi(w) = 1 - (1 - f)^w, where w is the stake of a participant
pub phi_f: f64,
}

impl ProtocolParametersMessage {
/// phi_f_fixed is a fixed decimal representation of phi_f
/// used for PartialEq and Hash implementation
pub fn phi_f_fixed(&self) -> U8F24 {
U8F24::from_num(self.phi_f)
}
}

impl PartialEq<ProtocolParametersMessage> for ProtocolParametersMessage {
fn eq(&self, other: &ProtocolParametersMessage) -> bool {
self.k == other.k && self.m == other.m && self.phi_f_fixed() == other.phi_f_fixed()
}
}

impl From<ProtocolParameters> for ProtocolParametersMessage {
fn from(params: ProtocolParameters) -> Self {
ProtocolParametersMessage {
k: params.k,
m: params.m,
phi_f: params.phi_f,
}
}
}

/// Configuration for the signing of Cardano transactions
///
/// used for the CBOR HEX representation of [ProtocolConfigurationForEpochMessage]
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
pub struct CardanoTransactionsSigningConfigMessage {
/// Number of blocks to discard from the tip of the chain when importing transactions.
pub security_parameter: BlockNumberOffset,

/// The number of blocks between signature of the transactions.
pub step: BlockNumber,
}

impl From<CardanoTransactionsSigningConfig> for CardanoTransactionsSigningConfigMessage {
fn from(config: CardanoTransactionsSigningConfig) -> Self {
CardanoTransactionsSigningConfigMessage {
security_parameter: config.security_parameter,
step: config.step,
}
}
}

/// Configuration for the signing of Cardano blocks and transactions
///
/// used for the CBOR HEX representation of [ProtocolConfigurationForEpochMessage]
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
pub struct CardanoBlocksTransactionsSigningConfigMessage {
/// Number of blocks to discard from the tip of the chain when importing blocks and transactions.
pub security_parameter: BlockNumberOffset,

/// The number of blocks between signature of the blocks and transactions.
pub step: BlockNumber,
}

impl From<CardanoBlocksTransactionsSigningConfig>
for CardanoBlocksTransactionsSigningConfigMessage
{
fn from(config: CardanoBlocksTransactionsSigningConfig) -> Self {
CardanoBlocksTransactionsSigningConfigMessage {
security_parameter: config.security_parameter,
step: config.step,
}
}
}

//A epoch configuration used for the CBOR HEX representation in the [ProtocolConfigurationMarker]
#[derive(PartialEq, Clone, Debug, Serialize, Deserialize)]
/// A network configuration available for an epoch
pub struct ProtocolConfigurationForEpochMessage {
/// Cryptographic protocol parameters (`k`, `m` and `phi_f`)
pub protocol_parameters: ProtocolParametersMessage,

/// List of available types of certifications
pub enabled_signed_entity_types: BTreeSet<SignedEntityTypeDiscriminantsMessage>,

/// Signing configuration for Cardano transactions
pub cardano_transactions: Option<CardanoTransactionsSigningConfigMessage>,

/// Signing configuration for Cardano blocks and transactions
pub cardano_blocks_transactions: Option<CardanoBlocksTransactionsSigningConfigMessage>,
}

impl ProtocolConfigurationForEpochMessage {
/// Serialize the structure to a CBOR bytes representation.
fn to_cbor_bytes(&self) -> Result<Vec<u8>, ProtocolConfigurationForEpochMessageParseError> {
let mut cursor = std::io::Cursor::new(Vec::new());
ciborium::ser::into_writer(&self, &mut cursor)
.with_context(|| "ProtocolConfigurationForEpoch can not serialize data to cbor")
.map_err(ProtocolConfigurationForEpochMessageParseError)?;

Ok(cursor.into_inner())
}

/// Serialize the structure to a CBOR HEX representation.
pub fn to_cbor_hex(&self) -> Result<String, ProtocolConfigurationForEpochMessageParseError> {
Ok(hex::encode(self.to_cbor_bytes()?))
}

/// Deserialize a ProtocolConfigurationForEpochMessage from CBOR bytes representation.
fn from_cbor_bytes(
bytes: &[u8],
) -> Result<Self, ProtocolConfigurationForEpochMessageParseError> {
let mut cursor = std::io::Cursor::new(&bytes);
let a: Self = ciborium::de::from_reader(&mut cursor)
.with_context(|| "ProtocolConfigurationForEpoch can not unserialize cbor data")
.map_err(ProtocolConfigurationForEpochMessageParseError)?;

Ok(a)
}

/// Deserialize a ProtocolConfigurationForEpochMessage from CBOR HEX representation.
pub fn from_cbor_hex(
hex: &str,
) -> Result<Self, ProtocolConfigurationForEpochMessageParseError> {
let hex_vector = Vec::from_hex(hex)
.with_context(|| "ProtocolConfigurationForEpochMessage can not unserialize HEX data")
.map_err(ProtocolConfigurationForEpochMessageParseError)?;

Self::from_cbor_bytes(&hex_vector)
.with_context(|| "ProtocolConfigurationForEpochMessage can not unserialize CBOR data")
.map_err(ProtocolConfigurationForEpochMessageParseError)
}
}

#[cfg(test)]
mod tests {
Comment thread
turmelclem marked this conversation as resolved.
use mithril_common::test::double::Dummy;

use super::*;

#[test]
fn golden_master_cbor_hex_conversion() {
const EXPECTED_JSON_HEX: &str = "a47370726f746f636f6c5f706172616d6574657273a3616b01616d02657068695f66fb3fd3333333333333781b656e61626c65645f7369676e65645f656e746974795f74797065738578184d69746872696c5374616b65446973747269627574696f6e781843617264616e6f5374616b65446973747269627574696f6e6f43617264616e6f44617461626173657343617264616e6f5472616e73616374696f6e73781943617264616e6f426c6f636b735472616e73616374696f6e737463617264616e6f5f7472616e73616374696f6e73a27273656375726974795f706172616d657465720a647374657005781b63617264616e6f5f626c6f636b735f7472616e73616374696f6e73a27273656375726974795f706172616d657465720b647374657007";

let mithril_network_configuration_for_epoch = ProtocolConfigurationForEpochMessage::dummy();
let mithril_network_configuration_for_epoch_from_cbor_hex =
ProtocolConfigurationForEpochMessage::from_cbor_hex(EXPECTED_JSON_HEX).unwrap();

assert_eq!(
mithril_network_configuration_for_epoch,
mithril_network_configuration_for_epoch_from_cbor_hex
);
}

#[test]
fn to_cbor_hex_from_cbor_hex_conversion() {
let mithril_network_configuration_for_epoch = ProtocolConfigurationForEpochMessage::dummy();
let cbor_hex = mithril_network_configuration_for_epoch.to_cbor_hex().unwrap();
let mithril_network_configuration_for_epoch_from_cbor_hex =
ProtocolConfigurationForEpochMessage::from_cbor_hex(&cbor_hex).unwrap();
assert_eq!(
mithril_network_configuration_for_epoch,
mithril_network_configuration_for_epoch_from_cbor_hex
);
}
}
10 changes: 10 additions & 0 deletions internal/mithril-protocol-config/src/cardano_chain/mod.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
//! Cardano Chain module to read protocol configuration markers
pub mod message;
Comment thread
github-advanced-security[bot] marked this conversation as resolved.
Fixed
Comment thread
github-advanced-security[bot] marked this conversation as resolved.
Fixed
pub mod payload;
Comment thread
github-advanced-security[bot] marked this conversation as resolved.
Fixed
Comment thread
github-advanced-security[bot] marked this conversation as resolved.
Fixed
pub mod protocol_configuration_reader;
Comment thread
github-advanced-security[bot] marked this conversation as resolved.
Fixed
Comment thread
github-advanced-security[bot] marked this conversation as resolved.
Fixed

pub use payload::{
ProtocolConfigurationMarkersPayload as ProtocolConfigurationMarkersPayloadCardanoChain,
SignedProtocolConfigurationMarkersPayload as SignedProtocolConfigurationMarkersPayloadCardanoChain,
};
Loading
Loading