rbpf虚拟机-opcode码

本文涉及的产品
可观测可视化 Grafana 版,10个用户账号 1个月
任务调度 XXL-JOB 版免费试用,400 元额度,开发版规格
MSE Nacos/ZooKeeper 企业版试用,1600元额度,限量50份
简介: 该篇文章是rbpf虚拟机opcode码作用和使用的整理。(学习该虚拟机的目的是为了搞懂solana合约的执行方式,solana使用的rbpf是在该虚拟机上进行扩展。)

@[toc]

Welcome to Code Block's blog

本篇文章主要介绍了
[rbpf虚拟机-opcode码]
❤博主广交技术好友,喜欢我的文章的可以关注一下❤

一、概述

该篇文章是rbpf虚拟机opcode码作用和使用的整理。

(学习该虚拟机的目的是为了搞懂solana合约的执行方式,solana使用的rbpf是在该虚拟机上进行扩展。)

经过验证器后在rbpf虚拟机需要知道每条指令是用来做什么的,就需要用到opcode码,opcode码中由8种操作码、5种访问模式、4种数据大小进行组合获得,其结构如下图:

  7   6   5   4   |  3   2   |  1   0  
+---------------+--------+--------+
|     操作码    |  访问模式  |  大小   |
+---------------+--------+--------+

二、eBPF 的指令格式

完整的 eBPF 指令通常是 8 字节(64 位),其中 opcode 仅占 低 8 位,其余部分包含寄存器编号、立即数等。

  31      24 23     16 15      8 7       0
+--------+--------+--------+--------+
|    dst  |    src  |  offset  |  opcode |
+--------+--------+--------+--------+
|           immediate / address          |
+----------------------------------------+

字段说明:
| 字段 | 位数 | 说明 |
|-------------|--------|---------|
| opcode | 8-bit | 操作码,包括 OP、MODE 和 SIZE |
| dst | 4-bit | 目标寄存器编号 |
| src | 4-bit | 源寄存器编号(用于二元运算) |
| offset | 16-bit | 偏移量(用于内存访问或跳转) |
| immediate | 32-bit | 立即数(用于算术或跳转指令) |


三、Opcode 具体字段解释

1. 操作码(OP,7~4位)4位

Opcode 值 名称 说明
0x00 BPF_LD 立即数/内存加载指令
0x40 BPF_LDX 从内存加载到寄存器
0x60 BPF_ST 存储指令(寄存器 → 内存)
0x61 BPF_STX 存储指令(寄存器 → 内存,带索引)
0x80 BPF_ALU 算术运算(立即数模式)
0xc0 BPF_ALU64 64 位算术运算
0xa0 BPF_JMP 跳转指令
0xe0 BPF_JMP32 32 位跳转指令

2. 访问模式(MODE,3~2位)2位

Mode 值 名称 说明
0x00 BPF_IMM 立即数模式(直接使用值)
0x10 BPF_ABS 绝对地址模式(用于 BPF_LD
0x20 BPF_IND 间接地址模式(用于 BPF_LD
0x60 BPF_MEM 内存模式(从内存读取/写入)
0x70 BPF_LEN 报文长度(仅在 BPF_LD 使用)

3. 数据大小(SIZE,1~0位) 2位

Size 值 名称 说明
0x00 BPF_W 4 字节(32 位)
0x08 BPF_H 2 字节(16 位)
0x10 BPF_B 1 字节(8 位)
0x18 BPF_DW 8 字节(64 位)

三、具体使用

opcode码有很多种,如果直接使用如:0x71表示从内存加载 1 字节到寄存器,在定义时如果使用:

LD_B_REG = 0x71

这读起来有点费力,不利于维护操作。为了解决这一问题,可以直接将上述的操作码、访问模式、数据大小进行预先定义,然后使用以下方式进行定义:

LD_B_REG = BPF_LDX | BPF_MEM | BPF_B

BPF_LDX表示从内存加载到寄存器,BPF_MEM表示内存模式,BPF_B表示1个字节。这时我们就可以清楚的知晓LD_B_REG为从内存加载 1 字节到寄存器。这样,哪怕不知道是什么值,也可以通过按位或计算得到
opcode(操作码).

LD_B_REG = BPF_LDX | BPF_MEM | BPF_B
         = 0x61 | 0x00 | 0x10
         = 0b0110 0001 | 0b0000 0000 | 0b0001 0000
         ------------------------------------------
         = 0b0111 0001   // 结果 = 0x71(十六进制)

四、总结

通过上述对opcode码结构进行解读,对opcode码有了更深刻的理解,同时这种结构组合按位或处理可以产生很多组合结果,该方法可以很好的运用到日常的其它语言项目中。

代码来源:rbpf虚拟机
鸣谢: qmonnet 提供的开源代码.

当然,我也会将带有中文注释和自己理解的一些代码上传的我的github页面,感兴趣的朋友可以进行clone查看.

我的GitHub:forked


感谢您的点赞、关注、收藏!

目录
相关文章
|
5月前
|
人工智能 数据挖掘 Linux
Centos安装Python3.7(亲测可用)
本指南详细介绍了在基于Linux(以CentOS系统为例,使用yum包管理器)的系统上安装Python 3.7版本的完整流程。Python是一种广泛使用的高级编程语言,在各种领域如软件开发、数据分析、人工智能和区块链开发等都有着重要的应用。
491 3
|
5月前
|
区块链 数据安全/隐私保护 Python
小试牛刀-区块链WalletConnect协议数据解密
最近在学习如何使用Wallet Connect,查阅官方文档后,发现并没有太多的中文参考资料,英文直译读起来也有一些偏差,所以这边直接采用网页Demo的方式,对WC协议有了一定了解.在此进行记录,同时希望帮助到有实现相关功能的朋友.
305 4
|
5月前
|
存储 Java API
小试牛刀-SpringBoot集成SOL链
java工程师:如何在java/springboot中使用solana区块链呢?不用担心,现在solanaj来了!
168 0
|
5月前
|
存储 Java 区块链
Springboot应用开发:工具类整理
在实际的Springboot应用开发中,有很多类可作为工具类,这些类将实际开发中可能用到的重复性代码进行提取,方便在后续的开发中使用,在这里我对在开发中经常用到的工具类进行整理,方便自己之后查找,同时希望可以帮助到有实现相关功能的朋友。
266 1
|
5月前
|
存储 算法 fastjson
火点监测:Nasa高分卫星接入
NASA(美国国家航空航天局)是美国联邦政府的一个独立机构,负责国家的航空航天研究和探索任务。NASA成立于1958年,其使命是探索太空并推动科学技术的发展。NASA的主要任务包括研究地球和太空的物理特性、开发和测试航空航天技术、进行太空探索和科学研究,以及促进航空航天技术的应用和技术转移。这里使用其开发的系统firms(火灾资源管理系统),通过Http请求获取数据来实现火点的监测,帮助需要实现相关功能,有类似开发任务的朋友。
172 6
|
5月前
|
机器学习/深度学习 人工智能 自然语言处理
深度学习模型、算法与应用的全方位解析
深度学习,作为人工智能(AI)的一个重要分支,已经在多个领域产生了革命性的影响。从图像识别到自然语言处理,从语音识别到自动驾驶,深度学习无处不在。本篇博客将深入探讨深度学习的模型、算法及其在各个领域的应用。
936 3
|
5月前
|
机器学习/深度学习 算法 Java
Java实现林火蔓延路径算法
记录正在进行的森林防火项目中林火蔓延功能,本篇文章可以较好的实现森林防火蔓延,但还存在很多不足,如:很多参数只能使用默认值,所以蔓延范围仅供参考。(如果底层设备获取的数据充足,那当我没说)。注:因林火蔓延涉及因素太多,如静可燃物载量、矿质阻尼系数等存在估值,所以得出的结果仅供参考。
80 4
|
5月前
|
存储 JavaScript 区块链
小试牛刀-SOL链创建Token
最近需要编写SOL合约进行SPL Token的转移,因为在测试网上需要自己部署测试Token,同时为了更加美观,Token需携带metadata数据(对名称、头像等)进行定义.在此对创建过程进行记录,希望帮助到有需要实现相关功能的朋友.
102 1
|
5月前
|
Rust 安全 区块链
Rust-引用借用规则
Rust为确保程序在运行时不会出现数据竞争和其他内存安全,在使用引用时有很多规则,我在第一眼看到这些规则时也是有些头大,看了一段时间后才有了一些自己的一些理解。在这里对一些官方的术语和借用规则进行解释和记录。
67 1
|
5月前
|
传感器 定位技术 数据格式
常用通信协议及数据格式
常用通信协议和格式总结
447 2