我正在编写一个代码(128位)的幂(4位)和一个除法器,以查找(128位)次幂(4位)和变量(4位)的余数。我使用重复加法找到第一个运算,然后使用重复减法找到余数。我用循环来做同样的事情。对于(128位)的(4位)幂,for循环的上限确实很高,并且仿真给出了错误。仿真突然停止,说明该过程已终止。并且在模块电源(Windows XP上的Xilinx 12.1)中发现了致命错误。 在Windows 10的xilinx 14.7上弹出此错误:
错误:可移植性:3-此Xilinx应用程序的内存不足或 遇到内存冲突。当前的内存使用情况是3085052 kb。您可以尝试增加系统的物理或虚拟 记忆。如果您使用的是Win32系统,则可以增加 使用/ 3G开关将应用程序内存从2GB扩展到3GB boot.ini文件。有关更多信息,请参考Xilinx。 回答记录#14932。有关此问题的技术支持,请 访问http://www.xilinx.com/support。
模拟器已意外终止。请查看ISim日志(isim.log)了解详细信息。 有什么有效的方法可以避免此问题?请帮忙。 寻找力量:
entity power is
Port ( mes : in STD_LOGIC_VECTOR (207 downto 0);
d : in STD_LOGIC_VECTOR (11 downto 0);
outt : out STD_LOGIC_VECTOR (2007 downto 0);
clk : in STD_LOGIC);
end power;
architecture Behavioral of power is
signal mes1:unsigned (207 downto 0);
signal d1:unsigned (11 downto 0);
signal mes3:unsigned (2007 downto 0);
begin
process(clk)
begin
if(clk'event and clk='1') then
mes1<=unsigned(mes);
d1<=unsigned(d);
end if;
end process;
process(clk,mes1)
variable varr:unsigned (2007 downto 0);
variable cnt,cnt1: unsigned (207 downto 0);
variable mes2: unsigned (2007 downto 0);
begin
cnt:=x"0000000000000000000000000000000000000000000000000001";
mes2:=x"0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000";
mes2(207 downto 0):=mes1;
if(clk'event and clk='1') then
for i in 0 to 90 loop
if(cnt<d1) then
varr:=x"0000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000";
cnt1:=x"0000000000000000000000000000000000000000000000000001";
for j in 0 to 150000 loop
if (cnt1<=mes1) then
varr:=varr+mes2;
cnt1:=cnt1+1;
end if;
end loop;
mes2:=varr;
cnt:=cnt+1;
end if;
end loop;
mes3<=mes2;
end if;
end process;
process(clk)
begin
if(clk'event and clk='1') then
outt<=std_logic_vector(mes3);
end if;
end process;
end Behavioral;
要找到其余部分:
entity div22 is
Port ( a : in STD_LOGIC_VECTOR (2007 downto 0);
b : in STD_LOGIC_VECTOR (7 downto 0);
remi : out STD_LOGIC_VECTOR (2007 downto 0);
clk : in STD_LOGIC);
end div22;
architecture Behavioral of div22 is
signal q:unsigned (11 downto 0);
signal a1,r:unsigned (2007 downto 0);
signal b1:unsigned (7 downto 0);
--signal i:STD_LOGIC_VECTOR (3 downto 0);
begin
process(clk)
begin
if(clk'event and clk='1') then
a1<=unsigned(a);
b1<=unsigned(b);
end if;
end process;
process(clk,a1,b1)
variable remo1,remo2: unsigned(2007 downto 0);
begin
remo1:=a1;
if RISING_EDGE(clk) then
for i in 0 to 150000 loop
remo2:=remo1;
if(remo2>=b1) then
remo1:=remo2-b1;
end if;
end loop;
r<=remo1;
end if;
end process;
process(clk,r)
begin
if RISING_EDGE(clk) then
remi<= std_logic_vector(r);
end if;
end process;
end Behavioral;
要找到提醒,for循环的上限确实很高。有什么有效的方法可以解决这个问题?请帮忙。
答案 0 :(得分:0)
在您的上下文中,最好的方法是不使用循环。
通常,为了获得最佳性能和可接受的实现区域大小,应使用状态实现(fsm)。您应该在频率(关键路径)和完成工作所需的周期数之间取得平衡。这是我的硕士论文中“全部除法的其余部分-余数”操作的基本实现(在Verilog中)。就我而言,问题是加法器太大。所以在我的最终版本中,添加实现是并行的-我使用了一些较小的加法器来获得更好的频率。该代码是“我的硕士论文”的RSA实现的一部分。
module div(a,n,clk,reset,R, ready); // a,b,n mniejszy rozmiar
// a mod n = R
parameter size=1024; // data length
parameter
A0 = 2'b00, // Reset.
A1 = 2'b01, // Find _n > _R.
A2 = 2'b10, // Calc.
A3 = 2'b11; // Ready - calc done.
input [size-1:0] a,n;
input clk,reset;
output ready;
output [size-1:0] R;
reg signed [size:0] _R;
reg [size:0] _n;
reg [size-1:0] tmp_r;
reg ready; // operation is done.
reg [11:0]i;
(*safe_implementation = "yes"*)// directive for XST
(* signal_encoding = "user" *) // directive for XST
(* fsm_encoding = "user" *) // directive for XST
reg [1:0] cs;
initial
begin
_R = 0;
_n = 0;
i = 0;
ready = 0;
tmp_r = 0;
cs = A0;
end
always @(posedge clk)
begin
if (reset)
begin
_R = a;
_n = n;
i = 0;
tmp_r= a;
ready = 0;
cs = A0;
end
else
begin
case(cs)
A0:
begin
cs = A1;
end
A1:
begin
_n = _n << 1;
i = i + 1;
if ( _n > _R )
begin
_n = _n >> 1;
_R = _R - _n;
cs = A2;
end
else
begin
cs = A1;
end
end
A2:
begin
if (i==0)
begin
cs = A3;
end
else
begin
_n = _n >> 1;
if (_R[size]==1'b0)
begin
tmp_r = _R; // Save last positiv number.
_R = _R - _n;
end
else
begin
_R = _R + _n;
end
i = i -1;
cs = A2;
end
end
A3:
begin
ready = 1'b1;
cs = A3;
end
default:;
endcase
end
end
assign R=tmp_r;
endmodule
您可以在“我的硕士论文”中找到更多技巧,以获得适用于您的上下文的更好的性能和区域优化(问题在于它是波兰语): https://www.researchgate.net/publication/332752272_Realizacja_wybranych_algorytmow_kryptograficznych_w_strukturach_FPGA_Smolinski_Lukasz
对不起,我的英语。