1use crate::cli::*;
22
23use clap::Parser;
24use cumulus_primitives_core::ParaId;
25use polkadot_parachain::primitives::Sibling;
26use polkadot_primitives::AccountId;
27use sp_core::hexdisplay::HexDisplay;
28use sp_runtime::traits::AccountIdConversion;
29use xcm::latest::prelude::*;
30use xcm_builder::{
31 DescribeAllTerminal, DescribeFamily, HashedDescription, ParentIsPreset,
32 SiblingParachainConvertsVia,
33};
34use xcm_executor::traits::ConvertLocation;
35
36pub type Error = String;
38
39pub fn run() -> Result<(), Error> {
41 let cli = Cli::parse();
42
43 match &cli.subcommand {
44 Some(Subcommand::RelayChainAccount) => {
45 let relay_account =
46 ParentIsPreset::<AccountId>::convert_location(&Location::parent()).unwrap();
47 println!("{}", relay_account);
48 }
49 Some(Subcommand::SovereignAccount(cmd)) => {
50 let parachain_account = if cmd.sibling {
51 let location = Location {
52 parents: 1,
53 interior: Parachain(cmd.parachain_id).into(),
54 };
55 SiblingParachainConvertsVia::<Sibling, AccountId>::convert_location(&location)
56 .unwrap()
57 } else {
58 let para_id = ParaId::from(cmd.parachain_id);
59 AccountIdConversion::<AccountId>::into_account_truncating(¶_id)
60 };
61 println!("{}", parachain_account);
62 }
63 Some(Subcommand::AssetId(cmd)) => {
64 const ASSET_PRECOMPILE_ADDRESS_PREFIX: &[u8] = &[255u8; 4];
65 let mut data = [0u8; 20];
66 data[0..4].copy_from_slice(ASSET_PRECOMPILE_ADDRESS_PREFIX);
67 data[4..20].copy_from_slice(&cmd.asset_id.to_be_bytes());
68 println!("pallet_assets: {}", cmd.asset_id);
69 println!("EVM XC20: 0x{}", HexDisplay::from(&data));
70 }
71 Some(Subcommand::RemoteAccount(cmd)) => {
72 let mut sender_multilocation = Location::parent();
73
74 if let Some(parachain_id) = cmd.parachain_id {
75 sender_multilocation
76 .append_with(Parachain(parachain_id))
77 .expect("infallible, short sequence");
78 }
79
80 match cmd.account_key {
81 AccountWrapper::SS58(id) => {
82 sender_multilocation
83 .append_with(AccountId32 {
84 id,
85 network: None,
87 })
88 .expect("infallible, short sequence");
89 }
90 AccountWrapper::H160(key) => {
91 sender_multilocation
92 .append_with(AccountKey20 {
93 key,
94 network: None,
96 })
97 .expect("infallible, short sequence");
98 }
99 }
100
101 let derived_acc =
102 HashedDescription::<AccountId, DescribeFamily<DescribeAllTerminal>>::convert_location(
103 &sender_multilocation,
104 );
105 if let Some(derived_acc) = derived_acc {
106 println!("{}", derived_acc);
107 } else {
108 println!("Failed to derive account Id.");
109 }
110 }
111 None => {}
112 }
113 Ok(())
114}