You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Rust中将EVM存储槽H256拆分为u32、u128、u128

高效拆分EVM存储槽打包的uint256值

针对你给出的存储槽值 0x638d0490000000004b7cdeca2fe41a1b6411000000158fb5610df6aa553bfedb,最优的拆分方式是直接用位运算,避免字符串截取这类低效操作。以下是具体实现思路和代码示例:

核心逻辑

该存储槽按 uint32(最高32位)+ uint112(中间112位)+ uint112(最低112位) 的顺序打包为uint256,总位数32+112+112=256,刚好匹配uint256的长度。位运算直接操作数值底层,无额外内存开销,是性能最优的方案。

拆分步骤

  1. 提取uint32值:将uint256值右移224位(256-32),原最高32位会移动到最低位,直接转u32即可。
  2. 提取中间uint112值:先右移112位,再与112位全1的掩码(0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF)做与运算,得到中间段后转u128。
  3. 提取最低uint112值:直接与112位全1的掩码做与运算,得到最低段后转u128。

代码示例

Rust(基于ethers库)

use ethers::types::U256;

fn unpack_evm_slot(slot: U256) -> (u32, u128, u128) {
    // 112位掩码:2^112 - 1
    const U112_MASK: U256 = U256::from(0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF);

    // 拆分最高32位为u32
    let val_u32 = (slot >> 224).as_u32();
    // 拆分中间112位为u128
    let val_u128_mid = ((slot >> 112) & U112_MASK).as_u128();
    // 拆分最低112位为u128
    let val_u128_low = (slot & U112_MASK).as_u128();

    (val_u32, val_u128_mid, val_u128_low)
}

// 测试调用
fn main() {
    let slot = U256::from_str("0x638d0490000000004b7cdeca2fe41a1b6411000000158fb5610df6aa553bfedb").unwrap();
    let (val1, val2, val3) = unpack_evm_slot(slot);
    
    println!("u32值: 0x{:x}", val1);
    println!("中间u128值: 0x{:x}", val2);
    println!("最低u128值: 0x{:x}", val3);
}

Solidity

pragma solidity ^0.8.0;

contract SlotUnpacker {
    function unpackSlot(uint256 slot) public pure returns (uint32, uint128, uint128) {
        uint32 val1 = uint32(slot >> 224);
        uint128 val2 = uint128((slot >> 112) & 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF);
        uint128 val3 = uint128(slot & 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF);
        return (val1, val2, val3);
    }
}

Python

def unpack_evm_slot(slot_hex: str) -> tuple[int, int, int]:
    slot = int(slot_hex, 16)
    # 112位掩码
    u112_mask = (1 << 112) - 1
    
    val_u32 = (slot >> 224) & 0xFFFFFFFF
    val_u128_mid = (slot >> 112) & u112_mask
    val_u128_low = slot & u112_mask
    
    return (val_u32, val_u128_mid, val_u128_low)

# 测试调用
slot_hex = "0x638d0490000000004b7cdeca2fe41a1b6411000000158fb5610df6aa553bfedb"
val1, val2, val3 = unpack_evm_slot(slot_hex)
print(f"u32值: 0x{val1:x}")
print(f"中间u128值: 0x{val2:x}")
print(f"最低u128值: 0x{val3:x}")

说明

  • 位运算的时间复杂度为O(1),远优于字符串截取、补零后转换的方案,尤其适合批量处理存储槽的场景。
  • 拆分后的数值长度均小于目标类型(如112位 < 128位),不会出现溢出问题。

内容的提问来源于stack exchange,提问作者0xDmtri

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.09 20:05:16