Quartus II 在进行分析和综合时卡在 10%(我的内存 ram 模块 verilog 实现有问题吗?)
Quartus II get stuck at 10% while doing Analysis and Synthesis (something wrong with my memory ram module verilog implementatioon?)
我正在做一个系统,它从一个 txt 文件中获取一个由 57,600 个二进制数组成的数据,用一些算术模块处理它,然后将结果数据存储在 3 组输出内存 ram 上,每组由 57,600 个二进制数组成. ModelSim 工作正常,结果符合预期,但在 Quartus II 中编译时,它卡在 10% 并且几个小时内没有做任何事情,直到我停止进程。虽然,当我将实现的输出内存的大小时减少一位数时,它会在几秒钟内成功编译。输出内存的大小是 3 组 57.600 个 32 位二进制数。
我怀疑我没有正确实现内存,或者我正在执行的内存使用有问题,但我不确定,请提供任何建议?我正在寻找最简单直接的方法来实现它。
这是 ram 的模块
module RAM_OUT (clk, pix_val, w_mem_out, set_ram);
input clk;
input [2:0] w_mem_out;
input [31:0] pix_val;
input set_ram;
reg [15:0] addr_out; // tamano de 57600 datos
reg [31:0] mem_out1 [0:57599];
reg [31:0] mem_out2 [0:57599];
reg [31:0] mem_out3 [0:57599];
/////////// ram out ///////////////
always @ (posedge clk)
begin
if (set_ram)
addr_out = 0;
else
begin
if (w_mem_out == 1)
begin
mem_out1 [addr_out] = pix_val;
mem_out2 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 2)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 3)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out3 [addr_out] = pix_val;
addr_out = addr_out + 16'b0000000000000001;
end
else
addr_out = addr_out;
end
end
//////////////////////////////////
/*
module RAM_OUT (pix_val, w_mem_out, set_ram);
input [2:0] w_mem_out;
input [31:0] pix_val;
input set_ram;
reg [15:0] addr_out; // tamano de 57600 datos
reg [31:0] mem_out1 [0:57599];
reg [31:0] mem_out2 [0:57599];
reg [31:0] mem_out3 [0:57599];
/////////// ram out ///////////////
always @ (w_mem_out or set_ram)
begin
if (set_ram)
addr_out = 0;
else
begin
if (w_mem_out == 1)
begin
mem_out1 [addr_out] = pix_val;
mem_out2 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 2)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 3)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out3 [addr_out] = pix_val;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 4)
begin
mem_out1 [addr_out] = pix_val;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 5)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = pix_val;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 6)
begin
mem_out1 [addr_out] = pix_val;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = pix_val;
addr_out = addr_out + 16'b0000000000000001;
end
else
addr_out = addr_out;
end
end
//////////////////////////////////
*/
endmodule
我发现您的代码存在以下问题:
- 数据仅写入 mem_out1、mem_out2 和 mem_out3。从技术上讲,如果您根本不使用写入内存的数据,Quartus 可以优化它而不是综合那部分。
编码风格不太对。您可以尝试将 always 块中的“=”(阻塞语句)替换为“<=”(非阻塞)。
您可以参考Quartus Prime Handbook(第11.4.1 节)来了解如何编写HDL 来推断RAM。请注意,link 适用于 Quartus Pro 16.0,某些点可能不适用于您的 Quartus 软件版本。有关正确的详细信息,请参阅与您的 Quartus 版本对应的手册。
我正在做一个系统,它从一个 txt 文件中获取一个由 57,600 个二进制数组成的数据,用一些算术模块处理它,然后将结果数据存储在 3 组输出内存 ram 上,每组由 57,600 个二进制数组成. ModelSim 工作正常,结果符合预期,但在 Quartus II 中编译时,它卡在 10% 并且几个小时内没有做任何事情,直到我停止进程。虽然,当我将实现的输出内存的大小时减少一位数时,它会在几秒钟内成功编译。输出内存的大小是 3 组 57.600 个 32 位二进制数。
我怀疑我没有正确实现内存,或者我正在执行的内存使用有问题,但我不确定,请提供任何建议?我正在寻找最简单直接的方法来实现它。
这是 ram 的模块
module RAM_OUT (clk, pix_val, w_mem_out, set_ram);
input clk;
input [2:0] w_mem_out;
input [31:0] pix_val;
input set_ram;
reg [15:0] addr_out; // tamano de 57600 datos
reg [31:0] mem_out1 [0:57599];
reg [31:0] mem_out2 [0:57599];
reg [31:0] mem_out3 [0:57599];
/////////// ram out ///////////////
always @ (posedge clk)
begin
if (set_ram)
addr_out = 0;
else
begin
if (w_mem_out == 1)
begin
mem_out1 [addr_out] = pix_val;
mem_out2 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 2)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 3)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out3 [addr_out] = pix_val;
addr_out = addr_out + 16'b0000000000000001;
end
else
addr_out = addr_out;
end
end
//////////////////////////////////
/*
module RAM_OUT (pix_val, w_mem_out, set_ram);
input [2:0] w_mem_out;
input [31:0] pix_val;
input set_ram;
reg [15:0] addr_out; // tamano de 57600 datos
reg [31:0] mem_out1 [0:57599];
reg [31:0] mem_out2 [0:57599];
reg [31:0] mem_out3 [0:57599];
/////////// ram out ///////////////
always @ (w_mem_out or set_ram)
begin
if (set_ram)
addr_out = 0;
else
begin
if (w_mem_out == 1)
begin
mem_out1 [addr_out] = pix_val;
mem_out2 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 2)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 3)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out3 [addr_out] = pix_val;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 4)
begin
mem_out1 [addr_out] = pix_val;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = 32'b00000000_000000000000000000000000;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 5)
begin
mem_out1 [addr_out] = 32'b11111111_000000000000000000000000;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = pix_val;
addr_out = addr_out + 16'b0000000000000001;
end
else if (w_mem_out == 6)
begin
mem_out1 [addr_out] = pix_val;
mem_out2 [addr_out] = pix_val;
mem_out3 [addr_out] = pix_val;
addr_out = addr_out + 16'b0000000000000001;
end
else
addr_out = addr_out;
end
end
//////////////////////////////////
*/
endmodule
我发现您的代码存在以下问题:
- 数据仅写入 mem_out1、mem_out2 和 mem_out3。从技术上讲,如果您根本不使用写入内存的数据,Quartus 可以优化它而不是综合那部分。
编码风格不太对。您可以尝试将 always 块中的“=”(阻塞语句)替换为“<=”(非阻塞)。
您可以参考Quartus Prime Handbook(第11.4.1 节)来了解如何编写HDL 来推断RAM。请注意,link 适用于 Quartus Pro 16.0,某些点可能不适用于您的 Quartus 软件版本。有关正确的详细信息,请参阅与您的 Quartus 版本对应的手册。