1use alloy::primitives::{keccak256, Address, Bytes, U256};
8use alloy::sol_types::SolCall;
9
10use crate::contracts::ISafeSetup;
11
12pub fn encode_setup_call(owners: &[Address], threshold: u64, fallback_handler: Address) -> Bytes {
22 let setup_call = ISafeSetup::setupCall {
23 _owners: owners.to_vec(),
24 _threshold: U256::from(threshold),
25 to: Address::ZERO,
26 data: Bytes::new(),
27 fallbackHandler: fallback_handler,
28 paymentToken: Address::ZERO,
29 payment: U256::ZERO,
30 paymentReceiver: Address::ZERO,
31 };
32
33 Bytes::from(setup_call.abi_encode())
34}
35
36pub fn compute_create2_address(
55 factory: Address,
56 singleton: Address,
57 initializer: &Bytes,
58 salt_nonce: U256,
59 creation_code: &Bytes,
60) -> Address {
61 let initializer_hash = keccak256(initializer);
63
64 let mut salt_input = [0u8; 64];
65 salt_input[..32].copy_from_slice(initializer_hash.as_slice());
66 salt_input[32..64].copy_from_slice(&salt_nonce.to_be_bytes::<32>());
67
68 let salt = keccak256(salt_input);
69
70 let mut init_code = creation_code.to_vec();
72 let mut singleton_padded = [0u8; 32];
74 singleton_padded[12..].copy_from_slice(singleton.as_slice());
75 init_code.extend_from_slice(&singleton_padded);
76
77 let init_code_hash = keccak256(&init_code);
78
79 let mut create2_input = Vec::with_capacity(1 + 20 + 32 + 32);
81 create2_input.push(0xff);
82 create2_input.extend_from_slice(factory.as_slice());
83 create2_input.extend_from_slice(salt.as_slice());
84 create2_input.extend_from_slice(init_code_hash.as_slice());
85
86 let hash = keccak256(&create2_input);
87
88 Address::from_slice(&hash[12..])
89}
90
91#[cfg(test)]
92mod tests {
93 use super::*;
94 use alloy::primitives::address;
95
96 #[test]
97 fn test_encode_setup_call() {
98 let owners = vec![address!("1234567890123456789012345678901234567890")];
99 let threshold = 1;
100 let fallback_handler = address!("fd0732Dc9E303f09fCEf3a7388Ad10A83459Ec99");
101
102 let data = encode_setup_call(&owners, threshold, fallback_handler);
103
104 assert!(!data.is_empty());
106 assert_eq!(&data[0..4], &[0xb6, 0x3e, 0x80, 0x0d]);
108 }
109
110 #[test]
111 fn test_encode_setup_call_multiple_owners() {
112 let owners = vec![
113 address!("1111111111111111111111111111111111111111"),
114 address!("2222222222222222222222222222222222222222"),
115 address!("3333333333333333333333333333333333333333"),
116 ];
117 let threshold = 2;
118 let fallback_handler = address!("fd0732Dc9E303f09fCEf3a7388Ad10A83459Ec99");
119
120 let data = encode_setup_call(&owners, threshold, fallback_handler);
121
122 assert!(!data.is_empty());
124 assert_eq!(&data[0..4], &[0xb6, 0x3e, 0x80, 0x0d]);
126 }
127
128 #[test]
129 fn test_compute_create2_address_deterministic() {
130 let factory = address!("4e1DCf7AD4e460CfD30791CCC4F9c8a4f820ec67");
132 let singleton = address!("41675C099F32341bf84BFc5382aF534df5C7461a");
133 let initializer = Bytes::from(vec![0x01, 0x02, 0x03]);
134 let salt_nonce = U256::from(42);
135 let creation_code = Bytes::from(vec![0x60, 0x80, 0x60, 0x40]);
136
137 let addr1 = compute_create2_address(
138 factory,
139 singleton,
140 &initializer,
141 salt_nonce,
142 &creation_code,
143 );
144
145 let addr2 = compute_create2_address(
146 factory,
147 singleton,
148 &initializer,
149 salt_nonce,
150 &creation_code,
151 );
152
153 assert_eq!(addr1, addr2, "CREATE2 address should be deterministic");
154 }
155
156 #[test]
157 fn test_compute_create2_address_different_nonce() {
158 let factory = address!("4e1DCf7AD4e460CfD30791CCC4F9c8a4f820ec67");
160 let singleton = address!("41675C099F32341bf84BFc5382aF534df5C7461a");
161 let initializer = Bytes::from(vec![0x01, 0x02, 0x03]);
162 let creation_code = Bytes::from(vec![0x60, 0x80, 0x60, 0x40]);
163
164 let addr1 = compute_create2_address(
165 factory,
166 singleton,
167 &initializer,
168 U256::from(1),
169 &creation_code,
170 );
171
172 let addr2 = compute_create2_address(
173 factory,
174 singleton,
175 &initializer,
176 U256::from(2),
177 &creation_code,
178 );
179
180 assert_ne!(addr1, addr2, "Different salt nonces should produce different addresses");
181 }
182}