2 个版本
0.1.2 | 2024 年 3 月 5 日 |
---|---|
0.1.1 |
|
0.1.0 | 2024 年 3 月 5 日 |
#95 在 性能分析
每月 67 次下载
205KB
5.5K SLoC
分割器
rubbler
是一个用 Rust 编写的 RISC-V 汇编器 🦀。这个库的主要目的是将一个简单的 RISC-V 汇编器嵌入到用 verilator 编写的 RISC-V CPU 测试代码中。
此外,还可以安装一个名为 rubble
的命令行程序。rubble
从标准输入读取行,并将表示汇编代码的 '1' 和 '0' 字符串输出到标准输出。
特性
详细的错误解释
$ rubble
> Input RISC-V assembly line(s): (Press <CTRL-d> once finished)
add t0, t1, 5
> Rubbling...
[Line 1] Generator error: `add` instruction expects the following arguments: [RegDest, RegSrc1, RegSrc2].
$ rubble
> Input RISC-V assembly line(s): (Press <CTRL-d> once finished)
jal t0, hello
> Rubbling...
[Line 1] Generator error: Cannot resolve symbol: `hello`.
$ rubble
> Input RISC-V assembly line(s): (Press <CTRL-d> once finished)
hello
> Rubbling...
[Line 1] Syntax error: Unknown opcode or directive `hello`.
支持标签
$ rubble
> Input RISC-V assembly line(s): (Press <CTRL-d> once finished)
fibonacci:
addi t0, zero, 0 # t0
addi t1, zero, 1 # t1
addi t2, zero, 0 # i
loop:
bge t2, a0, end
add t3, t0, t1 # temp
addi t0, t1, 0
addi t1, t3, 0
addi t2, t2, 1
jal t4, loop
end:
addi a0, t0, 0
> Rubbling...
> Here's your bytes:
10010011000000100000000000000000
00010011000000110001000000000000
10010011000000110000000000000000
01100011110111001010001100000000
00110011100011100110001000000000
10010011000000100000001100000000
00010011000000110000111000000000
10010011100000110001001100000000
11101111111111101101111111111110
00010011100001010000001000000000
支持指令
$ rubble
> Input RISC-V assembly line(s): (Press <CTRL-d> once finished)
.section .data
.byte 1, 2, 3
> Rubbling...
> Here's your bytes:
000000010000001000000011
请参阅支持的指令以获取所有支持的指令。
支持的指令
目前,仅支持 RV32I 的一小部分
- 寄存器-立即数算术操作
- ADDI, ANDI, ORI, XORI, SLTI, SLTIU, SLLI, SRLI, LUI, AUIPC
- 寄存器-寄存器算术操作
- ADD, AND, OR, XOR, SLT, SLTU, SLL, SRL, SRA, SUB
- 跳转指令
- JAL, JALR
- 分支指令
- BEQ, BNE, BLT, BLTU, BGE, BGEU
- 加载操作
- LW, LH, LHU, LB, LBU
- 存储操作
- SW, SH, SB
支持的汇编指令
目前,以下指令可供使用
- .align
- .p2align
- .comm
- .common
- .section
- .equ
- .byte
请参阅RISC-V 汇编程序员手册以获取每个指令的语法。
从源码构建
要求
Rust (请参阅安装 Rust)
构建说明
git clone https://github.com/fuad1502/rubbler.git
cd rubbler
cargo build --release
这些命令会生成 rubbler
可执行文件、rubbler/target/rubbler.h
头文件和 rubbler
目标目录下的 librubbler.a
静态库。
使用示例
Rust
let source = "lui t2, -3";
let expected_res = vec![0b10110111,0b11110011,0b11111111,0b11111111];
let res = rubbler::rubble(source).unwrap();
assert_eq!(res, expected_res);
有关 Rust 中的更多示例,请参阅 docs.rs/rubbler。
C/C++
此示例是从rubbler-verilator-example中摘取的代码片段。
#include "rubbler.h"
...
auto source = "add t0, t1, t2";
auto bytes = (uint8_t *)malloc(sizeof(uint8_t) * MAX_SIZE);
uintptr_t size = MAX_SIZE;
assert(rubble(source, bytes, &size));
...
有关如何使用每个函数的完整解释,请参阅rubbler::ffi
模块,或者简单地查看rubbler.h
中每个函数的文档字符串。
与Verilator集成
在以下讨论中,我们假设您已经安装了verilator
,并且verilator
命令可用。有关如何进行安装的说明,请参阅verilator 文档。以下两个示例均来自rubbler-verilator-example。
使用Makefile
假设以下项目目录结构
- project
- main.cpp
- top.sv
- Makefile
以下Makefile
将从main.cpp
和top.sv
构建main
,这两个文件都可以从main.cpp
中使用verilator
和rubbler
库。
VERILATOR_ROOT := /usr/local/share/verilator
VM_SC := 0
VM_TRACE := 0
VERILATOR_OBJS := verilated.o verilated_threads.o verilated_dpi.o
main:main.o obj_dir/Vtop__ALL.a librubbler.a $(VERILATOR_OBJS)
$(CXX) $^ -o $@
main.o: main.cpp obj_dir/Vtop.h rubbler.h
$(CXX) \
-Iobj_dir \
-I$(VERILATOR_ROOT)/include \
-I$(VERILATOR_ROOT)/include/vltstd \
-c main.cpp -o $@
obj_dir/Vtop__ALL.a obj_dir/Vtop.h: top.sv
verilator -cc --build -j top.sv
rubbler.h librubbler.a: rubbler
cd rubbler && cargo build --release
cp rubbler/target/rubbler.h rubbler/target/release/librubbler.a .
rubbler:
git clone https://github.com/fuad1502/rubbler.git
include $(VERILATOR_ROOT)/include/verilated.mk
.PHONY:clean
clean:
rm -rf obj_dir
rm -rf rubbler
rm librubbler.a rubbler.h
rm *.o *.d
rm main
有关完整示例,请参阅rubbler-verilator-example。
使用CMake ExternalProject
假设以下项目目录结构
- project
- main.cpp
- top.sv
- CMakeLists.txt
以下CMakeLists.txt
文件将从main.cpp
和top.sv
构建main
,这两个文件都可以从main.cpp
中使用verilator
和rubbler
库。
cmake_minimum_required(VERSION 3.14)
set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
project(rubbler-verilator-example)
find_package(verilator REQUIRED)
include(ExternalProject)
ExternalProject_Add(
rubbler
GIT_REPOSITORY https://github.com/fuad1502/rubbler.git
DOWNLOAD_DIR ${CMAKE_BINARY_DIR}
SOURCE_DIR ${CMAKE_BINARY_DIR}/rubbler
BINARY_DIR ${CMAKE_BINARY_DIR}/rubbler
CONFIGURE_COMMAND ""
INSTALL_COMMAND ""
BUILD_COMMAND cargo build --release
)
set(RUBBLER_LIB ${CMAKE_BINARY_DIR}/rubbler/target/release/librubbler.a)
add_executable(main main.cpp)
target_include_directories(main PRIVATE ${CMAKE_BINARY_DIR}/rubbler/target)
target_link_libraries(main PRIVATE ${RUBBLER_LIB})
verilate(main SOURCES top.sv)
有关完整示例,请参阅rubbler-verilator-example。
二进制安装
要全局使用rubble
二进制文件,请使用以下命令安装
cargo install rubbler
问题
- 尚不支持在内存寻址表达式中使用符号。
计划功能
- 报告多个错误而不是在检测到第一个错误时终止。
- 通过添加列信息来增加错误报告的详细程度,并显示与报告一起的违规行。
- 支持伪指令。
无运行时依赖
~0–1.4MB
~19K SLoC