1

我正在使用 Verilog 从 Lattice CPLD 构建 VGA 控制器。过去我对 Verilog 有过相当多的了解,但已经有一段时间了,而且我已经生疏了,而且控制显示器所需的同步线没有被驱动(检查 O.Scope),并且我不知道为什么不。

我试图在 Active-HDL 中模拟代码,但我收到一条奇怪的错误消息(无法为非阻塞事务分配内存)并收到计数器没有负载的警告(我相信在这种情况下我可以忽略? ) 代码如下:

module CtrlLines(NRST, CLK, H_SYNC, V_SYNC);
    input  wire CLK;        /*< CLK input from Top module   >*/
    input  wire NRST;       /*< Reset input from Top module >*/
    output reg  H_SYNC;
    output reg  V_SYNC;

    reg [10:0] h_counter;   /*< Tracks amount of pulses from CLK    >*/
    reg [10:0] v_counter;   /*< Tracks amount of pulses from H_SYNC >*/

    `define H_FRONT_PORCH   10'd95
    `define H_BACK_PORCH    10'd720
    `define H_COUNT_MAX     10'd800

    `define V_FRONT_PORCH   10'd2
    `define V_BACK_PORCH    10'd514
    `define V_COUNT_MAX     10'd528

    always @(negedge NRST, posedge CLK) begin
        if (!NRST) begin
            h_counter <= 10'b00;
        end
        else begin
            h_counter <= h_counter + 1'b1;
            case (h_counter)
                `H_FRONT_PORCH: H_SYNC <= 1;    /*< If the counter has reached Front Porch, go High >*/
                `H_BACK_PORCH : H_SYNC <= 0;    /*< If the counter has reached Back Porch, go Low   >*/
                `H_COUNT_MAX  : h_counter <= 0; /*< If the counter has reached Max, Reset   >*/
            endcase                             /*< Else, remain at current level           >*/
        end
    end

    always @(negedge NRST, negedge H_SYNC) begin
        if (!NRST) begin
            v_counter <= 10'b00;
        end
        else begin
            v_counter <= v_counter +1'b1;
            case (v_counter)
                `V_FRONT_PORCH  : V_SYNC <= 1;
                `V_BACK_PORCH   : V_SYNC <= 0;
                `V_COUNT_MAX    : v_counter <= 0;
            endcase
        end
    end
endmodule
4

3 回答 3

2

reg这段代码是有问题的,因为您对同一个( )有多个非阻塞分配h_counter。哪个将首先执行是不确定的,这会导致模拟竞争条件:

    h_counter <= h_counter + 1'b1;
    case (h_counter)
        `H_FRONT_PORCH: H_SYNC <= 1;    /*< If the counter has reached Front Porch, go High >*/
        `H_BACK_PORCH : H_SYNC <= 0;    /*< If the counter has reached Back Porch, go Low   >*/
        `H_COUNT_MAX  : h_counter <= 0; /*< If the counter has reached Max, Reset   >*/

我的猜测是你的综合工具也有这个问题。

default也许您的意思是在语句的子句中发生增量case

这同样适用于v_counter

于 2013-03-18T12:35:37.717 回答
1

我不知道它是否导致了问题,但有一条奇怪的线:

default         : V_SYNC = V_SYNC;

您在其中使用阻塞分配给自己分配 V_SYNC。

我建议删除这一行。

于 2013-03-17T19:31:56.237 回答
0

我会重申 Tim 的建议,即以不使用 H_SYNC 作为时钟的方式对 V_SYNC 部分进行编码。使用数据作为时钟(反之亦然)通常不受欢迎,因为大多数工具都不能很好地处理它。

For the main problem I might suggest that you verify that the H_SYNC and V_SYNC signals are properly routed to your top level and the IOs? Based on the warning I think your logic might be getting optimized out during syn. I don't see any major functional issues with what you posted.

于 2013-03-18T14:56:41.973 回答