我有一个64位的导线向量;
wire [63:0] sout;
我想计算这些位的总和,或者等价地计算1的数量。
最好的方法是什么? (它应该是可合成的)
答案 0 :(得分:12)
我更喜欢使用for-loops,因为它们更容易扩展,并且需要更少的打字(从而更不容易出现拼写错误)。
SystemVerilog(IEEE Std 1800):
logic [$clog2($bits(sout)+1)-1:0] count_ones;
always_comb begin
count_ones = '0;
foreach(sout[idx]) begin
count_ones += sout[idx];
end
end
Verilog(IEEE Std 1364-2005):
parameter WIDTH = 64;
// NOTE: $clog2 was added in 1364-2005, not supported in 1364-1995 or 1364-2001
reg [$clog2(WIDTH+1)-1:0] count_ones;
integer idx;
always @* begin
count_ones = {WIDTH{1'b0}};
for( idx = 0; idx<WIDTH; idx = idx + 1) begin
count_ones = count_ones + sout[idx];
end
end
答案 1 :(得分:0)
“最佳”是相当主观的,但简单而明确的表述只是:
wire [6:0] sout_sum = sout[63] + sout[62] + ... + sout[1] + sout[0];
你可能会认真思考并想出能产生更好合成结果的东西,但这可能是一个良好的开端,直到计时工具说它不够好。
答案 2 :(得分:0)
以下解决方案使用一个函数来计算64位宽总线中置位(为高)位的总数:
function logic [6:0] AddBitsOfBus (
input [63:0] InBus
);
AddBitsOfBus[2:0] = '0;
for (int k = 0; k < 64; k += 1) begin // for loop
AddBitsOfBus[6:0] += {6'b00_0000, InBus[k]};
end
endfunction