来自 4 位进位预测 (CLA) 的 16 位加法器 - 来自 Block Generate and Propagate 的 Cout
16-bit adder from 4-bit Carry Look Ahead (CLA) - Cout from Block Generate and Propagate
我是 Verilog 新手。这是我到目前为止所做的,4 位 CLA 可以工作。然而,16 位(使用 4 位 CLA 的实例)没有。问题肯定在于设置来自块传播 (BP
) 和块生成 (BG
) 的 Cout_itermed
(中间进位)值。我创建了一个模块 carries
来处理这个问题。
在 Xilinx ISE 中,输出波形显示如下(未显示波形):
module CLA_4bit(
output [3:0] S,
output Cout, PG, GG,
input [3:0] A, B,
input Cin
);
wire [3:0] G,P,C;
assign G = A & B; //Generate
assign P = A ^ B; //Propagate
assign C[0] = Cin;
assign C[1] = G[0] | (P[0] & C[0]);
assign C[2] = G[1] | (P[1] & G[0]) | (P[1] & P[0] & C[0]);
assign C[3] = G[2] | (P[2] & G[1]) | (P[2] & P[1] & G[0]) | (P[2] & P[1] & P[0] & C[0]);
assign Cout = G[3] | (P[3] & G[2]) | (P[3] & P[2] & G[1]) | (P[3] & P[2] & P[1] & G[0]) |(P[3] & P[2] & P[1] & P[0] & C[0]);
assign S = P ^ C;
assign PG = P[3] & P[2] & P[1] & P[0]; // block generate
assign GG = G[3] | (P[3] & G[2]) | (P[3] & P[2] & G[1]) | (P[3] & P[2] & P[1] & G[0]); // block propagate
endmodule
module CLA_16bit(
output reg [15:0] S,
output reg Cout,
input [15:0] A, B,
input Cin
);
reg [3:0] BP, BG;
reg [3:0] Cout_itermed;
carries my_carries(BP, GP, Cin, Cout_itermed, Cout);
CLA_4bit cla0(S[3:0], Cout_itermed[0], BP[0], BG[0], A[3:0], B[3:0], Cin);
CLA_4bit cla1(S[7:4], Cout_itermed[1], BP[1], BG[1], A[7:4], B[7:4], Cout_itermed[0]);
CLA_4bit cla2(S[11:8], Cout_itermed[2], BP[2], BG[2], A[11:8], B[11:8], Cout_itermed[1]);
CLA_4bit cla3(S[15:12], Cout_itermed[3], BP[3], BG[3], A[15:12], B[15:12], Cout_itermed[2]);
Cout = Cout_itermed[3];
endmodule
module carries (
input [3:0] BP,
input [3:0] BG,
input Cin,
output reg [3:0] Cout_itermed,
output reg Cout
);
assign Cout_itermed[0] = BG[0] | (BP[0] & Cin);
assign Cout_itermed[1] = BG[1] | (BP[1] & Cout_itermed[0]);
assign Cout_itermed[2] = BG[2] | (BP[2] & Cout_itermed[1]);
assign Cout = Cout_itermed[3];
endmodule
当我 运行 4 位 CLA 的测试台时,波形确实显示(并且正确)。谁能解释问题出在 carries
或 CLA_16bit
模块中?
Cout_itermed
有两个驱动程序 - 第一个是 CLA_4bit
的 Cout
输出,第二个是 carries
的 Cout_itermed
输出模块。
这同样适用于 CLA_16bit
中的 Cout
(尽管它的两个驱动程序最终成为相同的信号,Cout_itermed[3]
,在 CLA_16bit
和 carries
中).
请记住,在 Verilog 中您描述的是物理电路,您永远不应将两个源(驱动器)连接到同一根导线 - 这就是我们短路的原因!
以下内容基于https://en.wikipedia.org/wiki/Lookahead_carry_unit#16-bit_adder。
您要做的是定义从 CLA_16bit
中的 Cout
端口删除 Cout_itermed[x]
(您可以让端口挂起)。您应该将确定 Cout_itermed[3]
(即 BG[3] | (BP[3]&Cout_itermed[2])
)的逻辑移动到 carries
模块。
我是 Verilog 新手。这是我到目前为止所做的,4 位 CLA 可以工作。然而,16 位(使用 4 位 CLA 的实例)没有。问题肯定在于设置来自块传播 (BP
) 和块生成 (BG
) 的 Cout_itermed
(中间进位)值。我创建了一个模块 carries
来处理这个问题。
在 Xilinx ISE 中,输出波形显示如下(未显示波形):
module CLA_4bit(
output [3:0] S,
output Cout, PG, GG,
input [3:0] A, B,
input Cin
);
wire [3:0] G,P,C;
assign G = A & B; //Generate
assign P = A ^ B; //Propagate
assign C[0] = Cin;
assign C[1] = G[0] | (P[0] & C[0]);
assign C[2] = G[1] | (P[1] & G[0]) | (P[1] & P[0] & C[0]);
assign C[3] = G[2] | (P[2] & G[1]) | (P[2] & P[1] & G[0]) | (P[2] & P[1] & P[0] & C[0]);
assign Cout = G[3] | (P[3] & G[2]) | (P[3] & P[2] & G[1]) | (P[3] & P[2] & P[1] & G[0]) |(P[3] & P[2] & P[1] & P[0] & C[0]);
assign S = P ^ C;
assign PG = P[3] & P[2] & P[1] & P[0]; // block generate
assign GG = G[3] | (P[3] & G[2]) | (P[3] & P[2] & G[1]) | (P[3] & P[2] & P[1] & G[0]); // block propagate
endmodule
module CLA_16bit(
output reg [15:0] S,
output reg Cout,
input [15:0] A, B,
input Cin
);
reg [3:0] BP, BG;
reg [3:0] Cout_itermed;
carries my_carries(BP, GP, Cin, Cout_itermed, Cout);
CLA_4bit cla0(S[3:0], Cout_itermed[0], BP[0], BG[0], A[3:0], B[3:0], Cin);
CLA_4bit cla1(S[7:4], Cout_itermed[1], BP[1], BG[1], A[7:4], B[7:4], Cout_itermed[0]);
CLA_4bit cla2(S[11:8], Cout_itermed[2], BP[2], BG[2], A[11:8], B[11:8], Cout_itermed[1]);
CLA_4bit cla3(S[15:12], Cout_itermed[3], BP[3], BG[3], A[15:12], B[15:12], Cout_itermed[2]);
Cout = Cout_itermed[3];
endmodule
module carries (
input [3:0] BP,
input [3:0] BG,
input Cin,
output reg [3:0] Cout_itermed,
output reg Cout
);
assign Cout_itermed[0] = BG[0] | (BP[0] & Cin);
assign Cout_itermed[1] = BG[1] | (BP[1] & Cout_itermed[0]);
assign Cout_itermed[2] = BG[2] | (BP[2] & Cout_itermed[1]);
assign Cout = Cout_itermed[3];
endmodule
当我 运行 4 位 CLA 的测试台时,波形确实显示(并且正确)。谁能解释问题出在 carries
或 CLA_16bit
模块中?
Cout_itermed
有两个驱动程序 - 第一个是 CLA_4bit
的 Cout
输出,第二个是 carries
的 Cout_itermed
输出模块。
这同样适用于 CLA_16bit
中的 Cout
(尽管它的两个驱动程序最终成为相同的信号,Cout_itermed[3]
,在 CLA_16bit
和 carries
中).
请记住,在 Verilog 中您描述的是物理电路,您永远不应将两个源(驱动器)连接到同一根导线 - 这就是我们短路的原因!
以下内容基于https://en.wikipedia.org/wiki/Lookahead_carry_unit#16-bit_adder。
您要做的是定义从 CLA_16bit
中的 Cout
端口删除 Cout_itermed[x]
(您可以让端口挂起)。您应该将确定 Cout_itermed[3]
(即 BG[3] | (BP[3]&Cout_itermed[2])
)的逻辑移动到 carries
模块。