pallet_revive/vm/evm/instructions/
utility.rs1use revm::primitives::{Address, B256, U256};
19
20#[inline]
27pub fn cast_slice_to_u256(slice: &[u8], dest: &mut U256) {
28 if slice.is_empty() {
29 return;
30 }
31 assert!(slice.len() <= 32, "slice too long");
32
33 let n_words = slice.len().div_ceil(32);
34
35 unsafe {
37 let dst = dest.as_limbs_mut().as_mut_ptr();
40
41 let mut i = 0;
42
43 let words = slice.chunks_exact(32);
45 let partial_last_word = words.remainder();
46 for word in words {
47 for l in word.rchunks_exact(8) {
50 dst.add(i).write(u64::from_be_bytes(l.try_into().unwrap()));
51 i += 1;
52 }
53 }
54
55 if partial_last_word.is_empty() {
56 return;
57 }
58
59 let limbs = partial_last_word.rchunks_exact(8);
61 let partial_last_limb = limbs.remainder();
62 for l in limbs {
63 dst.add(i).write(u64::from_be_bytes(l.try_into().unwrap()));
64 i += 1;
65 }
66
67 if !partial_last_limb.is_empty() {
69 let mut tmp = [0u8; 8];
70 tmp[8 - partial_last_limb.len()..].copy_from_slice(partial_last_limb);
71 dst.add(i).write(u64::from_be_bytes(tmp));
72 i += 1;
73 }
74
75 debug_assert_eq!(i.div_ceil(4), n_words, "wrote too much");
76
77 let m = i % 4; if m != 0 {
80 dst.add(i).write_bytes(0, 4 - m);
81 }
82 }
83}
84
85pub trait IntoU256 {
87 fn into_u256(self) -> U256;
89}
90
91impl IntoU256 for Address {
92 fn into_u256(self) -> U256 {
93 self.into_word().into_u256()
94 }
95}
96
97impl IntoU256 for B256 {
98 fn into_u256(self) -> U256 {
99 U256::from_be_bytes(self.0)
100 }
101}
102
103pub trait IntoAddress {
105 fn into_address(self) -> Address;
107}
108
109impl IntoAddress for U256 {
110 fn into_address(self) -> Address {
111 Address::from_word(B256::from(self.to_be_bytes()))
112 }
113}
114
115#[cfg(test)]
116mod tests {
117 use revm::primitives::address;
118
119 use super::*;
120
121 #[test]
122 fn test_into_u256() {
123 let addr = address!("0x0000000000000000000000000000000000000001");
124 let u256 = addr.into_u256();
125 assert_eq!(u256, U256::from(0x01));
126 assert_eq!(u256.into_address(), addr);
127 }
128}