FHEVM 原生链(FHEVM-native)密文链上存储与 GetCiphertext 读取指南

FHEVM 原生链(FHEVM-native)密文链上存储与 GetCiphertext 读取指南 FHEVM 原生链FHEVM-native密文链上存储与 GetCiphertext 读取指南【免费下载链接】fhevmFHEVM, a full-stack framework for integrating Fully Homomorphic Encryption (FHE) with blockchain applications项目地址: https://gitcode.com/GitHub_Trending/fh/fhevm导读本文聚焦 Zama fhEVM 全栈框架中FHEVM-native原生链模式的密文存储子系统介绍密文以何种布局落盘在链上、为何是只追加append-only的不可变存储、以及任何节点/用户如何通过FheLib预编译合约上的GetCiphertext函数函数选择器ff627e77用一次eth_call读取序列化 TFHE 密文。读完本文你将掌握 FHEVM-native 密文存储的地址布局、handle 与密文的映射关系、以及用 Python/curl实测读取密文的完整方法并理解它与符号执行、Executor 调度之间的衔接原理。存储模型总览在 FHEVM-native 中所有持久化的 FHE 密文都直接存放在链上这与 fhEVM-coprocessor 将密文存放在链下数据库与 DA 层形成对比见 系统总览。具体落盘位置是一个预定义的、没有部署任何代码的合约——它纯粹充当密文的存储容器。截至本文撰写时该密文存储合约的地址为0x5estorage.md。EVM 的合约存储本质上是一个 key-value 映射FHEVM-native 直接复用了这一原语key 密文的handle即 ebool/e(u)int 值一个 32 字节标识符value 该 handle 对应的实际 TFHE 序列化密文。这种设计带来三个关键特性特性说明链上可验证密文与区块状态绑定天然具备可审计性可被 Gateway 等组件用于构造存储证明storage proof不可变已写入的密文不可修改存储是**只追加append-only**的公开可读任何人都能读取密文读取入口是FheLib预编译合约的GetCiphertext函数节点/验证者必须支持该函数Handle密文在存储中的钥匙要理解handle 作为 key需要先理解 handle 的生成方式。FHEVM 采用符号执行symbolic execution链上智能合约在 EVM 内执行时并不做真实的 FHE 计算而是把密文的引用——handle——作为符号值在合约间传递。handle 是一个 32 字节值由对 FHE 操作及其输入做哈希得到H keccak256(fheOperation, input1, input2, ..., inputN)其中输入既可以是其他 handle也可以是明文值。这样结果 handle 可以确定性地在链上FHEVMExecutor 合约内先行计算出来无需等待真实密文符号执行文档。而 handle 与真实密文的最终绑定正是通过本文所述的链上存储完成的Executor 完成 FHE 计算后把结果密文以 handle 为 key 写入0x5e密文存储合约合约说明。何时真正写入存储并非每一个中间计算结果都会被持久化。在 FHEVM-native 中块执行分两阶段符号执行EVM 在一个块内累积所有请求的 FHE 操作输入 handle、结果 handle并通过SSTORE操作码记录哪些结果 handle 被智能合约真正存储——这一阶段不产生任何真实 FHE 计算FHE 计算块结束时 EVM 将累积的操作列表发给链下 ExecutorExecutor 完成真实计算并返回结果密文持久化EVM 只把被SSTORE过的 handle对应的结果密文写入链上存储从而避免把从未被合约开发者保存的中间结果密文也写进去原生链 FHE 计算文档。这意味着你能够通过GetCiphertext读到的就是这些被智能合约真正写入存储的 handle 对应的密文中间结果的 handle 即使出现在某笔交易中也可能不在存储中。FheLib 预编译合约与 GetCiphertext 函数读取密文的入口是FheLib预编译合约。它在每个节点/验证者上以预编译precompile形式存在不依赖任何合约代码术语表其地址为0x000000000000000000000000000000000000005d。注意与密文存储合约区分地址角色0x5d即...005dFheLib预编译合约——密文读取接口所在0x5e无代码密文存储合约——密文实际落盘所在GetCiphertext函数根据给定的 ebool/e(u)int 值handle返回序列化的 TFHE 密文其函数选择器function selector为ff627e77。只能通过 eth_call 调用GetCiphertext只支持eth_callRPC 调用。这是因为读取密文是一个无副作用的查询操作它不修改链上状态、不产生交易直接在节点本地执行并返回结果因此既不能也不需要通过发送交易来调用。调用格式一次eth_call的参数中需要携带toFheLib预编译地址0x000000000000000000000000000000000000005d该地址按链硬编码data0x 函数选择器 待查询的 handle。由于本函数只有一个 32 字节参数data可以简写为0x后直接拼接 handle 的十六进制字符串不足 64 位时需左补零对齐到 32 字节block通常使用latest也可以指定其他区块以读取历史快照下的存储。实战用 Python 通过 eth_call 读取密文以下代码摘自 storage.md完整演示了如何向本地节点的 JSON-RPC 端点发起eth_call读取一个 handle 对应的密文import http.client import json # 这是 FheLib 预编译合约的地址。该值按区块链硬编码。 fhe_lib_precompile_address 0x000000000000000000000000000000000000005d # 需要查询密文的 ebool/e(u)int 值handle。 handle f038cdc8bf630e239f143abeb039b91ec82ec17a8460582e7a409fa551030c06 # GetCiphertext 的函数选择器。 get_ciphertext_selector ff627e77 # 以 handle 作为 data 调用 FheLib 预编译合约。 payload { jsonrpc: 2.0, method: eth_call, params: [ { to: fhe_lib_precompile_address, data: 0x handle }, latest ], id: 1, } con http.client.HTTPConnection(localhost, 8545) con.request(POST, /, bodyjson.dumps(payload), headers{Content-Type: application/json}) resp json.loads(con.getresponse().read()) # 去掉开头的 0x 并解码十六进制得到包含密文的字节缓冲。 ciphertext bytes.fromhex(resp[result][2:])要点说明地址拼接data 0x handle利用 handle 本身已是 64 位十六进制32 字节恰好满足选择器 32 字节参数的 ABI 编码选择器其实已经内嵌在 handle 所在数据的最前 4 字节之前——更严谨的做法是在 handle 前显式拼上选择器0xff627e77 handle但本函数参数的 ABI 编码恰好使0x handle 也能被节点识别源码示例采用了这种简写。响应解析resp[result]是0x开头的十六进制串bytes.fromhex(...)将其还原为原始字节流即为序列化后的 TFHE 密文可直接交给 TFHE 相关工具链如 tfhe-rs反序列化使用。端口说明示例假设节点 RPC 监听在localhost:8545geth 默认端口实际请替换为你所连全节点/验证者的地址与端口。等价的 curl 调用如果你更习惯命令行同样的请求可以这样发出curl -s -X POST http://localhost:8545 -H Content-Type: application/json \ --data { jsonrpc: 2.0, method: eth_call, params: [{ to: 0x000000000000000000000000000000000000005d, data: 0xff627e77f038cdc8bf630e239f143abeb039b91ec82ec17a8460582e7a409fa551030c06 }, latest], id: 1 }响应中的result字段即为密文数据。谁来读这些密文生态中的读取方密文虽然人人可读但真实世界里主要由以下组件消费Executor / 调度器在执行 FHE 计算时节点需要先拿到输入 handle 对应的密文。在 scheduler.rs 的调度实现中可以看到FheGetCiphertext是一个被特殊对待的操作它直接返回输入密文本身而不产生新的 FHE 计算——也就是说它是计算图中取数节点从链上存储取回输入密文喂给后续真正计算。Gateway解密流程中Gateway 需要计算存储证明P来证明某个 handleh即密文C确实存在于链上存储且可解密Gateway 解密文档密文的链上公开性正是这类证明的前提。dApp / fhevmjs 用户用户通过完整节点full node的 RPC 读取密文进行链下的加密/解密操作。完整节点自身也维护全部链上数据天然可以响应这类查询原生链架构。小结FHEVM-native 用无代码存储合约 预编译读取接口这一对组合解决了密文的持久化与公开可读问题0x5e合约用 handle 作 key 保存不可变、只追加的序列化密文0x5d的FheLib预编译通过GetCiphertextff627e77让任何节点在eth_call中一键取回密文。二者共同支撑起符号执行→Executor 计算→结果落盘→按需读取的完整数据闭环也是 Gateway 存储证明、用户链下解密等上层功能的事实基础。相关延伸阅读符号执行与 handle 生成原生链 FHE 计算与持久化时机FHEVM-native 节点架构系统术语表FheLib、handle 定义FHEVMExecutor 合约实现【免费下载链接】fhevmFHEVM, a full-stack framework for integrating Fully Homomorphic Encryption (FHE) with blockchain applications项目地址: https://gitcode.com/GitHub_Trending/fh/fhevm创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考