Skip to content

Commit

Permalink
feat!: speicfy on-chain parameters explicitly in genesis
Browse files Browse the repository at this point in the history
Signed-off-by: Shanin Roman <[email protected]>
  • Loading branch information
Erigara committed Jul 8, 2024
1 parent 9174001 commit 6bde1a2
Show file tree
Hide file tree
Showing 7 changed files with 103 additions and 61 deletions.
Binary file modified configs/swarm/executor.wasm
Binary file not shown.
62 changes: 23 additions & 39 deletions configs/swarm/genesis.json
Original file line number Diff line number Diff line change
Expand Up @@ -137,70 +137,54 @@
]
}
}
},
}
],
"topology": [],
"parameters": [
{
"SetParameter": {
"Sumeragi": {
"BlockTimeMs": 2000
}
"Sumeragi": {
"BlockTimeMs": 2000
}
},
{
"SetParameter": {
"Sumeragi": {
"CommitTimeMs": 4000
}
"Sumeragi": {
"CommitTimeMs": 4000
}
},
{
"SetParameter": {
"Block": {
"MaxTransactions": 512
}
"Block": {
"MaxTransactions": 512
}
},
{
"SetParameter": {
"Transaction": {
"MaxInstructions": 4096
}
"Transaction": {
"MaxInstructions": 4096
}
},
{
"SetParameter": {
"Transaction": {
"SmartContractSize": 4194304
}
"Transaction": {
"SmartContractSize": 4194304
}
},
{
"SetParameter": {
"SmartContract": {
"Fuel": 55000000
}
"Executor": {
"Fuel": 55000000
}
},
{
"SetParameter": {
"SmartContract": {
"Memory": 55000000
}
"Executor": {
"Memory": 55000000
}
},
{
"SetParameter": {
"SmartContract": {
"Fuel": 55000000
}
"SmartContract": {
"Fuel": 55000000
}
},
{
"SetParameter": {
"SmartContract": {
"Memory": 55000000
}
"SmartContract": {
"Memory": 55000000
}
}
],
"topology": []
]
}
34 changes: 24 additions & 10 deletions data_model/src/block.rs
Original file line number Diff line number Diff line change
Expand Up @@ -369,23 +369,37 @@ mod candidate {
};
}

let Some(transaction_executor) = transactions.first() else {
let Some(transaction) = transactions.first() else {
return Err("Genesis block must contain at least one transaction");
};
let Executable::Instructions(instructions_executor) =
transaction_executor.value.instructions()
else {
let Executable::Instructions(instructions) = transaction.value.instructions() else {
return Err("Genesis transaction must contain instructions");
};
let [InstructionBox::Upgrade(_)] = instructions_executor.as_slice() else {
return Err(
"First transaction must contain single `Upgrade` instruction to set executor",
);

if instructions
.as_slice()
.iter()
.all(|isi| matches!(isi, InstructionBox::SetParameter(_)))
{
let Some(transaction) = transactions.get(1) else {
return Err("Genesis block must contain at least two transactions if first transaction is set parameters");
};
let Executable::Instructions(instructions) = transaction.value.instructions()
else {
return Err("Genesis transaction must contain instructions");
};
if !matches!(instructions.as_slice(), [InstructionBox::Upgrade(_)]) {
return Err("Second transaction must be executor upgrade if first one is set parameters");
}
} else if matches!(instructions.as_slice(), [InstructionBox::Upgrade(_)]) {
// Nothing to do, case when there is no set parameter instructions
} else {
return Err("First transaction nor executor upgrade nor set parameters");
};

if transactions.len() > 2 {
if transactions.len() > 3 {
return Err(
"Genesis block must have one or two transactions (first with executor upgrade)",
"Genesis block must have 1 to 3 transactions (parameters, executor upgrade, other isi)",
);
}

Expand Down
2 changes: 1 addition & 1 deletion data_model/src/parameter.rs
Original file line number Diff line number Diff line change
Expand Up @@ -377,7 +377,7 @@ impl Parameters {
.map(Parameter::Sumeragi)
.chain(self.block.parameters().map(Parameter::Block))
.chain(self.transaction.parameters().map(Parameter::Transaction))
.chain(self.executor.parameters().map(Parameter::SmartContract))
.chain(self.executor.parameters().map(Parameter::Executor))
.chain(
self.smart_contract
.parameters()
Expand Down
7 changes: 7 additions & 0 deletions docs/source/references/schema.json
Original file line number Diff line number Diff line change
Expand Up @@ -3182,6 +3182,10 @@
{
"name": "topology",
"type": "Vec<PeerId>"
},
{
"name": "parameters",
"type": "Vec<Parameter>"
}
]
},
Expand Down Expand Up @@ -4558,6 +4562,9 @@
"Vec<InstructionBox>": {
"Vec": "InstructionBox"
},
"Vec<Parameter>": {
"Vec": "Parameter"
},
"Vec<PeerId>": {
"Vec": "PeerId"
},
Expand Down
49 changes: 43 additions & 6 deletions genesis/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ use std::{

use eyre::{eyre, Result, WrapErr};
use iroha_crypto::{KeyPair, PublicKey};
use iroha_data_model::{block::SignedBlock, isi::Instruction, prelude::*};
use iroha_data_model::{block::SignedBlock, isi::Instruction, parameter::Parameter, prelude::*};
use iroha_schema::IntoSchema;
use once_cell::sync::Lazy;
use parity_scale_codec::{Decode, Encode};
Expand Down Expand Up @@ -40,6 +40,9 @@ pub struct RawGenesisTransaction {
instructions: Vec<InstructionBox>,
/// Initial topology
topology: Vec<PeerId>,
/// Parameters
#[serde(default)]
parameters: Vec<Parameter>,
}

/// Path to [`Executor`] file
Expand Down Expand Up @@ -105,6 +108,7 @@ impl RawGenesisTransaction {
self.chain,
genesis_key_pair,
self.topology,
self.parameters,
);
Ok(genesis)
}
Expand All @@ -116,27 +120,48 @@ fn build_and_sign_genesis(
chain_id: ChainId,
genesis_key_pair: &KeyPair,
topology: Vec<PeerId>,
parameters: Vec<Parameter>,
) -> GenesisBlock {
let transactions = build_transactions(instructions, executor, chain_id, genesis_key_pair);
let transactions = build_transactions(
instructions,
executor,
parameters,
chain_id,
genesis_key_pair,
);
let block = SignedBlock::genesis(transactions, genesis_key_pair.private_key(), topology);
GenesisBlock(block)
}

fn build_transactions(
instructions: Vec<InstructionBox>,
executor: Executor,
parameters: Vec<Parameter>,
chain_id: ChainId,
genesis_key_pair: &KeyPair,
) -> Vec<SignedTransaction> {
let upgrade_isi = Upgrade::new(executor).into();
let transaction_executor =
build_transaction(vec![upgrade_isi], chain_id.clone(), genesis_key_pair);
if instructions.is_empty() {
vec![transaction_executor]
} else {
let mut transactions = Vec::new();
if !parameters.is_empty() {
let parameters = build_transaction(
parameters
.into_iter()
.map(SetParameter)
.map(InstructionBox::from)
.collect(),
chain_id.clone(),
genesis_key_pair,
);
transactions.push(parameters);
}
transactions.push(transaction_executor);
if !instructions.is_empty() {
let transaction_instructions = build_transaction(instructions, chain_id, genesis_key_pair);
vec![transaction_executor, transaction_instructions]
transactions.push(transaction_instructions);
}
transactions
}

fn build_transaction(
Expand Down Expand Up @@ -166,6 +191,7 @@ fn get_executor(file: &Path) -> Result<Executor> {
#[derive(Default)]
pub struct GenesisBuilder {
instructions: Vec<InstructionBox>,
parameters: Vec<Parameter>,
}

/// `Domain` subsection of the [`GenesisBuilder`]. Makes
Expand All @@ -174,6 +200,7 @@ pub struct GenesisBuilder {
#[must_use]
pub struct GenesisDomainBuilder {
instructions: Vec<InstructionBox>,
parameters: Vec<Parameter>,
domain_id: DomainId,
}

Expand All @@ -196,6 +223,7 @@ impl GenesisBuilder {
self.instructions.push(Register::domain(new_domain).into());
GenesisDomainBuilder {
instructions: self.instructions,
parameters: self.parameters,
domain_id,
}
}
Expand All @@ -206,6 +234,12 @@ impl GenesisBuilder {
self
}

/// Add parameter to the end of parameter list
pub fn append_parameter(mut self, parameter: Parameter) -> Self {
self.parameters.push(parameter);
self
}

/// Finish building, sign, and produce a [`GenesisBlock`].
pub fn build_and_sign(
self,
Expand All @@ -220,6 +254,7 @@ impl GenesisBuilder {
chain_id,
genesis_key_pair,
topology,
self.parameters,
)
}

Expand All @@ -233,6 +268,7 @@ impl GenesisBuilder {
RawGenesisTransaction {
instructions: self.instructions,
executor: ExecutorPath(executor_file),
parameters: self.parameters,
chain: chain_id,
topology,
}
Expand All @@ -245,6 +281,7 @@ impl GenesisDomainBuilder {
pub fn finish_domain(self) -> GenesisBuilder {
GenesisBuilder {
instructions: self.instructions,
parameters: self.parameters,
}
}

Expand Down
10 changes: 5 additions & 5 deletions tools/kagami/src/genesis/generate.rs
Original file line number Diff line number Diff line change
Expand Up @@ -139,10 +139,11 @@ pub fn generate_default(
.into();

let parameters = Parameters::default();
let set_parameters = parameters
.parameters()
.map(SetParameter)
.map(InstructionBox::from);
let parameters = parameters.parameters();

for parameter in parameters {
builder = builder.append_parameter(parameter);
}

for isi in [
mint.into(),
Expand All @@ -153,7 +154,6 @@ pub fn generate_default(
]
.into_iter()
.chain(std::iter::once(register_user_metadata_access))
.chain(set_parameters)
{
builder = builder.append_instruction(isi);
}
Expand Down

0 comments on commit 6bde1a2

Please sign in to comment.