feat(rockchip-rga): add the RK3588 RGA2 2D accelerator driver with /dev/rga and dma-heap#1388
Conversation
2ff62b8 to
5fe885e
Compare
There was a problem hiding this comment.
PR Review Summary
改动内容
本 PR 将仓库中仅有的 rockchip-rga dry-run 编码器升级为完整的 RK3588 RGA2 2D 加速器驱动,涵盖 95 个文件、约 +5536/-2716 行。核心改动:
- 驱动核心 (
drivers/gpu/rockchip-rga):重写为 OS 解耦的#![no_std]crate,包含 RGA2 MMIO 后端(命令编码、轮询完成、超时复位)、Copy/Fill/Blit 操作模型、13 种像素格式、RGA3 骨架。 - 平台接入 (
ax-driver/rga.rs,rockchip-soc):FDT 探测、时钟门控(hclk/aclk/clk)、CRU 软复位释放、电源域上电。正确跳过未验证的 RGA3 core,避免访问未时钟域的 MMIO 导致同步异常。 - 用户态接口:
/dev/rga实现 librga MultiRGA v1.3.1 全套 ioctl(BLIT_SYNC、IMPORT/RELEASE_BUFFER、REQUEST_CREATE/CONFIG/SUBMIT/CANCEL、版本查询),句柄按 task 隔离并在 fd 关闭时回收;/dev/dma_heap/{system,cma}提供真实物理连续 DMA 分配器,支持 mmap 锚定与 cache 同步。 - librga 互操作:
rga_req结构布局经编译期offset_of!+size_of断言(504 字节)与 LP64 C probe 交叉验证;GET_HW_VERSION上报(3,2,0x63318)让 librga 识别为 RGA_2_ENHANCE;旋转检测修正为rotate_mode != 0(此前cosa != 0拒绝了所有 librga blit)。
实现逻辑评价
驱动架构清晰:
backend::RgaBackendtrait 分离硬件代际,RGA2 后端实现完整的 MMU-off 命令编码,RGA3 标记为 Unsupported(IOMMU 依赖,合理延迟)。- 命令编码 (
command.rs) 有详尽的注释,说明每个寄存器位域与 vendor 参考实现的对应关系,包括 SRC1 fill format 追踪 dst 格式、PAT_CON/FADING_CTRL 与 vendor 一致的无条件写入。 - DMA coherency 正确处理:分配为 cached,提交前
sync_for_device(clean),完成后sync_for_cpu(invalidate),避免 stale cache line 抢写引擎输出。 - 安全性:
RGA_PHYSICAL_ADDRESS导入需CAP_SYS_RAWIO;拒绝 color-key/palette/Porter-Duff 等 RGA2 无法正确实现的特性(静默忽略会产出错误像素)。
测试覆盖
- 主机单元测试 59 项全部通过(本地
cargo test -p rockchip-rga验证):寄存器编码 golden 向量 20 项、librga ABI 结构布局与字段偏移 16 项、操作语义校验 13 项、CRC-32 / 格式映射 / 解析路径测试 10 项。 - QEMU ABI 测试 (
test-suit/starryos/qemu-smp1/system/rga-abi):C grouped system test,覆盖版本查询、句柄导入/释放、BLIT_SYNC 返回 ENODEV(证明解析链完整运行后才到达设备检查),通过 CITest starry aarch64 qemu / run_containerSUCCESS。 - QEMU dma-heap 测试 (
test-suit/starryos/qemu-smp1/system/dma-heap-dmabuf):覆盖 alloc/mmap/sync/lifetime(fd 先于 munmap 关闭后内存仍可读),通过 CI。 - 板级 selftest (
apps/starry/rga-selftest, OrangePi-5-Plus):fill/copy/resize/YUYV→RGB CSC,CRC + poison 哨兵分类,超时时 dump 引擎寄存器。board-orangepi-5-plus 配置正确,success_regex匹配终态 sentinel,fail_regex仅匹配灾难性故障。 rockchip-rga已纳入scripts/test/std_crates.csv白名单,随 CITest with std执行。
CI 状态
CI 全部通过(GraphQL statusCheckRollup.state = SUCCESS)。所有 run_host required checks 为 SUCCESS;run_container counterparts 为 SKIPPED(预期的 run_host/run_container 互斥矩阵行为)。本地 cargo fmt --check 无差异。
重复与重叠分析
- base branch:现有
rockchip-rga仅为 dry-run 编码器(仅PixelFormat::Abgr8888、无提交路径、无 librga ABI)。本 PR 替换并扩展,不是重复实现。 - open PRs:仅 #1390(lockdep RwLock 迁移)为不相关改动,无冲突风险。
- 无
[patch.crates-io]:所有依赖使用正常 workspace resolution。
测试放置
- QEMU ABI 测试正确放在
test-suit/starryos/qemu-smp1/system/rga-abi,通过 CMakeGLOB自动发现,install 到usr/bin/starry-test-suit,qemu-smp1 aarch64 构建配置已包含starry-kernel/rgafeature。 - dma-heap 测试放在
test-suit/starryos/qemu-smp1/system/dma-heap-dmabuf,同样自动发现。 - 板级 selftest 在
test-suit/starryos/board-orangepi-5-plus/rga-selftest和apps/starry/rga-selftest,分层正确。
无阻塞问题
未发现任何阻塞问题。PR 实现完整、测试充分、CI 通过、无冲突/重复/补丁问题。
Powered by mimo-v2.5-pro
ZR233
left a comment
There was a problem hiding this comment.
本次改动把 rockchip-rga 从 dry-run 编码器扩展为 RK3588 RGA2 后端,并接入 ax-driver、Starry /dev/rga 与 dma_heap。驱动核心本身的 host/std 覆盖和 rockchip-rga 分层方向我没有看到明显阻塞;当前 head 5dd485d37aa6361e2f91ad071311d3dc75b3e1ae 上 CI 也没有失败,cargo fmt --check 和 cargo xtask clippy --package rockchip-rga 在本地通过。
阻塞点是测试层级:PR 现在把 RGA2 硬件 bring-up 自测做成 starry-kernel/rga-selftest,并在 Starry initproc 前执行。这类测试覆盖的是可复用内核 RGA 驱动、DMA coherency、RK3588 power/clock/reset/platform 接入,不是 StarryOS 的 Linux 兼容行为。后续 RGA 继续增加 rotate/fence/IOMMU/multicore 等测试 feature 时,如果都按这个模式进 Starry kernel feature,会让 Starry 启动路径承载越来越多硬件驱动 bring-up 回归,维护边界会失控。
请把硬件驱动自测迁到 ArceOS app / test-suit/arceos 方向来做,参考现有 test-suit/arceos/{rust,c} 的 build/qemu 配置和 cargo xtask arceos test qemu 运行方式;或者提交一个真正的 RGA 用户态/librga 测试程序,放入 Starry 文件系统后通过 /dev/rga、/dev/dma_heap 验证用户态 ABI。Starry 侧保留 /dev/rga 的 ABI/QEMU no-device 测试是合理的,但不应通过 Starry 内核启动钩子来测试内核 RGA 驱动本体。
重复/重叠方面:当前 base 已有 rockchip-rga crate 和 Starry RGA app 依赖背景,但没有等价 RGA2 驱动实现;open PR 搜索中也没有同类 RGA 驱动 PR。这个 review 因测试位置和验证入口设计请求修改。
There was a problem hiding this comment.
PR Review — #1388 RGA2 驱动
改动内容
将 rockchip-rga 从 dry-run 编码器升级为完整的 RK3588 RGA2 2D 加速器驱动(+5257/-584 行,45 文件),涵盖:
- 驱动核心:
#![no_std]、OS 解耦,RGA2 MMIO 后端(命令编码、轮询完成、超时复位),Copy/Fill/Blit 操作,13 种像素格式,RGA3 骨架; - 平台接入:FDT 探测、时钟门控(hclk/aclk/clk)、CRU 软复位释放、电源域上电,RGA3 正确跳过;
- 用户态接口:
/dev/rga(librga MultiRGA v1.3.1 ioctl)、/dev/dma_heap/{system,cma}(物理连续 DMA 分配 + mmap + cache sync); - librga 互操作:
rga_req504 字节编译期断言、版本查询(3,2,0x63318)识别为RGA_2_ENHANCE、旋转检测修正为rotate_mode != 0; - 安全性:
RGA_PHYSICAL_ADDRESS导入需CAP_SYS_RAWIO;拒绝 color-key/palette/Porter-Duff 等 RGA2 无法正确实现的特性。
实现逻辑
架构设计清晰:backend::RgaBackend trait 分离硬件代际,RGA2 后端实现完整的 MMU-off 命令编码。命令编码有详尽的寄存器位域注释与 vendor 参考实现的对应关系。DMA coherency 正确处理(submit 前 sync_for_device clean,完成后 sync_for_cpu invalidate)。安全边界合理,解析链完整(resolve_buf → parse → validate → submit → poll)。
CI 状态
CI 全部通过(所有 run_host 必需检查为 SUCCESS,run_container 互斥对应为 SKIPPED,均为预期行为)。本地验证:cargo fmt --check 通过,cargo clippy -p rockchip-rga --all-features -- -D warnings 无警告,cargo test -p rockchip-rga 59 项测试全部通过。
先前 Review 处理
ZR233 在 commit 5dd485d37 上提出 CHANGES_REQUESTED,要求将 RGA2 硬件自测从 Starry 内核启动钩子迁出。作者在最新 commit b985b3032 中已响应:
- 移除
entry.rs的rga-selftestfeature 和rga_selftest::run()钩子; - 硬件验证改为用户态
test-suit/starryos/qemu-smp1/system/rga-blit-hw,QEMU 无设备时返回ENODEV/SKIP; - 保留
/dev/rga+/dev/dma_heap的 QEMU ABI 测试(rga-abi、dma-heap-dmabuf)。
测试层级问题已解决,Starry 内核启动路径不再承载任何 RGA 驱动 bring-up。
重复与重叠
- base branch:现有
rockchip-rga仅为 dry-run 编码器,本 PR 替换并扩展,不是重复实现。 - open PRs:#1430(x86 IRQ 重构)、#1431(block IRQ 拆分)均不相关,无冲突风险。
- 无
[patch.crates-io]:所有依赖使用正常 workspace resolution。
结论
无阻塞问题。驱动实现完整,测试覆盖充分,CI 通过,先前 review 意见已解决。
Powered by mimo-v2.5-pro
ZR233
left a comment
There was a problem hiding this comment.
复审当前 head b985b303227981ed8ee0f86bce46409f2088ed9a,仍需修改。
这版已经把前一轮指出的 Starry 内核启动钩子移除了,这是正确方向;但测试边界还没有收敛。当前 diff 仍新增了:
test-suit/starryos/qemu-smp1/system/rga-abi/test-suit/starryos/qemu-smp1/system/rga-blit-hw/test-suit/starryos/qemu-smp1/system/dma-heap-dmabuf/test-suit/starryos/board-orangepi-5-plus/rga-blit-hw/
这些仍然把 RGA / DMA heap 的硬件驱动 bring-up 和 ABI 覆盖放进 Starry test-suit。rga-blit-hw 尤其是在验证 RK3588 RGA2 驱动、DMA coherency、clock/reset/platform 接入,这不是 StarryOS Linux 兼容层本身的回归;后续如果继续增加 rotate/fence/IOMMU/multicore 等 feature,放在 Starry test-suit 会继续扩大 Starry 测试入口的职责。
请不要把这组 RGA 驱动测试继续放在 test-suit/starryos。建议改成以下二选一:
- 做成 ArceOS app / ArceOS 测试入口,按
test-suit/arceos现有方式验证可复用内核驱动和 RK3588 平台接入; - 提供真正的 RGA 用户态测试程序,通过 rootfs 放入 Starry 后只验证
/dev/rga、/dev/dma_heap的用户态 ABI,而不是把驱动 bring-up 作为 Starry test-suit case 维护。
当前 CI 里还有 Run clippy / run_host cancelled、Starry loongarch64 qemu failure,以及部分 Starry/self-hosted board cancelled;这些不作为本轮主要结论。主要阻塞仍是测试放置位置和验证入口设计。
|
收到,已按这一轮的测试边界调整(最新 commit da66ca2)。 把 RGA 驱动硬件 bring-up 用例从 Starry test-suit 移除:
这两个用例做的是真实 RGA2 blit + 像素回读校验(驱动命令编码 / DMA coherency / clock-reset-platform 接入),确实属于可复用内核驱动的硬件回归,不应作为 Starry test-suit case 维护。 Starry 侧只保留纯用户态 ABI 覆盖——即上一轮 review 认可的「/dev/rga / dma_heap 的 ABI 覆盖」,不含任何硬件 blit:
RGA2 驱动核心的正确性仍由 若后续需要保留真实硬件回归,会单独走 ArceOS app / 另:本次 push 一并带上两个与本轮 review 无关的驱动修复——dma-buf fd 上报 |
There was a problem hiding this comment.
PR Review — #1388 RK3588 RGA2 驱动(round 3 复审)
改动概览
将 rockchip-rga 从 dry-run 编码器升级为完整的 RK3588 RGA2 2D 加速器驱动,涉及 40 个文件、+4919/-584 行、82 个 commit。涵盖:
- 驱动核心(
drivers/gpu/rockchip-rga):#![no_std]OS 解耦 crate,RGA2 MMIO 后端(命令编码、轮询完成、超时复位),Copy/Fill/Blit 操作模型,13 种像素格式,RGA3 骨架; - 平台接入(
ax-driver/rga.rs、rockchip-soc):FDT 探测、时钟门控(hclk/aclk/clk)、CRU 软复位释放、电源域上电,RGA3 正确跳过; - 用户态接口:
/dev/rga(librga MultiRGA v1.3.1 ioctl 全套),/dev/dma_heap/{system,cma}(物理连续 DMA 分配 + mmap + cache sync); - librga 互操作:
rga_req504 字节编译期断言、版本查询(3,2,0x63318)→RGA_2_ENHANCE、旋转检测修正为rotate_mode != 0; - 安全性:
RGA_PHYSICAL_ADDRESS导入需CAP_SYS_RAWIO,拒绝 color-key/palette/Porter-Duff。
实现质量
代码架构清晰,分层合理:
backend::RgaBackendtrait 分离硬件代际,RGA2 完整实现 MMU-off 命令编码,RGA3 标记 Unsupported(合理延迟);- 命令编码注释详尽,每个寄存器位域均标注 vendor 参考实现的对应关系;
- DMA coherency 正确:submit 前
sync_for_deviceclean,完成后sync_for_cpuinvalidate; - 安全边界合理:解析链完整(
resolve_buf → parse → validate → submit → poll),handle 按 task 隔离并在 fd 关闭时回收。
ZR233 review 反馈处理
- Round 1(commit
5dd485d37a):要求移除 Starry 内核启动钩子 → 作者在b985b30322响应,迁为用户态测试; - Round 2(commit
b985b30322):仍要求移除rga-blit-hw硬件 bring-up 测试 → 作者在最新da66ca2d1b完整响应:- 移除
test-suit/starryos/qemu-smp1/system/rga-blit-hw - 移除
test-suit/starryos/board-orangepi-5-plus/rga-blit-hw - 保留纯用户态 ABI 测试(
rga-abi:版本查询/句柄 import/release/无设备 ENODEV;dma-heap-dmabuf:alloc/mmap/lifetime/sync),不含任何硬件 blit
- 移除
当前 test-suit/starryos 下的 RGA 测试已收敛为纯 ABI 覆盖,不涉及驱动 bring-up。ZR233 提出的测试职责边界问题已在最新 commit 中解决。
本地验证
cargo fmt --check:通过cargo clippy -p rockchip-rga --all-features -- -D warnings:无警告cargo test -p rockchip-rga:60 项全部通过(寄存器编码 golden 向量 20 项、librga ABI 结构布局与字段偏移 16 项、操作语义校验 13 项、CRC-32 / 格式映射 / 解析路径测试 11 项)
CI 状态
Fork CI 最新 run(da66ca2d1b)因 Docker pull 基础设施问题失败(Docker pull failed with exit code 1),非代码问题。rcore-os 上无 check runs 配置。
重复/重叠
- base branch 现有
rockchip-rga仅为 dry-run 编码器,本 PR 替换并扩展,非重复; - 无
[patch.crates-io]; - 无相关 open PR 冲突。
结论
驱动实现完整、测试覆盖充分、前三轮 review 意见均已响应解决。建议合入。
Powered by mimo-v2.5-pro
…ion and capabilities
新增一个专用 build wrapper `test-suit/starryos/qemu-rga`(仅 aarch64,启用 `rga`, 从而同时带出 `/dev/dma_heap`),把 `/dev/rga` 的用户态 ABI 生命周期回归放在 `qemu-rga/system/rga-lifecycle`。共享的 `qemu/build-*.toml` 保持不含 `rga`;其他 架构在该 wrapper 下发现不到用例,不受影响。 QEMU virt 无 RGA2 硬件:handle 解析成功后 `RGA_BLIT_SYNC` 会走到设备检查返回 ENODEV,而 handle 查不到则在解析前就返回 EBADF——用 “ENODEV 而非 EBADF” 判定 lookup 是否命中,无需硬件即可验证。两个确定性用例: - A(同一 fd 跨线程):主线程 import 得到 handle,兄弟线程用同一 fd 对该 handle 做 blit(应 ENODEV)并 release(应成功),验证按 tgid 归属的 handle 在同进程各 线程间可见。 - B(两个独立 open):同进程开 fd_a、fd_b 各自 import,关闭 fd_a 后 fd_b 的 handle 仍应解析成功(ENODEV,而非 EBADF)。修复前 close 会回收整个进程的 handle,此用 例即返回 EBADF;修复后仅在最后一个 open description 关闭时回收,用例通过。
|
最新两项修改中,跨线程问题和“关闭一个 fd 误清理另一个 fd”的直接现象已经处理,专用测试配置也避免了影响通用 QEMU 构建。不过还需要继续调整以下两点。 1. 请实现真正的 per-open RGA session。 当前 此外,fork 会暴露更明确的问题:Starry fork 复制的是同一个 Orange Pi 6.1 RK35xx 的 RGA3 驱动是在每次
这样不需要扩展通用 2. 不需要增加 RGA QEMU 测试,请删除本轮新增的 QEMU 没有 RGA 设备,通过 建议新增
成功终态统一为: 失败统一为: 构建产物应是可整体复制到 rootfs 的 bundle: 可执行文件使用 同时请顺带按 Orange Pi RGA3 1.3.1 UAPI 对齐当前 ioctl:
本轮无需执行真机测试,提交前完成 smoke 的 aarch64 交叉编译、RPATH/依赖检查,以及现有 fmt、host test 和 Starry clippy 即可。 |
… RGA3 UAPI
生命周期改为正确的 open-file-description 语义(对齐 Linux RGA 的 file->private_data
与 Starry 现有的 usbfs per-open FileLike):节点 RgaDevice 不再持有任何 per-open 状态;
每次 open("/dev/rga") 在 fd_ops 中改造成一个 per-open RgaFile,内含该 open 的 handle /
request 表与 id 分配。dup/fork/SCM_RIGHTS 共享同一个 Arc<RgaFile> 从而自然共享 session,
独立 open() 得到独立 session;session 在最后一个引用 drop 时释放(RAII,即 release()
语义)。删除了 current_id()、open_counts 与所有 (pid, id) 键。
这修复了 fork 下的生命周期错误:此前 handle 按 tgid 归属,fork 复制同一个
Arc<FileLike> 而不再调用 open(),子进程 tgid 不同即无法解析父进程用继承 fd 导入的
handle,且最后一个引用由子进程关闭时按子 tgid 清理会漏回收父进程的表项。
同时按 RGA3 UAPI 源码对齐 ioctl 行为:
- buffer pool 上限 40(RGA_BUFFER_POOL_SIZE_MAX)、request task 上限 256
(RGA_TASK_NUM_MAX);
- CONFIG/SUBMIT/CANCEL 均要求 request id 已存在,否则返回 EINVAL;CANCEL 未知 id 不再
静默成功;SUBMIT 原子地取走请求(并发同 id 只跑一次);
- RGA_GET_VERSION 写回完整 16 字节;SUBMIT 遇 async(sync_mode == RGA_BLIT_ASYNC)
显式返回 unsupported;
- 保留 EFAULT 写回失败时的 handle/request 回滚;RELEASE 未知 handle 返回 ENOENT。
(AxError 无 EFBIG,超限统一返回 EINVAL。)
新增回归 C(fork):父进程 import 得到 handle,fork 后子进程用继承的 fd 解析该 handle 应成功(ENODEV,而非查不到的 EBADF),证明子进程与父进程共享同一 per-open session;子 进程退出后父进程的 handle 仍有效,证明 session 仅在最后一个引用关闭时才回收。这正是按 tgid 归属时无法通过的场景。回归 B 的说明也相应更新为「两个独立 open = 两个独立 session」。
|
第七轮的两点已处理(commit 1. 改为真正的 per-open session(不再用 tgid + open_counts)。 参照 Linux RGA 的 您指出的 fork 问题据此修复:子进程通过继承 fd 共享父 session、可解析父进程导入的 handle;父/子中最后一个引用关闭时才回收。已补一条 fork 回归覆盖(子进程解析父 handle、子退出后父 handle 仍有效)。 2. ABI 对齐(按 RGA3 UAPI 源码核对)。
3. 关于删除 本地已验证:aarch64 构建、fmt、 |
There was a problem hiding this comment.
审查结论
本 PR 将现有 rockchip-rga dry-run 骨架扩展为 RK3588 RGA2 MMU-off 驱动,完成 FDT/power/clock/reset 接入,并在 Starry 提供 /dev/rga、dma-heap 与 librga ioctl;新增的 grouped QEMU 用例覆盖 ABI、导入/释放和 fd/open-file-description 生命周期。驱动核心与 OS glue 的分层方向清晰,但当前 dma-buf 导入缺少访问范围约束,暂不能合入。
影响与既有反馈
该功能大部分由 feature/platform 配置隔离,不改变未启用 RGA 的通用路径;启用 /dev/rga 后,导入缓冲、cache sync 和 MMU-off 物理 DMA 属于新的安全边界。此前关于 task/tgid 归属、独立 open 互相影响以及 dup/fork 生命周期的意见是合理的;当前 head 已改成 per-open RgaFile,并增加 sibling thread、独立 open、fork 共享 open-file-description 回归,原问题已解决。写回失败回滚等旧意见也已处理。当前仍有一项新的阻塞安全问题,见 inline 评论。
测试与验证
- 组织仓库中当前 head
2a5c142d0244bde036048723454c8aa7d7049db9的 Actions run29490828041为成功;格式、clippy、std test、Starry aarch64 QEMU 等相关run_host/run_container实际执行项成功,互斥 counterpart 与 publish 项的 skipped 属预期矩阵行为,未发现 PR 导致的 CI 失败。 - 本地
cargo fmt --check:通过。 - 本地
cargo test -p rockchip-rga --all-features:60 项通过。 - 本地
cargo xtask clippy --package rockchip-rga、cargo xtask clippy --package starry-kernel:通过。 - 新测试位于当前 grouped system 结构下并由对应 QEMU 配置选择;current-head CI 已执行 Starry aarch64 QEMU,因此未重复本地运行完整 QEMU。现有测试尚未覆盖“小 dma-buf + 大几何”的拒绝路径,这正是本轮安全缺口。
重复、冲突与规范
origin/dev 仅有此前的 RGA dry-run 骨架,没有真实提交或 /dev/rga 等价实现,本 PR 不是重复实现;未确认到功能重复的开放 PR,也没有 [patch.crates-io]。基于准备好的 origin/dev 进行 merge-tree 检查无冲突。仓库当前 checkout 未提供 book/guideline/starry/syscall.md,所以无法直接按该文档复核 ioctl ABI;本轮按代码质量规范、驱动/DMA 边界及已有 ABI 测试检查。
修复 inline 的 dma-buf 边界校验并补充可在硬件提交前确定失败的负向回归后,可继续复审。
Powered by gpt-5.6-sol
| let obj = resolve_contiguous_dmabuf(ext.memory as c_int) | ||
| .ok_or(VfsError::BadFileDescriptor)?; | ||
| ImportedBuf { | ||
| phys_addr: obj.phys_base() as u64, |
There was a problem hiding this comment.
【阻塞|安全:DMA 越界】这里导入 dma-buf 时只保存了物理基址和生命周期引用,没有保存分配长度;后续 resolve_buf 也只返回基址,而 ImageDesc::validate 仅检查计算出的末地址不超过 4 GiB。用户可以导入一个 4 KiB dma-buf,再提交合法的 4096×4096 RGBA 几何,RGA2 在 MMU-off 模式下就会越过该 dma-buf 读写相邻物理内存,造成越权读取或内存破坏。当前 DmaBufFile 已持有 alloc.size,但 size() 仅在 rknpu feature 下开放,证明该边界信息存在却没有传到 RGA 路径。请让长度在 rga feature 下可用,把它保存在 ImportedBuf 并在提交前校验每个 RGB/Y/UV 平面的完整访问区间(含派生的 semiplanar UV 区间)都落在对应导入对象内;同时增加“小缓冲区 + 大几何必须在触发硬件前失败”的回归。
There was a problem hiding this comment.
已修复此处的 DMA 越界(commit 42cf45dcb、3c2ce4d3f,已 push)。
DmaBufFile::size()现在在rgafeature 下可用;导入时把字节长度存进ImportedBuf(RGA_DMA_BUFFER记 dma-buf 长度;rawRGA_PHYSICAL_ADDRESS已受 CAP_SYS_RAWIO 限制、由特权调用方担保,记为无界)。- 提交前、在
get_list/ 触碰硬件之前,对每个平面做边界校验:新增ImageDesc::plane_extents()给出各平面从基址起的字节区间(luma/RGB 用stride*height,semiplanar chroma 用stride*chroma_rows),逐平面校验其落在对应导入缓冲[base, base+len)内;派生的 semiplanar UV(紧随 luma、同一缓冲)与单独导入的 chroma 分别处理。越界返回 EINVAL,不下发硬件。 - 新增回归 D:导入 4 KiB 缓冲、提交 512×512 RGBA(需 1 MiB)在硬件前以 EINVAL 拒绝;同缓冲的 16×16 仍能到设备检查(ENODEV),证明仅拒绝越界项。另加
plane_extentshost 单测。
本地验证:aarch64 构建、fmt、rockchip-rga host 单测 61、Starry clippy(22 检查),以及在 QEMU 跑通 qemu-rga/system(A/B/C/D 全过,23 断言)。
|
可先不加测例,我会在稍后增加 rga smoke 测试,放到板子中 |
…re RGA submit RGA2 runs MMU-off, so the engine DMAs the exact physical addresses it is programmed with. The import path saved only a buffer's physical base and lifetime ref, not its length, and `ImageDesc::validate` only bounded the end address against 4 GiB — so a small imported dma-buf paired with a large geometry (e.g. a 4 KiB buffer and a 4096x4096 RGBA blit) let the engine read/write past the buffer into adjacent physical memory. - Expose `DmaBufFile::size()` under the `rga` feature (was `rknpu`-only), so the RGA path can see each imported buffer's byte length. - Store the length in `ImportedBuf` (dma-buf length for `RGA_DMA_BUFFER`; `u64::MAX` for a raw `RGA_PHYSICAL_ADDRESS` import, which is already CAP_SYS_RAWIO-gated and owned by the privileged caller) and thread it through `resolve_buf`. - Add `ImageDesc::plane_extents()` (luma/RGB `stride*height`, semiplanar chroma `stride*chroma_rows`) and, before touching hardware, verify every plane the engine will address — including a derived semiplanar UV plane inside the luma buffer and a separately imported chroma plane — stays within its imported buffer `[base, base+len)`. Out-of-range geometry is rejected with EINVAL before submit.
回归 D:导入一个 4 KiB dma-buf,提交 512x512 RGBA(需 1 MiB)必须在触碰硬件前以 EINVAL 拒绝;同一缓冲上 16x16 的几何仍能走到设备检查(QEMU 无 RGA2 → ENODEV),证明 只有越界项被拒绝、边界校验不误伤合法请求。
There was a problem hiding this comment.
本 PR 将 rockchip-rga 从 dry-run 编码器扩展为 RK3588 RGA2 驱动,包含 RGA2 命令编码、操作/格式与 librga ABI 解析、ax-driver 的时钟/复位/电源域接入,以及 Starry /dev/rga 的句柄和请求 ioctl 路径;RGA3 明确保留为不支持的骨架。改动主要集中在 RGA 驱动及其 StarryOS glue,现有其他设备接口未见不兼容影响;RGA2 硬件 bring-up 自测已从 Starry 启动路径和 test-suit 移除,符合此前测试边界意见。
验证:cargo fmt --all -- --check 通过;cargo test -p rockchip-rga 通过(61 项);cargo clippy -p rockchip-rga --all-targets -- -D warnings 通过。当前 head 没有可用的 GitHub check runs,因此未将缺失的远程检查误判为通过或失败。已阅读此前 review/issue 评论:关于将硬件自测移出 Starry 启动钩子、共享 dma-heap/clock-reset 接入、写回 fault 回滚及与 dev 冲突的意见,当前 head 已相应处理;未发现仍然合理且未解决的阻塞问题。剩余硬件板级行为仍依赖真实 RK3588 验证,但 host 覆盖了寄存器编码、ABI 布局和操作校验,未见新的阻塞性测试缺口。
Powered by gpt-5.6-luna
|
请处理冲突 |
There was a problem hiding this comment.
审查结论
本 PR 将现有 rockchip-rga dry-run 编码器扩展为 RK3588 RGA2 后端,并接入 ax-driver 的时钟/复位/电源域初始化,以及 StarryOS 的 /dev/rga、共享 /dev/dma_heap 和 librga ioctl/请求路径;RGA3 仍明确拒绝。它会改变用户可见的 RGA ioctl、dma-buf 生命周期与直接物理 DMA 的安全边界,因此并非孤立改动。
此前关于硬件自测不应绑在 Starry 启动路径、每个 open-file-description 应有独立 handle session、以及小 dma-buf 不能被大几何越界 DMA 的意见均合理;当前实现的 RgaFile、生命周期 C 回归和提交前 bounds check 已相应处理。qemu-rga/system 的根 CMake/subcase 布局也符合 grouped C 约定;本地交叉 CMake 构建确认 rga-lifecycle 被安装到 usr/bin/starry-test-suit。
验证
cargo fmt --check:通过。cargo test --manifest-path drivers/gpu/rockchip-rga/Cargo.toml --all-features:61 项通过。cargo clippy --manifest-path drivers/soc/rockchip/rockchip-soc/Cargo.toml --all-features -- -D warnings与对应 82 项单测:通过。cargo clippy --manifest-path drivers/gpu/rockchip-rga/Cargo.toml --all-features -- -D warnings:失败,见行内评论;这是本 PR 引入 crate 的合并阻塞项。- 当前 head 的 check runs 为 success=29、skipped=29、cancelled=1;没有 failure。取消的是非本改动面的 AKA-00-SG2002 自托管板任务,相关 aarch64 QEMU 矩阵成功。由于本地 clippy 已失败,未将远程 CI 或仅 CMake 构建视为可合并证据。
基线仅有旧 RGA crate/编码器而没有等价 RGA2 驱动;以 rockchip-rga、/dev/rga、qemu-rga 和 dma_heap 搜索的开放 PR 未发现重复实现,命中的 RK3588 cpufreq 改动不重叠。
剩余两个阻塞问题:新增 crate 未通过项目要求的 -D warnings clippy,且 NV16(4:2:2 semiplanar)的非零 Y 裁剪会采用错误的 chroma 行偏移。修复并补齐 NV16 crop golden 覆盖后,请重新执行 clippy 与相应 QEMU case。
Powered by gpt-5.6-terra
| // SAFETY: the mutable slice is not retained across the device submission below. | ||
| { | ||
| let dbytes = unsafe { dst.cpu_bytes_mut() }; | ||
| for px in dbytes.chunks_exact_mut(4) { |
There was a problem hiding this comment.
【阻塞|验证】项目要求新增/修改 crate 必须通过 cargo clippy ... -D warnings。当前 HEAD 执行 cargo clippy --manifest-path drivers/gpu/rockchip-rga/Cargo.toml --all-features -- -D warnings 在本行(以及 81、224)报出 clippy::chunks_exact_to_as_chunks,因而该 crate 不能通过要求的合并检查。请按诊断改用 as_chunks_mut::<4>() / as_chunks::<4>() 并以同一命令验证。
There was a problem hiding this comment.
已修复(commit 7abc8dff7):selftest.rs 的 4 字节像素循环改用 as_chunks::<4>() / as_chunks_mut::<4>()。cargo clippy --manifest-path drivers/gpu/rockchip-rga/Cargo.toml --all-features -- -D warnings 现已通过。
| { | ||
| buf.set_register( | ||
| registers::DST_CB_BASE_ADDR, | ||
| rect_base(uv, dst_rect.x, dst_rect.y / 2, dst.stride_bytes, 1), |
There was a problem hiding this comment.
【阻塞|RGA2 4:2:2 crop 地址】这里对所有 semiplanar 格式都用 dst_rect.y / 2 计算 CbCr 行偏移,但 NV16 是 4:2:2 SP,色度垂直采样率为 1;非零 Y crop 的偏移应为 dst_rect.y * stride,而不是一半。否则 NV16 目标 crop 会写入错误的 chroma 行并产生颜色错位;源平面 280 行同样受影响。请按格式的垂直 chroma subsampling(NV12/NV21 为 2,NV16 为 1)计算,并加入覆盖源和目标非零 Y 的 NV16 command golden 测试。
There was a problem hiding this comment.
已修复(commit 58c1ab74e):新增 PixelFormat::chroma_v_subsampling()(NV12/NV21=2,NV16=1),src/dst 的 CbCr 行偏移改为 rect.y / chroma_v_subsampling(),NV16(4:2:2)因此使用完整 y、不再折半;ImageDesc::plane_extents/validate 也复用该 helper。补了覆盖 src 与 dst 非零 Y crop 的 NV16 command golden 测试(blit_nv16_cropped_src_uv_offset、blit_nv16_cropped_dst_uv_offset),host 单测 63 通过。
# Conflicts: # os/StarryOS/kernel/src/task/cred.rs
…iplanar crop The RGA2 command encoder computed the CbCr row offset for a cropped/placed rect as `rect.y / 2` for every semiplanar format. That is correct for 4:2:0 (NV12/NV21), whose chroma is half-height, but wrong for NV16 (4:2:2), whose chroma is full-height — a non-zero Y crop on an NV16 source or destination addressed the wrong chroma rows and produced a color shift. Add `PixelFormat::chroma_v_subsampling()` (2 for NV12/NV21, 1 for NV16) and divide the chroma row by it at both the src and dst CB base computations. `ImageDesc::plane_extents` and `validate` now use the same helper instead of open-coding the NV16 special case. Adds NV16 command golden tests covering a non-zero Y crop on both the source and destination.
…ll-features `cargo clippy --all-features -- -D warnings` (a required merge check) flagged `clippy::chunks_exact_to_as_chunks` in the selftest's 4-byte pixel loops. Use `as_chunks::<4>()` / `as_chunks_mut::<4>()`, which also lets the closures take the pixel as `&[u8; 4]` directly.
There was a problem hiding this comment.
本 PR 将 rockchip-rga 从 dry-run 编码器扩展为 RK3588 RGA2 后端,并接入 ax-driver 的电源/时钟/复位初始化和 StarryOS 的 /dev/rga、共享 dma-buf 生命周期及 librga ioctl 路径。它改变了用户可见 ioctl 的 errno、并发和缓冲区安全边界,并非孤立改动;RGA3 仍明确不支持。
此前评论均已审阅。硬件自测已移出 Starry 启动路径;写回 fault 的 handle/request 回滚、per-open-file-description session、dma-buf 平面边界检查,以及 NV16 非零 Y crop 的色度偏移和对应 golden 覆盖都已在当前 head 处理。当前没有发现重叠的开放 RGA 实现 PR。
验证:cargo fmt --check、rockchip-rga 的 cargo clippy --all-features -- -D warnings、63 个单测、rockchip-soc 的 clippy 和 82 个单测,以及 ax-driver 的 --no-default-features --features rga clippy 均通过;cargo check --manifest-path os/StarryOS/kernel/Cargo.toml --no-default-features --features rga 也通过。cargo xtask starry test qemu --target aarch64-unknown-none-softfloat --list 已发现 qemu-rga/system。完整 ax-driver --all-features clippy 被未改动的 rockchip-npu lint 阻塞,完整 host test 也受现有 axklib 链接符号限制,分别与本次 RGA 路径无关。
当前远程 checks 有一次 Axvisor self-hosted x86_64(VMX) failure,另外有预期的 skipped/cancelled matrix job;我没有将它们作为 RGA 通过的证据。当前阻塞问题是下方的 RGA 设备锁竞争被误报为 ENODEV。除真实 RK3588 板级像素结果仍需硬件验证外,修复后请增加竞争回归并重新运行专用 QEMU case。
Powered by gpt-5.6-terra
| // core on this board and has no RGA2 core (-> NoSuchDevice, blit fails). | ||
| let mut guard = devs | ||
| .iter() | ||
| .filter_map(|d| d.try_lock().ok()) |
There was a problem hiding this comment.
这里会把 try_lock() 的所有失败静默跳过。rdrive 在另一个请求持有实际 RGA2 时返回 UsedByOthers,于是已注册但忙碌的 RGA2 会走到下面的 NoSuchDevice,使第二个同步 BLIT_SYNC 看到 ENODEV(设备不存在)而不是等待/串行化;librga 可能因此把正常的瞬时并发误判为 RGA 不可用。请先定位 RGA2,再用能串行化的 lock() 或显式队列等待;若以后为非阻塞调用设计了路径,则应返回 EBUSY 而不是 ENODEV。同时补一个并发提交或受控锁持有的回归,断言锁竞争不会报 ENODEV。
There was a problem hiding this comment.
本 PR 将 rockchip-rga 从 dry-run 编码器扩展为 RK3588 RGA2 后端,并接入 ax-driver 的电源/时钟/复位初始化,以及 StarryOS 的 /dev/rga、dma-buf 导入和 librga ioctl 路径;RGA3 仍明确不支持。这会改变用户态 ioctl 的 errno、并发行为与 MMU-off DMA 的安全边界,并非孤立改动。
已审阅此前反馈。硬件自检已移出 Starry 启动流程;写回 fault 回滚、per-open-file-description session(含跨线程/fork 生命周期回归)、dma-buf 各平面边界校验,以及 NV16 非零 Y crop 色度偏移和 golden 覆盖均已在当前 head 处理。未发现重叠的开放 RGA 实现 PR。
本地验证:cargo fmt --check、rockchip-rga 的 cargo clippy --all-features -- -D warnings 和 63 个单测、rockchip-soc 的 clippy 和 82 个单测、ax-driver --no-default-features --features rga clippy,以及 starry-kernel --no-default-features --features rga clippy/check 均通过。cargo xtask starry test qemu --target aarch64-unknown-none-softfloat -c qemu-rga/system 已实际通过,--list 也发现该 case。辅助计划中的广泛 ax-driver/Starry all-features clippy 仍被未改动 rockchip-npu/src/task/op/matmul.rs:312 的 needless_late_init 阻断,all-features ax-driver host test 也受既有重复 axklib DMA symbol 阻断;两者与新增 RGA 路径无关,已单独记录。
远程 checks 当前有 Axvisor self-hosted x86_64(VMX) failure,以及 cancelled/skipped matrix 项;该 x86 Axvisor 任务不由本 PR 的 RGA/Starry aarch64 改动引起,未将其作为 RGA 通过证据。剩余阻塞问题是行内所述的设备锁竞争被误报为 ENODEV。真实 RK3588 板级像素结果仍是残余硬件验证风险。
Powered by gpt-5.6-terra
| // core on this board and has no RGA2 core (-> NoSuchDevice, blit fails). | ||
| let mut guard = devs | ||
| .iter() | ||
| .filter_map(|d| d.try_lock().ok()) |
There was a problem hiding this comment.
这里的 try_lock() 在另一条 BLIT_SYNC 正持有实际 RGA2 时会返回 UsedByOthers,但 .ok() 把该状态静默丢弃。若这是唯一的 RGA2,迭代随后落到 NoSuchDevice,使正常的并发同步提交返回 ENODEV、被用户态误判为硬件不存在。请先定位 RGA2 并用可串行化的 lock()/队列等待;若以后明确提供非阻塞语义,也应返回 EBUSY,而不是 ENODEV。同时增加受控锁竞争回归,断言竞争不会报设备不存在。
There was a problem hiding this comment.
已修复(commit 7ae304376):设备选择不再用 try_lock().ok() 静默丢弃 UsedByOthers。现在先 try_lock() 走无竞争快路径(并顺带跳过空闲的 RGA3 skeleton 而不阻塞),繁忙则退回阻塞 lock() 等待,从而对 RGA2 设备上的并发 blit 串行化,而不是把「繁忙」当作「不存在」。NoSuchDevice(ENODEV)因此只在根本没有 RGA2 core 时返回;将来若新增非阻塞提交路径,应在此返回 EBUSY。
关于回归:该竞争路径仅在真机可达——QEMU virt 无 RGA2 设备,get_list::<RockchipRga>() 为空,ioctl 在进入锁选择之前就返回 ENODEV,所以「锁竞争不报 ENODEV」的断言无法在 QEMU CI 中触发。它属于您计划补的板级 rga smoke 的范畴(并发两个 BLIT_SYNC、断言两者都成功而非其一得到 ENODEV);如需要我可以在该 smoke 里补上这条。
本地验证:aarch64 构建、fmt、Starry clippy(21 检查)、QEMU qemu-rga/system(23 断言全过)均通过。
… ENODEV The RGA2 device selection used `devs.iter().filter_map(|d| d.try_lock().ok())`, which silently dropped rdrive's `UsedByOthers`. When a concurrent `BLIT_SYNC` already held the single RGA2 device, it was skipped and the iterator fell through to `NoSuchDevice`, so a normal concurrent submit saw ENODEV — as if the hardware were absent — for what is really transient contention (librga can then wrongly conclude RGA is unavailable). Acquire the RGA2 device with `try_lock()` for the fast, uncontended path (which also skips idle RGA3 skeleton devices without blocking), then fall back to the blocking `lock()` to wait our turn on a busy device, serialising concurrent blits. `NoSuchDevice` is now returned only when no RGA2 core exists at all, never for a busy-but-present one. A future non-blocking submit path should return EBUSY here instead. The contention itself is board-only: on QEMU virt there is no RGA2 device, so `get_list` is empty and the ioctl returns ENODEV before the lock selection — the "lock contention must not report ENODEV" regression belongs in the on-board rga smoke.
There was a problem hiding this comment.
本 PR 将 rockchip-rga 从 dry-run 编码器扩展为 RK3588 RGA2 后端,并接入 FDT 时钟/复位/电源域、Starry /dev/rga、共享 /dev/dma_heap 以及 aarch64 专用 QEMU 生命周期用例。RGA2/RGA3 后端边界、MMU-off 缓冲区范围检查和按 open-file-description 持有 RgaFile 会话的方向清晰;RGA3 仍显式拒绝,未把未验证路径伪装成可用功能。
该变更会影响 Starry 用户态可观察的 ioctl、fd 的 dup/fork 共享与关闭生命周期、dma-buf 导入以及 RK3588 DMA/时钟路径,因而不是孤立重构。Starry ABI 准则适用;结构布局和命令值已在代码中按 PR 所述的 Rockchip Linux 6.1 MultiRGA ABI 固定,并需由可执行的用户态回归持续保护。
验证情况:当前 head 的组织 CI 为 completed 59 项(success 30、skipped 29;后者是 run_host/run_container 互斥矩阵和发布分支条件的预期跳过),无失败;其中 Test starry aarch64 qemu / run_container、Run clippy / run_host、Test with std / run_host 均成功。当前工作区本地通过 cargo fmt --all --check、cargo test -p rockchip-rga --all-features(63 项)、cargo xtask clippy --package rockchip-rga、cargo test --manifest-path drivers/soc/rockchip/rockchip-soc/Cargo.toml --all-features,以及 cargo check --manifest-path os/StarryOS/kernel/Cargo.toml --features rga 和 cargo check --manifest-path drivers/ax-driver/Cargo.toml --features rga。专用 case 由 cargo xtask starry test qemu --arch aarch64 -l 发现为 qemu-rga/system,其 CMake 配置和构建也通过;因当前 CI 已覆盖 aarch64 QEMU,本轮未重复运行完整 QEMU。
测试放置方面,当前的独立 build wrapper 没有污染共享 qemu 配置,system/CMakeLists.txt 与子用例的 CMakeLists.txt/src 布局符合 runner 约定,且失败标记能够使 wrapper 失败。此前关于把硬件 bring-up 移出 Starry 启动路径、以及将 session 从 task/tgid 改为 open-file-description 的意见,当前实现已实质处理。不过此前已被修复的用户指针写回回滚问题,其当前可执行回归在测试迁移时丢失,见内联评论;这是本次阻塞项。
重复/重叠检查:基线的 rockchip-rga 仅有不下发命令的实现,未提供等价 RGA2 后端或 /dev/rga ABI;以 RGA、rockchip-rga 和 /dev/rga 检索开放 PR,未发现需要依赖、重复或冲突的独立实现。未发现 [patch.crates-io] 覆盖。
请补充该 fault 回滚的确定性 QEMU 回归后重新请求审查。其余已知限制(RGA3、IOMMU、异步 fence 等)目前有显式拒绝或范围说明。
Powered by gpt-5.6-terra
| TEST_DONE(); | ||
| } | ||
|
|
||
| /* ---- Regression A: same fd, cross-thread handle visibility. ---- */ |
There was a problem hiding this comment.
阻塞|回归覆盖缺失。 这个专用 QEMU case 已覆盖跨线程、独立 open、fork 和缓冲区边界,但没有覆盖此前修复的 RGA_IOC_IMPORT_BUFFER / RGA_IOC_REQUEST_CREATE 写回用户指针失败回滚;当前 rga.rs 虽保留了 vm_write 失败后删除 handle/request 的代码,PR 讨论中也确认原先的只读页回归已在迁移时移除。这样该修复再次退化为“插入后不回滚”时,现有用例仍会全部通过,违反 bugfix 必须在未修复实现上失败的回归要求。
请在这里补回确定性负向用例:让 ioctl 输入仍可读、但输出字段所在页经 mprotect(..., PROT_READ) 变为不可写,断言返回 EFAULT;恢复页权限后,用预期的首个 handle 发起一次已验证请求(旧实现会解析到泄漏项并到达 ENODEV,修复后必须 EBADF),并对首个 request id 验证 CANCEL/SUBMIT 返回 EINVAL。这样才能同时证明两个表项确实被回滚,而不只是证明用户写回失败。
There was a problem hiding this comment.
审查结论:需要修改
本 PR 将 rockchip-rga 从 dry-run 编码器扩展为 RK3588 RGA2 后端,并接入 ax-driver 的电源/时钟/复位初始化,以及 StarryOS 的 /dev/rga、dma-buf 导入、librga ioctl 和每个 open-file-description 的 RgaFile 会话;RGA3 仍明确不支持。改动会影响用户可见 ioctl 的 errno、句柄生命周期和 MMU-off DMA 边界,因此不是孤立改动。
当前实现中,此前关于硬件自检移出 Starry 启动路径、per-open 会话(含跨线程/独立 open/fork)、dma-buf 平面边界、NV16 非零 Y crop 和设备锁竞争不得误报 ENODEV 的意见均已处理。qemu-rga/system 的根 CMake、子测例布局、安装目录和 success/fail 标记也符合当前 grouped C runner 约定。
验证:
- 当前 head 的组织 CI 为
success=30, skipped=29, failure=0;aarch64 Starry QEMU 检查成功,跳过项为 host/container 互斥矩阵或非适用项,没有发现由本 PR 引起的失败。 - 本地
cargo fmt --check、cargo clippy --manifest-path drivers/gpu/rockchip-rga/Cargo.toml --all-features -- -D warnings、cargo clippy --manifest-path drivers/ax-driver/Cargo.toml --no-default-features --features rga -- -D warnings、git diff --check以及新增 C 子测例的clang -fsyntax-only -Wall -Wextra -Werror -pthread均通过。 - helper 建议的
ax-driver --all-featuresclippy 会在未改动的drivers/npu/rockchip-npu/src/task/op/matmul.rs:312触发既有needless_late_init;该路径不在本 PR diff 中,已与 RGA 定向检查分开记录。
既有评论与测试覆盖: 当前用例已覆盖跨线程、两个独立 open、fork 和小 dma-buf 大几何的边界拒绝;不过下方写回 fault 回滚的修复尚无能够在旧实现失败、在当前实现通过的回归。该问题是当前未解决的阻塞项。
重复/重叠: 已检索 base 的旧 RGA dry-run 实现以及以 RGA、/dev/rga、qemu-rga 为关键词的开放 PR;没有发现等价或冲突的 RGA2 实现。未发现 [patch.crates-io]。
请补齐行内所述的负向回归并重新运行专用 QEMU case。真实 RK3588 板级像素/并发行为仍是后续硬件验证风险,但不是本轮额外阻塞点。现有请求的 elliott10、ZCShou、ZR233 已覆盖驱动和 test-suit 跟进,未改动 reviewer 元数据。
Powered by gpt-5.6-terra
| TEST_DONE(); | ||
| } | ||
|
|
||
| /* ---- Regression A: same fd, cross-thread handle visibility. ---- */ |
There was a problem hiding this comment.
【阻塞|bugfix 回归缺失】这里的 A–D 只覆盖会话生命周期和 DMA 范围,没有覆盖 RGA_IOC_IMPORT_BUFFER、RGA_IOC_REQUEST_CREATE 的用户写回 fault 回滚。内核路径虽在 vm_write 失败后删除刚插入的 handle/request,但若回归为“不回滚”,这些用例仍会全部通过,违反 bug 修复必须有未修复版本会失败的确定性回归要求。请新增只读输出页用例:让输入仍可读、输出页经 mprotect(..., PROT_READ) 不可写,断言两个 ioctl 返回 EFAULT;恢复权限后验证预期的首个 handle 只能得到 EBADF、首个 request 的 CANCEL/SUBMIT 得到 EINVAL。旧实现会保留表项并分别到达 ENODEV/成功,从而能证明两条回滚路径而非仅证明写回失败。
背景
StarryOS 在 RK3588 平台上尚无 RGA(Raster Graphic Acceleration,2D 图形加速器)驱动。RKNN、UVC 等数据通路所需的色彩空间转换(CSC)、缩放、letterbox 等 2D 操作只能由 CPU 完成,开销显著(基准测试中 CPU 解码约 5.7 ms,而 RGA 硬件路径约为 1 ms 量级)。仓库中既有的
rockchip-rgacrate 仅为一个不下发命令、无法实际执行的 dry-run 编码器;/dev/rga尚未提供,/dev/dma_heap亦为桩实现。本 PR 在真实 RK3588 硬件上完成 RGA2 的完整 bring-up,并通过
/dev/rga(兼容厂商 librga)向用户态开放。改动
驱动核心(
drivers/gpu/rockchip-rga,#![no_std],与 OS 解耦)平台接入(
ax-driver/rockchip-soc/rdrive)StarryOS 用户态接口
/dev/rga:实现RGA_BLIT_SYNC、RGA_IOC_IMPORT_BUFFER/RELEASE_BUFFER句柄接口、版本查询与RGA_IOC_REQUEST_SUBMIT;解析 librga 的rga_req;句柄按 task 隔离,并在 fd 关闭时回收对应 task 的句柄与请求;/dev/dma_heap/{system,cma}:物理连续 DMA 缓冲分配器,导出 dma-buf fd,支持 mmap 锚定与 cache 同步。librga 互操作
此为在真实硬件上跑通的关键改动:
RGA_IOC_GET_HW_VERSION上报 RK3588 RGA2 的分类键(major, minor, revision) = (3, 2, 0x63318);librga 的rga_get_info()据此将其识别为RGA_2_ENHANCE,从而放行 YUYV_422 输入与 CSC 能力;parse()仅在存在实际旋转(rotate_mode != 0)时拒绝请求。librga 对非旋转 blit 会以单位矩阵填充旋转参数(sina = 0、cosa = 0x10000,即 16.16 定点表示的 cos 0°),此前以cosa != 0判定旋转会拒绝掉每一个 librga blit。安全与健壮性
RGA_PHYSICAL_ADDRESS方式导入缓冲需要CAP_SYS_RAWIO:裸物理地址会使 MMU-off 的 RGA DMA 引擎访问任意物理内存(内核或其他进程),非特权进程应改用 dma-buf fd 导入(其物理范围由内核掌握);验证
rockchip-rga已纳入 std-test 白名单,随 CI 执行;test-suit/starryos/qemu-smp1/system/rga-abi):覆盖版本查询、句柄导入/释放、BLIT_SYNC,以及无设备时的优雅降级(返回 ENODEV 而非 EBADF,证明句柄解析与 parse 先于设备判定执行);test-suit/starryos/board-orangepi-5-plus/rga-selftest):fill / copy / resize / YUYV→RGB CSC 像素正确,采用 CRC 与 poison 哨兵分类,并在超时时 dump 引擎寄存器用于诊断;cargo fmt与sync-lint均通过。范围与限制