接口上的多重访问指针 编写的代码中,输入指针 d_i
和输出指针 d_o
在 RTL 中是作为 FIFO(或握手)接口实现的,目的是为了确保:
- 每次在 RTL 端口
d_i
上执行读取时,上游生产者模块都可提供新数据。 - 每次写入 RTL 端口
d_o
时,下游使用者模块都接受新数据。
通过标准 C/C++ 语言编译器来编译此代码时,针对每个指针的多重访问会减少为单次访问。就编译器而言,并无指示表明 d_i
上的数据在函数执行期间发生更改,仅限最终写入 d_o
的数据才相关。其他写入在函数完成时被覆盖。
Vitis HLS 与 gcc
编译器的行为相符,将这些读写最优化到单一读操作和单一写操作中。检验 RTL 时,每个端口上只有单一读写操作。
此设计的基本问题在于测试激励文件和设计无法对您期望的 RTL 端口实现方式进行建模:
- 您期望 RTL 端口在每次传输事务期间进行多次读写(并且可通过串流来输入和输出数据)。
- 测试激励文件仅提供单一输入值,并且仅返回单一输出值。按 接口上的多重访问指针 所示进行 C/C++ 语言仿真可显示如下结果,证明每次输入累加 4 次。同样的值读取一次,且每次都累加。这并非 4 次不同的读取操作。
Din Dout 0 0 1 4 2 8 3 12
为了使该设计能够多次读写 RTL 端口,请使用 volatile
限定符,如 接口上的多重访问指针 所示。volatile
限定符会告知 C/C++ 语言编译器和 Vitis HLS,不假定指针访问次数,且不将其优化掉。即数据为易变数据,可能更改。
volatile
限定符:- 阻止指针访问最优化。
- 生成的 RTL 设计会对输入端口
d_i
执行期望的 4 次读取,对输出端口d_o
执行 2 次写入。
即使使用 volatile
关键字,此编码样式(多次访问指针)仍存在函数和测试激励文件无法对多次独立的读写操作进行充分建模的问题。在此情况下,将执行 4 次读取,但只对相同数据读取 4 次。存在 2 次独立的写入,每次写入数据正确,但测试激励文件仅捕获最终写入的数据。
提示: 要查看中间访问,请使用
cosim_design -trace_level
以在 RTL 仿真期间创建追踪文件,并在相应的查看器中查看此追踪文件。多重访问易变指针接口可通过连线接口来实现。如果指定 FIFO 接口,Vitis HLS 会创建 RTL 测试激励文件以在每次读取时串流新数据。由于测试激励文件未提供新数据,因此 RTL 验证失败。测试激励文件也就无法对读写操作进行正确建模。