利用 RuyiSDK 玩转 RISC-V 版 Teeworlds
本文将手把手带你实操:在 x86_64 Ubuntu 24.04 上,利用 RuyiSDK 虚拟环境和 openEuler RISC-V Sysroot,从零编译并运行经典的开源射击游戏 Teeworlds。
环境准备:构建 RISC-V 的“地基”
首先,我们需要在 x86 主机上模拟出 RISC-V 的运行环境。这里我们选择 openEuler 作为目标系统的根文件系统(Sysroot)。
1. 安装“传送门”工具
我们需要 qemu-user-static 来让 x86 系统直接透明地运行 RISC-V 的二进制指令。
$ sudo apt update
$ sudo apt install -y qemu-user-static dnf git cmake
2. 部署 openEuler Sysroot
创建一个目录并初始化 openEuler 24.03 的最小系统环境。
$ mkdir -p ~/oe-sysroot/usr/bin
$ sudo cp /usr/bin/qemu-riscv64-static ~/oe-sysroot/usr/bin/
# 使用 dnf 跨架构安装基础包
$ sudo dnf --installroot=$HOME/oe-sysroot \
--forcearch=riscv64 \
--releasever=24.03 \
--repofrompath=oe-base,[https://mirrors.huaweicloud.com/openeuler/openEuler-24.03-LTS/OS/riscv64/](https://mirrors.huaweicloud.com/openeuler/openEuler-24.03-LTS/OS/riscv64/) \
--repofrompath=oe-update,[https://mirrors.huaweicloud.com/openeuler/openEuler-24.03-LTS/update/riscv64/](https://mirrors.huaweicloud.com/openeuler/openEuler-24.03-LTS/update/riscv64/) \
--disablerepo=* --enablerepo=oe-base,oe-update \
--nogpgcheck \
--setopt=install_weak_deps=False \
install -y bash coreutils dnf openEuler-release
3.安装依赖
为了编译 Teeworlds,我们需要在 Sysroot 中准备好 SDL2、OpenGL 等图形开发库。
# 同步 DNS 配置确保网络畅通
$ sudo cp /etc/resolv.conf ~/oe-sysroot/etc/resolv.conf
# 进入 chroot 环境
$ sudo chroot ~/oe-sysroot /bin/bash
# 在 Sysroot 内部安装开发依赖项
$ dnf install -y SDL2-devel freetype-devel libpng-devel wavpack-devel \
mesa-dri-drivers mesa-libGL-devel libX11-devel zlib-devel \
openssl-devel libXext-devel libXcursor-devel libXinerama-devel \
libXi-devel --nogpgcheck --releasever=24.03
$ exit
RuyiSDK 交叉编译
0.本文编译采用的是Licheepi4A虚拟环境,建立步骤可参考文档
1.获取源码
$ git clone --recursive [https://github.com/teeworlds/teeworlds.git](https://github.com/teeworlds/teeworlds.git)
$ cd teeworlds
2. 配置 Toolchain 映射
在 cmake/toolchains/ 目录下创建 riscv64.toolchain,将路径指向 Sysroot。
set(CMAKE_SYSTEM_NAME Linux)
set(CMAKE_SYSTEM_PROCESSOR riscv64)
# 指定 RuyiSDK 提供的交叉编译器
set(CMAKE_C_COMPILER "riscv64-plctxthead-linux-gnu-gcc")
set(CMAKE_CXX_COMPILER "riscv64-plctxthead-linux-gnu-g++")
set(CMAKE_SYSROOT "/home/cjh/oe-sysroot")
set(CMAKE_FIND_ROOT_PATH "/home/cjh/oe-sysroot")
set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER)
set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY)
set(CMAKE_FIND_ROOT_PATH_MODE_PACKAGE ONLY)
# 针对 Freetype 的手动路径修正
set(CMAKE_INCLUDE_PATH "/home/cjh/oe-sysroot/usr/include/freetype2")
set(FREETYPE_LIBRARY "/home/cjh/oe-sysroot/usr/lib64/libfreetype.so")
3.赋予权限
$ sudo chown -R $USER:$USER ~/oe-sysroot
4.建立软链接
$ cd ~/oe-sysroot
$ sudo ln -s usr/lib64 lib
$ sudo ln -s lib64 usr/lib
$ sudo ln -s ~/oe-sysroot/usr/lib64/dri ~/oe-sysroot/lib64/dri
5. 避坑
Sysroot 里的 sdl2-config.cmake 往往会将路径硬编码为 /usr。如果直接编译,它会去宿主机找 x86 的头文件导致报错。
修复: 编辑 ~/oe-sysroot/lib64/cmake/SDL2/sdl2-config.cmake,将硬编码路径修改为基于 ${prefix} 的动态路径:
#修改前
set(exec_prefix "/usr")
set(bindir "/usr/bin")
set(libdir "/usr/lib64")
set(includedir "/usr/include")
#修改后
set(exec_prefix "${prefix}")
set(bindir "${prefix}/bin")
set(libdir "${prefix}/lib64")
set(includedir "${prefix}/include")
6.编译运行
$ cd teeworlds
$ mkdir build && cd build
$ cmake .. -DCMAKE_TOOLCHAIN_FILE=../cmake/toolchains/riscv64.toolchain
$ make
通过 ruyi-qemu 运行游戏
启动服务器
$ ruyi-qemu -cpu rv64 -L ~/oe-sysroot ./teeworlds_srv
启动客户端
$ xhost +local:
$ DISPLAY=$DISPLAY LIBGL_ALWAYS_SOFTWARE=1 ruyi-qemu -cpu rv64 -L ~/oe-sysroot ./teeworlds
(留了个小问题,目前还没有解决音频的问题,后续会补充)

