无法实现简单的ALU

时间:2011-03-16 19:09:57

标签: verilog fpga xilinx synthesis

我在Verilog中描述了一个基本的8位ALU。我正在尝试实现设计,但我收到错误消息:

错误:NgdBuild:809 - 输出垫网'商'< 1>'有非法负载: 块Mmux_opcode [2] _GND_1_o_wide_mux_8_OUT81上的引脚I3,类型为LUT6

该设计执行以下操作,加法,减法,乘法,除法,AND,OR,XOR和XNOR。有趣的是,Xilinx XST无法合成除法器,除非被除数为2(基本上右移)。因此,为了解决这个问题,我使用了Xilinx Core Generator生成的CORE IP组件。它需要一个时钟(没有时钟使能或同步清零,并在大约20个左右的时钟周期后输出正确的商和余数。核心本身可以在核心生成器程序中的数学函数下找到。无论如何,这是我的代码:

`timescale 1ns / 1ps
module ALU8(A,B,opcode,clk,OUT);

// I/O
// We have two 16-bit inputs
input [7:0] A,B;
// The opcode determines our next operation
input [2:0] opcode;
// The processor clock
input clk;
// A 32-bit output
output [15:0] OUT;

// The inputs are wires
wire [7:0] A,B;
wire [2:0] opcode;

// The output is a register
reg [15:0] OUT;

// The quotient and remainder for tyhe divider
wire [7:0] quotient,remainder;
// Declare an internal dividing unit
Divider8 divider(.rfd(), .clk(clk), .dividend(A), .quotient(quotient), .divisor(B), .fractional(remainder));

// Define operation codes, there's only 9 so far
parameter   ADD = 3'b000;
parameter   SUB = 3'b001;
parameter   MUL = 3'b010;
parameter   DIV = 3'b011;
parameter   AND = 3'b100;
parameter   OR  = 3'b101;
parameter   XOR = 3'b110;
parameter   XNOR    = 3'b111;

// On the rising-edge of the clock
always @(posedge clk)
begin
    // The output is determined by the operation
    // Think of it as a MUX
    // A MUX8 will be added in later
    case(opcode)
        ADD: OUT <= A + B;
        SUB: OUT <= A - B;
        MUL: OUT <= A * B;
        DIV: OUT <= {quotient,remainder};
        AND: OUT <= A & B;
        OR:  OUT <= A | B;
        XOR: OUT <= A ^ B;
        XNOR: OUT <= A ~^ B;
        default: OUT <= 16'b0000000000000000;
    endcase
end
endmodule

显然我的代码太糟糕了,我的评论可能是错误的,但我只是Verilog的初学者。但是,我确实计划大大改进这些代码并为我添加更多操作来练习。模块本身可以成功合成并正确模拟,但我无法在任何FPGA上实现它。任何人都知道代码是否有问题,或Xilinx ISE(如常见的那样充满了bug),或者项目设置是否存在问题?

编辑:我对代码做了一些更改,以反映答案提供的建议。

2 个答案:

答案 0 :(得分:1)

这不是答案,但我认为这些提示可能会改善您的代码。

由于我没有Divider8模块,因此我无法编译您的代码,除非我注释掉divider实例。似乎错误消息与该实例有关。

对于许多综合工具initial块不可合成。由于我不使用xilinx,我无法对其支持发表评论。也许你可以删除initial块。

最好使用非阻塞分配(<=)来合成顺序逻辑。例如:

case(opcode)
    ADD: OUT <= A + B;
    SUB: OUT <= A - B;

您可以将常量重新编码为:

    default: OUT = {16{1'b0}};

答案 1 :(得分:1)

您是否在coregen项目中选择了“使用IO pad创建网表包装”选项?从错误来看,它听起来像Divider8核心有一个OBUF或类似的输出缓冲区驱动商输出。 OBUF只能驱动离开FPGA的信号。

另一个注意事项,虽然这与ngdbuild错误无关:通常非连接分配用于顺序块(“always @(posedge clk)”),例如, “OUT&lt; = A + B”。对此的简短解释是它延迟更新OUT信号,直到处理了当前时间的所有其他事件,这避免了模拟器中的竞争条件。