202 lines
5.4 KiB
Rust
202 lines
5.4 KiB
Rust
//! SPV (Simplified Payment Verification) 证明验证模块
|
||
//!
|
||
//! 实现以太坊交易的SPV证明生成和验证
|
||
|
||
use sha3::{Digest, Keccak256};
|
||
use serde::{Deserialize, Serialize};
|
||
|
||
/// SPV证明验证器
|
||
pub struct SPVProofVerifier;
|
||
|
||
/// Merkle证明
|
||
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||
pub struct MerkleProof {
|
||
/// 交易索引
|
||
pub tx_index: u64,
|
||
/// Merkle路径
|
||
pub proof: Vec<Vec<u8>>,
|
||
/// 根哈希
|
||
pub root: Vec<u8>,
|
||
}
|
||
|
||
impl SPVProofVerifier {
|
||
/// 创建新的SPV证明验证器
|
||
pub fn new() -> Self {
|
||
Self
|
||
}
|
||
|
||
/// 验证Merkle证明
|
||
///
|
||
/// # 参数
|
||
/// - `tx_hash`: 交易哈希
|
||
/// - `proof`: Merkle证明
|
||
///
|
||
/// # 返回
|
||
/// - `true`: 证明有效
|
||
/// - `false`: 证明无效
|
||
pub fn verify_merkle_proof(
|
||
&self,
|
||
tx_hash: &[u8],
|
||
proof: &MerkleProof,
|
||
) -> bool {
|
||
let mut current_hash = tx_hash.to_vec();
|
||
let mut index = proof.tx_index;
|
||
|
||
// 沿着Merkle树向上验证
|
||
for sibling in &proof.proof {
|
||
let mut hasher = Keccak256::new();
|
||
|
||
if index % 2 == 0 {
|
||
// 当前节点在左边
|
||
hasher.update(¤t_hash);
|
||
hasher.update(sibling);
|
||
} else {
|
||
// 当前节点在右边
|
||
hasher.update(sibling);
|
||
hasher.update(¤t_hash);
|
||
}
|
||
|
||
current_hash = hasher.finalize().to_vec();
|
||
index /= 2;
|
||
}
|
||
|
||
// 检查是否等于根哈希
|
||
current_hash == proof.root
|
||
}
|
||
|
||
/// 生成Merkle证明(简化版)
|
||
///
|
||
/// # 参数
|
||
/// - `tx_hashes`: 区块中的所有交易哈希
|
||
/// - `tx_index`: 目标交易的索引
|
||
///
|
||
/// # 返回
|
||
/// Merkle证明
|
||
pub fn generate_merkle_proof(
|
||
&self,
|
||
tx_hashes: &[Vec<u8>],
|
||
tx_index: usize,
|
||
) -> Option<MerkleProof> {
|
||
if tx_index >= tx_hashes.len() {
|
||
return None;
|
||
}
|
||
|
||
let mut proof = Vec::new();
|
||
let mut current_level = tx_hashes.to_vec();
|
||
let mut index = tx_index;
|
||
|
||
// 构建Merkle树
|
||
while current_level.len() > 1 {
|
||
let mut next_level = Vec::new();
|
||
|
||
// 记录当前层的兄弟节点
|
||
let sibling_index = if index % 2 == 0 { index + 1 } else { index - 1 };
|
||
if sibling_index < current_level.len() {
|
||
proof.push(current_level[sibling_index].clone());
|
||
}
|
||
|
||
// 计算下一层
|
||
for i in (0..current_level.len()).step_by(2) {
|
||
let mut hasher = Keccak256::new();
|
||
hasher.update(¤t_level[i]);
|
||
|
||
if i + 1 < current_level.len() {
|
||
hasher.update(¤t_level[i + 1]);
|
||
} else {
|
||
// 奇数个节点,复制最后一个
|
||
hasher.update(¤t_level[i]);
|
||
}
|
||
|
||
next_level.push(hasher.finalize().to_vec());
|
||
}
|
||
|
||
current_level = next_level;
|
||
index /= 2;
|
||
}
|
||
|
||
let root = current_level[0].clone();
|
||
|
||
Some(MerkleProof {
|
||
tx_index: tx_index as u64,
|
||
proof,
|
||
root,
|
||
})
|
||
}
|
||
|
||
/// 验证区块头
|
||
///
|
||
/// # 参数
|
||
/// - `block_header`: 区块头数据
|
||
/// - `expected_hash`: 期望的区块哈希
|
||
///
|
||
/// # 返回
|
||
/// - `true`: 区块头有效
|
||
/// - `false`: 区块头无效
|
||
pub fn verify_block_header(
|
||
&self,
|
||
block_header: &[u8],
|
||
expected_hash: &[u8],
|
||
) -> bool {
|
||
let mut hasher = Keccak256::new();
|
||
hasher.update(block_header);
|
||
let hash = hasher.finalize();
|
||
|
||
hash.as_slice() == expected_hash
|
||
}
|
||
}
|
||
|
||
impl Default for SPVProofVerifier {
|
||
fn default() -> Self {
|
||
Self::new()
|
||
}
|
||
}
|
||
|
||
#[cfg(test)]
|
||
mod tests {
|
||
use super::*;
|
||
|
||
#[test]
|
||
fn test_merkle_proof_generation_and_verification() {
|
||
let verifier = SPVProofVerifier::new();
|
||
|
||
// 创建4个交易哈希
|
||
let tx_hashes: Vec<Vec<u8>> = vec![
|
||
vec![1, 2, 3, 4],
|
||
vec![5, 6, 7, 8],
|
||
vec![9, 10, 11, 12],
|
||
vec![13, 14, 15, 16],
|
||
];
|
||
|
||
// 为第2个交易生成证明
|
||
let proof = verifier.generate_merkle_proof(&tx_hashes, 1);
|
||
assert!(proof.is_some());
|
||
|
||
let proof = proof.expect("mainnet: handle error");
|
||
|
||
// 验证证明
|
||
let is_valid = verifier.verify_merkle_proof(&tx_hashes[1], &proof);
|
||
assert!(is_valid);
|
||
}
|
||
|
||
#[test]
|
||
fn test_block_header_verification() {
|
||
let verifier = SPVProofVerifier::new();
|
||
|
||
let block_header = b"test block header";
|
||
|
||
// 计算期望的哈希
|
||
let mut hasher = Keccak256::new();
|
||
hasher.update(block_header);
|
||
let expected_hash = hasher.finalize();
|
||
|
||
// 验证
|
||
let is_valid = verifier.verify_block_header(block_header, &expected_hash);
|
||
assert!(is_valid);
|
||
|
||
// 错误的哈希
|
||
let wrong_hash = vec![0u8; 32];
|
||
let is_valid = verifier.verify_block_header(block_header, &wrong_hash);
|
||
assert!(!is_valid);
|
||
}
|
||
}
|