分类 Solana 下的文章

Solana调整出块时间为50ms,并且保持recent_blockhash(120秒)过期时间不变


背景

比如想基于Solana运行一个Layer2网络或者应用链,需要尽可能的加快出块时间{从综合测试和其它类似项目综合分析,50ms是最快最稳定的},
如果单一的降低出块时间,会导致 recent_blockhash过期时间变短,从而可能导致交易发送时容易报 “Blockhash not found”
下面我们将给出如何实现50ms的slot,并保持recent_blockhash过期时间(120s)不变的方案

代码修改

agave\sdk\program\src\clock.rs

/// 每秒 tick 数:PoH 产生 tick 的速度(原为 160)
pub const DEFAULT_TICKS_PER_SECOND: u64 = 1000;  // 1000 ticks = 1秒

/// 每 slot 包含 tick 数(原为 64)
pub const DEFAULT_TICKS_PER_SLOT: u64 = 50;      // 50 ticks = 1 slot

/// blockhash 最大有效时间(保持主网一致)
pub const MAX_HASH_AGE_IN_SECONDS: u64 = 120;    // blockhash 有效时间 120秒

Solana 会自动计算:

pub const MAX_RECENT_BLOCKHASHES: usize =
    MAX_HASH_AGE_IN_SECONDS * DEFAULT_TICKS_PER_SECOND as usize / DEFAULT_TICKS_PER_SLOT as usize;
// => 2400

MAX_RECENT_BLOCKHASHES 为什么要 调整为 2400

这是因为你想要 每个 slot 时间为 50ms,而官方默认是 400ms,两者时间差 8 倍。

解释为什么需要把 MAX_RECENT_BLOCKHASHES 调整到 2400

1. 官方默认参数回顾:

参数 数值
MAX_HASH_AGE_IN_SECONDS 120 s
DEFAULT_TICKS_PER_SECOND 160
DEFAULT_TICKS_PER_SLOT 64
MAX_RECENT_BLOCKHASHES 300

计算:

意味着最近 120 秒内链上大约有 300 个 slot(因为每 slot 约 0.4 秒)。


2. 你想改成 50ms/slot

50ms = 0.05秒,等于官方 0.4秒的 18\frac{1}{8}81。

在 120 秒内,会有:


3. 为了保持 blockhash 有效时间不变

你必须保存最近 2400 个 blockhash(对应 2400 个 slot),才能覆盖 120 秒内所有 slot。


4. 计算验证

MAX_RECENT_BLOCKHASHES = MAX_HASH_AGE_IN_SECONDS * DEFAULT_TICKS_PER_SECOND / DEFAULT_TICKS_PER_SLOT

现在参数改成:

  • MAX_HASH_AGE_IN_SECONDS = 120
  • DEFAULT_TICKS_PER_SECOND = 1000 (tick 速度提高了)
  • DEFAULT_TICKS_PER_SLOT = 50

计算:


总结

每 slot 时间 slot 数(120秒内) 需保存最近 blockhash 数量 MAX_RECENT_BLOCKHASHES
400ms 300 300
50ms 2400 2400

所以,MAX_RECENT_BLOCKHASHES 调整为 2400 是为了匹配新的更快 slot 频率,保证 blockhash 在 120 秒内仍有效

solana-genesis 初始化

对于初始化时也需要对应的加入启动参数

--ticks-per-slot 50

测试脚本

#!/bin/bash

RPC_URL="https://api.mainnet-beta.solana.com"

# Step 1: 获取最新 blockhash
echo "Fetching latest blockhash..."
RESPONSE=$(curl -s -X POST $RPC_URL \
  -H "Content-Type: application/json" \
  -d '{"jsonrpc":"2.0","id":1,"method":"getLatestBlockhash"}')

BLOCKHASH=$(echo $RESPONSE | jq -r '.result.value.blockhash')

echo " Got blockhash: $BLOCKHASH"
echo " Starting to monitor validity..."

SECONDS_ELAPSED=0
INTERVAL=1  # 每次检测间隔,单位秒

while true; do
  VALID_RESPONSE=$(curl -s -X POST $RPC_URL \
    -H "Content-Type: application/json" \
    -d "{\"jsonrpc\":\"2.0\",\"id\":1,\"method\":\"isBlockhashValid\",\"params\":[\"$BLOCKHASH\"]}")

  IS_VALID=$(echo $VALID_RESPONSE | jq -r '.result.value')

  if [ "$IS_VALID" = "true" ]; then
    echo "[$SECONDS_ELAPSED s]  Blockhash still valid"
    sleep $INTERVAL
    SECONDS_ELAPSED=$((SECONDS_ELAPSED + INTERVAL))
  else
    echo "[$SECONDS_ELAPSED s]  Blockhash EXPIRED"
    break
  fi
done

echo " Total validity duration: $SECONDS_ELAPSED seconds"

Solana SPL 程序编译


代码Clone

git clone https://github.com/solana-program/token.git
cd token
git checkout program@v3.5.0

基础环境

# 安装nvm
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/master/install.sh | bash
source ~/.bashrc

# 安装node
nvm install 20
node -v

# 安装pnpm
npm install -g pnpm

安装依赖

pnpm install

编译

cd program/
cargo build-sbf

默认编译可能出现以下错误

[2025-04-25T09:39:35.004769959Z ERROR cargo_build_sbf] Failed to obtain package metadata: `cargo metadata` exited with an error: error: current package believes it's in a workspace when it's not:
    current:   /mnt/d/github/token/program/Cargo.toml
    workspace: /mnt/d/github/token/Cargo.toml

    this may be fixable by adding `program` to the `workspace.members` array of the manifest located at: /mnt/d/github/token/Cargo.toml
    Alternatively, to keep it out of the workspace, add the package to the `workspace.exclude` array, or add an empty `[workspace]` table to the package's manifest.

解决

在 program 目录的 Cargo.toml 文件中添加空的 [workspace] 表

修改 program\Cargo.toml,在第一行增加

[workspace] // 增加此行
[package]
name = "spl-token"
version = "3.5.0"
...

执行成功后,程序编译出现在program\target\deploy\spl_token.so


Solana Secp256k1 ECDSA


no_std与 Secp256k1 曲线兼容的 ECDSA 实现,专为在 Solana 生态系统中使用而设计。

概述

该库使用 Secp256k1 曲线提供了 ECDSA 签名的轻量级实现。它旨在与各种环境兼容no_std,因此适用于嵌入式系统、WebAssembly 模块以及其他缺乏标准库支持的受限环境。

特征

  • no_std 兼容:在没有 Rust 标准库的环境中工作
  • 签名创建:使用各种方法生成 ECDSA 签名:
    • RFC6979 确定性随机数生成
    • 自定义临时密钥 (k) 支持
    • 预散列消息支持
  • 签名验证:根据公钥验证 ECDSA 签名
  • 签名规范化:使用可选的 s 值规范化(低 S)处理签名的可延展性
  • 最小依赖solana_secp256k1:建立在原语之上

https://github.com/deanmlittle/solana-secp256k1-ecdsa


RISC-V 与EVM集成的性能和可行性分析


前置总结

技术目的:以太坊网络扩容面临的几个长期瓶颈,包括稳定的数据可用性采样、确保区块生产保持竞争力,以及零知识EVM证明。在智能合约中实施RISC-V架构将保持区块生产市场的竞争力,并提高执行层零知识功能的效率。转向RISC-V将使 Ethereum 与 Solana 和Sui等更新的区块链更具竞争力

技术可行性:从《RISC-V 与以太坊虚拟机集成的性能和可行性分析》分析和测试结果应该可行

难度和风险:需要执行层的重新设计,社区大概评估整体需要数年的时间,需要大量资源,并可能出现新的漏洞,并且开发人员和项目将如何通过旧的智能控制trac移植到新系统存在问题。当涉及向后兼容性时,这可能会引起很多麻烦。基本等同于个完整的新链

现状:目前消息来看,Vitalik只是计划考虑信标链运行RISC-V,相当于技术调研初期,对于以太坊目前现状,可以主要为了造势,稳币价。对于以太坊是否真正开始投入开发支持,可能等先观望下了

RISC-V 与以太坊虚拟机集成的性能和可行性分析

https://hackmd.io/@0xdeveloperuche/Hk18BWxkxl

RISC-V与EVM相关项目:

evm

https://github.com/developeruche/riscv-evm-experiment/tree/main/crates/research-draft

img

zkevm

https://verified-zkevm.org/

https://argument.xyz/blog/riscv-good-bad/


Solana 节点服务器优化


系统初始化配置

https://docs.solanalabs.com/operations/guides/validator-start#system-tuning

sudo bash -c "cat >/etc/sysctl.d/21-agave-validator.conf <<EOF
# Increase UDP buffer sizes
net.core.rmem_default = 134217728
net.core.rmem_max = 134217728
net.core.wmem_default = 134217728
net.core.wmem_max = 134217728

# Increase memory mapped files limit
vm.max_map_count = 1000000

# Increase number of allowed open file descriptors
fs.nr_open = 1000000
EOF"
sudo sysctl -p /etc/sysctl.d/21-agave-validator.conf
sudo bash -c "cat >/etc/security/limits.d/90-solana-nofiles.conf <<EOF
# Increase process file descriptor count limit
* - nofile 1000000
EOF"