Skip to content

Commit 54d23f7

Browse files
authored
Merge pull request #345 from synapseweb3/chore/contract-deployment
chore: add contract deployment script and configs
2 parents bc6a7f7 + 8d8008b commit 54d23f7

35 files changed

+347
-301
lines changed

.github/workflows/ibc-test.yaml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ concurrency:
2525
jobs:
2626
ibc-test:
2727
runs-on: ubuntu-20.04
28-
timeout-minutes: 60
28+
timeout-minutes: 75
2929
env:
3030
SRC_DIR: ${{ github.workspace }}/ibc-test-src
3131
AXON_COMMIT: a088cf83d29b8658a7d2ae96a74a53bffb743f03

.gitignore

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,9 @@ target/
1717
# Ignore chain's data
1818
data
1919

20+
# Ignore debug persistence file
21+
debug
22+
2023
# Ignore Python artifacts
2124
.mypy_cache/
2225
__pycache__/
@@ -31,4 +34,4 @@ mc.log
3134
# Ignore native MMR storage
3235
ckb_mmr_storage*/
3336

34-
**/ckb-dev*
37+
**/ckb-dev*

Cargo.lock

Lines changed: 2 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

crates/relayer-cli/src/commands/keys/add.rs

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -276,6 +276,13 @@ pub fn restore_key(
276276
ChainType::Ckb => "ckb",
277277
ChainType::Ckb4Ibc => "ckb4ibc",
278278
};
279+
let address_type = match config.r#type() {
280+
ChainType::CosmosSdk => &config.cosmos().address_type,
281+
ChainType::Eth => todo!(),
282+
ChainType::Axon => &AddressType::Axon,
283+
ChainType::Ckb | ChainType::Ckb4Ibc => &AddressType::Ckb,
284+
};
285+
279286
let key_pair = {
280287
let mut keyring = KeyRing::new_secp256k1(Store::Test, account_prefix, config.id())?;
281288

@@ -284,7 +291,7 @@ pub fn restore_key(
284291
let key_pair = Secp256k1KeyPair::from_mnemonic(
285292
&mnemonic_content,
286293
hdpath,
287-
&config.cosmos().address_type,
294+
address_type,
288295
keyring.account_prefix(),
289296
)?;
290297

crates/relayer-types/Cargo.toml

Lines changed: 42 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,14 @@
11
[package]
2-
name = "ibc-relayer-types"
3-
version = "0.23.0"
4-
edition = "2021"
5-
license = "Apache-2.0"
6-
readme = "README.md"
7-
keywords = ["blockchain", "consensus", "cosmos", "ibc", "tendermint"]
8-
repository = "https://github.com/informalsystems/hermes"
9-
authors = ["Informal Systems <hello@informal.systems>"]
2+
name = "ibc-relayer-types"
3+
version = "0.23.0"
4+
edition = "2021"
5+
license = "Apache-2.0"
6+
readme = "README.md"
7+
keywords = ["blockchain", "consensus", "cosmos", "ibc", "tendermint"]
8+
repository = "https://github.com/informalsystems/hermes"
9+
authors = ["Informal Systems <hello@informal.systems>"]
1010
rust-version = "1.65"
11-
description = """
11+
description = """
1212
Implementation of the Inter-Blockchain Communication Protocol (IBC).
1313
This crate comprises the main data structures and on-chain logic.
1414
"""
@@ -28,31 +28,46 @@ mocks = ["tendermint-testgen", "clock", "std"]
2828
[dependencies]
2929
# Proto definitions for all IBC-related interfaces, e.g., connections or channels.
3030
ibc-proto = { version = "0.28.0", default-features = false }
31-
ics23 = { version = "=0.9.0", default-features = false, features = ["host-functions"] }
31+
ics23 = { version = "=0.9.0", default-features = false, features = [
32+
"host-functions",
33+
] }
3234
time = { version = ">=0.3.0, <0.3.21", default-features = false }
3335
serde_derive = { version = "1.0.104", default-features = false }
3436
serde = { version = "1.0", default-features = false }
3537
serde_json = { version = "1", default-features = false }
36-
erased-serde = { version = "0.3", default-features = false, features = ["alloc"] }
38+
erased-serde = { version = "0.3", default-features = false, features = [
39+
"alloc",
40+
] }
3741
prost = { version = "0.11", default-features = false }
3842
bytes = { version = "1.4.0", default-features = false }
3943
safe-regex = { version = "0.2.5", default-features = false }
4044
subtle-encoding = { version = "0.5", default-features = false }
4145
flex-error = { version = "0.4.4", default-features = false }
42-
derive_more = { version = "0.99.17", default-features = false, features = ["from", "into", "display"] }
46+
derive_more = { version = "0.99.17", default-features = false, features = [
47+
"from",
48+
"into",
49+
"display",
50+
] }
4351
uint = { version = "0.9", default-features = false }
44-
itertools = { version = "0.10.3", default-features = false, features = ["use_alloc"] }
45-
primitive-types = { version = "0.12.1", default-features = false, features = ["serde_no_std"] }
52+
itertools = { version = "0.10.3", default-features = false, features = [
53+
"use_alloc",
54+
] }
55+
primitive-types = { version = "0.12.1", default-features = false, features = [
56+
"serde_no_std",
57+
] }
4658
dyn-clone = "1.0.8"
4759
num-rational = "0.4.1"
48-
eth2_ssz_types = { git = "https://github.com/synapseweb3/lighthouse", rev = "2c246d6" }
49-
bls = { git = "https://github.com/synapseweb3/lighthouse", rev = "2c246d6" }
50-
tree_hash = { git = "https://github.com/synapseweb3/lighthouse", rev = "2c246d6" }
60+
eth2_ssz_types = { git = "https://github.com/synapseweb3/lighthouse", rev = "2c246d6" }
61+
bls = { git = "https://github.com/synapseweb3/lighthouse", rev = "2c246d6" }
62+
tree_hash = { git = "https://github.com/synapseweb3/lighthouse", rev = "2c246d6" }
5163
tree_hash_derive = { git = "https://github.com/synapseweb3/lighthouse", rev = "2c246d6" }
5264
thiserror = "1.0"
5365
ethereum-types = "0.14.1"
5466
hex = "0.4"
55-
axon-tools = { git = "https://github.com/axonweb3/axon-tools.git", branch = "main", version = "0.1.1", features = ["impl-serde", "proof"] }
67+
axon-tools = { git = "https://github.com/axonweb3/axon-tools.git", rev = "2e21582", version = "0.1.1", features = [
68+
"impl-serde",
69+
"proof",
70+
] }
5671
strum = { version = "0.24.1", features = ["derive"] }
5772

5873
[dependencies.tendermint]
@@ -76,7 +91,14 @@ default-features = false
7691
[dev-dependencies]
7792
env_logger = "0.10.0"
7893
tracing = { version = "0.1.36", default-features = false }
79-
tracing-subscriber = { version = "0.3.14", features = ["fmt", "env-filter", "json"] }
94+
tracing-subscriber = { version = "0.3.14", features = [
95+
"fmt",
96+
"env-filter",
97+
"json",
98+
] }
8099
test-log = { version = "0.2.10", features = ["trace"] }
81-
tendermint-rpc = { version = "0.30.0", features = ["http-client", "websocket-client"] }
100+
tendermint-rpc = { version = "0.30.0", features = [
101+
"http-client",
102+
"websocket-client",
103+
] }
82104
tendermint-testgen = { version = "0.30.0" } # Needed for generating (synthetic) light blocks.

crates/relayer/Cargo.toml

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,10 @@ tree_hash = { git = "https://github.com/synapseweb3/lighthouse", rev = "2c246d6"
3434

3535
eth_light_client_in_ckb-verification = { version = "0.2.1", git = "https://github.com/synapseweb3/eth-light-client-in-ckb", tag = "v0.2.1" }
3636
eth_light_client_in_ckb-prover = { version = "0.2.1", git = "https://github.com/synapseweb3/eth-light-client-in-ckb", tag = "v0.2.1" }
37-
axon-tools = { git = "https://github.com/axonweb3/axon-tools.git", branch = "main", version = "0.1.1", features = ["impl-serde", "proof"] }
37+
axon-tools = { git = "https://github.com/axonweb3/axon-tools.git", rev = "2e21582", version = "0.1.1", features = [
38+
"impl-serde",
39+
"proof",
40+
] }
3841

3942
subtle-encoding = "0.5"
4043
humantime-serde = "1.1.1"

crates/relayer/src/chain/axon.rs

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@ use axon_tools::types::{AxonBlock, Proof as AxonProof, ValidatorExtend};
44
use eth2_types::Hash256;
55
use k256::ecdsa::SigningKey;
66
use rlp::Encodable;
7-
use tracing::warn;
7+
use tracing::{debug, warn};
88

99
use crate::{
1010
account::Balance,
@@ -1266,11 +1266,17 @@ impl AxonChain {
12661266
height,
12671267
)
12681268
.unwrap();
1269+
let debug_content = generate_debug_content(&block, &state_root, &block_proof, &validators);
12691270

12701271
// check the validation of Axon block
12711272
axon_tools::verify_proof(block, state_root, &mut validators, block_proof).map_err(
12721273
|err| {
1273-
let err_msg = format!("unverified axon block, err: {:?}", err);
1274+
std::fs::write(
1275+
format!("./debug/axon_block_{block_number}.log"),
1276+
debug_content,
1277+
)
1278+
.unwrap();
1279+
let err_msg = format!("unverified axon block #{block_number}, err: {:?}", err);
12741280
Error::rpc_response(err_msg)
12751281
},
12761282
)?;
@@ -1442,6 +1448,11 @@ impl AxonChain {
14421448
.into_iter()
14431449
.map(Into::into)
14441450
.map(|log| OwnableIBCHandlerEvents::decode_log(&log));
1451+
debug!(
1452+
"Axon received '{}' with events of {}",
1453+
message.type_url.as_str(),
1454+
events.len()
1455+
);
14451456
match message.type_url.as_str() {
14461457
create_client::TYPE_URL => {
14471458
events.find(|event| matches!(event, Ok(CreateClientFilter(_))))

crates/relayer/src/chain/axon/utils.rs

Lines changed: 15 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
use std::str::FromStr;
22

3-
use axon_tools::types::{AxonBlock, Proof as AxonProof};
3+
use axon_tools::types::{AxonBlock, Proof as AxonProof, ValidatorExtend};
44
use ckb_ics_axon::proof::{
55
Log as CkbLog, ObjectProof, TransactionReceipt as CkbTransactionReceipt,
66
};
@@ -497,3 +497,17 @@ pub fn ibc_event_from_ibc_handler_event(
497497
tx_hash,
498498
}))
499499
}
500+
501+
pub fn generate_debug_content(
502+
block: &AxonBlock,
503+
state_root: &H256,
504+
block_proof: &AxonProof,
505+
validators: &Vec<ValidatorExtend>,
506+
) -> String {
507+
let block = serde_json::to_string_pretty(block).unwrap();
508+
let validators = serde_json::to_string_pretty(validators).unwrap();
509+
let state_root = hex::encode(state_root);
510+
let block_proof = serde_json::to_string_pretty(block_proof).unwrap();
511+
let content = format!("[block]\n{block}\n[validators]\n{validators}\n[state_root]\n{state_root}\n[block_proof]\n{block_proof}");
512+
content
513+
}

crates/relayer/src/chain/ckb4ibc.rs

Lines changed: 29 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ use ckb_ics_axon::handler::{IbcChannel, IbcConnections, IbcPacket, PacketStatus}
2525
use ckb_ics_axon::message::Envelope;
2626
use ckb_ics_axon::object::Ordering;
2727
use ckb_ics_axon::{ChannelArgs, PacketArgs};
28-
use ckb_jsonrpc_types::{JsonBytes, Status, TransactionView};
28+
use ckb_jsonrpc_types::{Status, TransactionView};
2929
use ckb_sdk::constants::TYPE_ID_CODE_HASH;
3030
use ckb_sdk::traits::SecpCkbRawKeySigner;
3131
use ckb_sdk::unlock::{ScriptSigner, SecpSighashScriptSigner};
@@ -369,13 +369,17 @@ impl Ckb4IbcChain {
369369
.build();
370370
let capacity: u64 = cell.output.capacity.into();
371371
let client_id = hex::encode(cell.output.lock.args.into_bytes());
372-
resps.push((tx, cell_input, capacity, client_id));
372+
if let Ok(client_type) = self.config.lc_client_type(&client_id) {
373+
resps.push((tx, cell_input, capacity, client_type));
374+
} else {
375+
warn!("skip local missing client_id found on-chain: {client_id}");
376+
}
373377
}
374378
Ok(resps)
375379
});
376380
let mut cache = self.connection_cache.borrow_mut();
377381
let prefix = self.query_commitment_prefix()?;
378-
for (transaction, cell_input, capacity, client_id) in self.rt.block_on(future)? {
382+
for (transaction, cell_input, capacity, client_type) in self.rt.block_on(future)? {
379383
let tx = transaction
380384
.expect("empty transaction response")
381385
.transaction
@@ -387,7 +391,6 @@ impl Ckb4IbcChain {
387391
}
388392
};
389393
let (connections, ibc_connection) = extract_connections_from_tx(tx, &prefix)?;
390-
let client_type = self.config.lc_client_type(&client_id)?;
391394
cache.insert(
392395
client_type,
393396
(ibc_connection, cell_input, capacity, connections),
@@ -506,7 +509,7 @@ impl ChainEndpoint for Ckb4IbcChain {
506509
) in &config.onchain_light_clients
507510
{
508511
let client_cell = rt.block_on(rpc_client.search_cell_by_typescript(
509-
&TYPE_ID_CODE_HASH.pack(),
512+
&config.client_code_hash.pack(),
510513
&client_cell_type_args.as_bytes().to_owned(),
511514
))?;
512515
let Some(cell) = client_cell else {
@@ -710,6 +713,13 @@ impl ChainEndpoint for Ckb4IbcChain {
710713
match response {
711714
Ok(height) => {
712715
if let Some(event) = events.get(i).unwrap().clone() {
716+
if let IbcEvent::CreateClient(e) = &event {
717+
let client_type = e.0.client_type;
718+
info!(
719+
"the counterparty client type of Ckb4Ibc is set as {client_type}"
720+
);
721+
self.sync_counterparty_client_type(client_type);
722+
}
713723
let tx_hash: [u8; 32] = tx_hashes.get(i).unwrap().clone().into();
714724
let ibc_event_with_height = IbcEventWithHeight {
715725
event,
@@ -968,32 +978,32 @@ impl ChainEndpoint for Ckb4IbcChain {
968978

969979
fn query_connection_channels(
970980
&self,
971-
_request: QueryConnectionChannelsRequest,
981+
request: QueryConnectionChannelsRequest,
972982
) -> Result<Vec<IdentifiedChannelEnd>, Error> {
973-
self.query_channels(QueryChannelsRequest { pagination: None })
983+
let connection_channels = self
984+
.query_channels(QueryChannelsRequest { pagination: None })?
985+
.into_iter()
986+
.filter(|channel| {
987+
channel
988+
.channel_end
989+
.connection_hops
990+
.contains(&request.connection_id)
991+
})
992+
.collect();
993+
Ok(connection_channels)
974994
}
975995

976996
fn query_channels(
977997
&self,
978-
request: QueryChannelsRequest,
998+
_request: QueryChannelsRequest,
979999
) -> Result<Vec<IdentifiedChannelEnd>, Error> {
9801000
let channel_code_hash = self.get_converter()?.get_channel_code_hash();
9811001
let script = Script::new_builder()
9821002
.code_hash(channel_code_hash)
983-
.args("".pack())
9841003
.hash_type(ScriptHashType::Type.into())
9851004
.build();
9861005
let search_key = get_prefix_search_key(script);
987-
let (limit, index) = {
988-
if let Some(pagination) = request.pagination {
989-
(pagination.limit as u32, pagination.offset as u32)
990-
} else {
991-
(u32::MAX, 0)
992-
}
993-
};
994-
let json_bytes = JsonBytes::from_vec(index.to_be_bytes().to_vec());
995-
let cursor = Some(json_bytes);
996-
let cells_rpc_result = self.rpc_client.fetch_live_cells(search_key, limit, cursor);
1006+
let cells_rpc_result = self.rpc_client.fetch_live_cells(search_key, u32::MAX, None);
9971007
let txs_rpc_result = self
9981008
.rt
9991009
.block_on(cells_rpc_result)?

crates/relayer/src/chain/ckb4ibc/message/client.rs

Lines changed: 27 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
1-
use ckb_ics_axon::message::{Envelope, MsgType};
1+
use ckb_ics_axon::{
2+
handler::IbcConnections,
3+
message::{Envelope, MsgType},
4+
};
5+
use ckb_types::packed::BytesOpt;
26
use ibc_relayer_types::{
37
clients::{
48
ics07_axon::client_state::AXON_CLIENT_STATE_TYPE_URL,
@@ -13,9 +17,12 @@ use ibc_relayer_types::{
1317
Height,
1418
};
1519

16-
use super::{CkbTxInfo, MsgToTxConverter};
20+
use super::{CkbTxInfo, MsgToTxConverter, TxBuilder};
1721

18-
use crate::error::Error;
22+
use crate::{
23+
chain::ckb4ibc::utils::{get_connection_lock_script, get_encoded_object},
24+
error::Error,
25+
};
1926

2027
pub fn convert_create_client<C: MsgToTxConverter>(
2128
msg: MsgCreateClient,
@@ -42,8 +49,24 @@ pub fn convert_create_client<C: MsgToTxConverter>(
4249
)));
4350
}
4451
};
52+
// one light client only matches one unique connections cell on CKB, if not exist, create it
53+
let find_unique_connections = converter.get_ibc_connections(client_id.as_str()).is_ok();
54+
let unsigned_tx = if !find_unique_connections {
55+
tracing::info!("connections_cell for {client_type} isn't detected on CKB, create one");
56+
let empty_ibc_connections = get_encoded_object(&IbcConnections::default());
57+
let connections_lock_script =
58+
get_connection_lock_script(converter.get_config(), Some(client_id.to_string()))?;
59+
60+
let packed_tx = TxBuilder::default()
61+
.output(connections_lock_script, empty_ibc_connections.data)
62+
.witness(BytesOpt::default(), empty_ibc_connections.witness)
63+
.build();
64+
Some(packed_tx)
65+
} else {
66+
None
67+
};
4568
Ok(CkbTxInfo {
46-
unsigned_tx: None,
69+
unsigned_tx,
4770
envelope: Envelope {
4871
msg_type: MsgType::MsgClientCreate,
4972
content: vec![],

0 commit comments

Comments
 (0)