我在编译时实现了一些VHDL代码来导出FSM状态编码,可以通过Xilinx ChipScope读回。该功能经Xilinx ISE 14.7,iSim 14.7和Mentor Graphic的QuestaSim 10.2c测试。对于Altera FPGA,我的设计也可以通过替代顶层来合成,但Quartus II似乎在return line.all;
上有问题。Quartus II是否支持line.all?
的Quartus II(14.0)的错误消息:
- 错误(10351):在sata_PhysicalLayer.vhdl VHDL子程序体错误(504):函数 “dbg_GenerateEncodings” 并不总是返回一个值
- 错误(10346):debug.vhdl(47)处的VHDL错误:正式端口或参数“编码”必须具有实际值或默认值
- 错误(10657):sata_PhysicalLayer.vhdl(514)处的VHDL子程序错误:未能详细说明调用子程序“dbg_ExportEncoding”
在下面,我将描述我的代码。
VHDL代码
该设计使用3个功能导出的FSM状态编码:
- 编码当前本地FSM状态为二进制值 - > dbg_EncodeState
(的结果此函数连接到ILA端口) - 将本地FSM的所有状态转换为以分号分隔的字符串 - > dbg_GenerateEncodings
- 格式此字符串和写入它的元件成记号的文件 - > dbg_ExportEncoding
(该功能位于一个包中)
FSM声明:
TYPE T_STATE IS (
ST_HOST_RESET,
ST_HOST_SEND_COMRESET,
ST_HOST_SEND_COMRESET_WAIT,
[...]
ST_HOST_SEND_ALIGN,
ST_HOST_TIMEOUT,
ST_HOST_LINK_OK
);
-- OOB-Statemachine
SIGNAL State : T_STATE := ST_HOST_RESET;
SIGNAL NextState : T_STATE;
本地函数 - 每个实体功能:
function dbg_EncodeState(st : T_STATE) return STD_LOGIC_VECTOR is
begin
return to_slv(T_STATE'pos(st), log2ceilnz(T_STATE'pos(T_STATE'high) + 1));
end function;
function dbg_GenerateEncodings return string is
variable l : STD.TextIO.line;
begin
for i in T_STATE loop
STD.TextIO.write(l, str_replace(T_STATE'image(i), "st_host_", ""));
STD.TextIO.write(l, ';');
end loop;
return l.all;
end function;
全局函数 - 在debug.pkg中定义。VHDL:
impure function dbg_ExportEncoding(Name : STRING; encodings : string; tokenFileName : STRING) return BOOLEAN is
file tokenFile : TEXT open WRITE_MODE is tokenFileName;
variable cnt, base : integer;
variable l : line;
begin
report "Exporting encoding of '" & Name & "' to '" & tokenFileName & "'..." severity note;
report "dbg_ExportEncoding: '" & encodings & "'" severity note;
-- write file header
write(l, "# Encoding file for '" & Name & "'"); writeline(tokenFile, l);
write(l, "#"); writeline(tokenFile, l);
write(l, "# ChipScope Token File Version"); writeline(tokenFile, l);
write(l, "@FILE_VERSION=1.0.0"); writeline(tokenFile, l);
write(l, "#"); writeline(tokenFile, l);
write(l, "# Default token value"); writeline(tokenFile, l);
write(l, "@DEFAULT_TOKEN="); writeline(tokenFile, l);
write(l, "#"); writeline(tokenFile, l);
-- write state entires
cnt := 0;
base := encodings'left;
for i in encodings'range loop
if encodings(i) = ';' then
-- Leave the str_trim call in!
-- Otherwise, the new parser of ISE 14.7 fails to slice properly.
write(l, str_trim(encodings(base to i-1)));
write(l, character'('='));
write(l, raw_format_nat_hex(cnt));
writeline(tokenFile, l);
cnt := cnt + 1;
base := i+1;
end if;
end loop;
file_close(tokenFile);
return true;
end function;
代码的最后部分是在实体,它调用导出函数的伪常数:
CONSTANT test : boolean := dbg_ExportEncoding("OOBControl (Host)", dbg_GenerateEncodings, MY_PROJECT_DIR & "CSP/FSM_OOB_Host.tok");
用于辅助的功能:
- log2ceilnz( x)计算所需的位以二进制编码x符号
- to_slv转换前夕进入std_logic_vector;在这种情况下,整数SLV
- str_replace函数由一个字符串
- str_trim从str'low返回字符串到NUL
- raw_format_nat_hex的第一次出现替换的字符串格式的自然到一个十六进制字符串
附加说明:
所有vhdl文件都标记为VHDL-2008。
我的问题:
- 已经与一的Quartus环境line.all人的经验?
- 是否有解决方法?
- 有没有更好的解决方案来实现导出任务,而不使用恒定长度的字符串?
解决方法:
我包裹着我的功能dbg_GenerateEncodings在生成声明:
genXilinx : if (VENDOR = VENDOR_XILINX) generate
function dbg_GenerateEncodings return string is
[...]
constant test : boolean := dbg_ExportEncoding("OOBControl (Host)", dbg_GenerateEncodings, MY_PROJECT_DIR & "CSP/FSM_OOB_Host.tok");
begin
end generate;
相较于XST中,Quartus不检查生成块内的功能。
感谢您参阅此页面。我还研究了VHDL-2008的增强功能,但TEXTIO仍然不支持合成:( – Paebbels 2014-11-20 23:09:56
'translate on/off'会阻止Quartus抱怨,但也会阻止XST将枚举和其他人员写入磁盘。 TEXTIO在合成环境中的作用是将枚举编码导出为标记文件,因此ChipScope可以显示FSM和其他总线值作为令牌。我的第二个用例是导出基于PicoBlaze的SoC的地址映射。想要更改设备地址我只需更改一点 - >我的VHDL代码 – Paebbels 2014-11-20 23:39:52
Altera有一个名为[SignalTap](http://www.altera.com/literature/hb/qts/qts_qii53009.pdf)的内容。一般来说,越是可靠的设计,厂商之间的便携设计越简单,你就可以开发你自己的第三方系统,并在不同厂商之间使用,一般来说,这意味着一个接口机制可以跨目标与主机和设备驱动程序兼容为主机。 – user1155120 2014-11-21 00:01:33