【发布时间】:2016-03-01 23:39:33
【问题描述】:
我想在 Verilog 上实现一个互易块,稍后将在 FPGA 上进行综合。输入应该是带符号的 32 位字长和 16 位小数长度。输出应具有相同的格式。
例子
输入:x ---> 输出 ---> 1/x
我已经使用内置的 IP 核分频器解决了这个问题。我想知道是否有一种优雅/替代的方法来解决这个问题,例如通过位移或 2 的补码加上一些异或研磨。
我已经使用 IP 内核来实现逆向,如手册中所述,但由于某种原因,我并不真正理解结果是错误的,需要向左移动 1。例如; 1 的倒数给出 0.5 。 2 的倒数得到 1。
下面是手册的一部分和我的测试台代码
测试台
module reciprical_tb;
// Inputs
reg clk;
reg [1:0] dividend;
reg [31:0] divisor;
// Outputs
wire rfd;
wire [1:0] quotient;
wire [31:0] fractional;
// Instantiate the Unit Under Test (UUT)
reciprical uut (
.rfd(rfd),
.clk(clk),
.dividend(dividend),
.quotient(quotient),
.divisor(divisor),
.fractional(fractional)
);
// clock
always begin
#5 clk = ~clk;
end
initial begin
// Initialize Inputs
clk = 0;
dividend = 2'b1; // 1
divisor = 2**16;; // = 1 when fraction length is 16bit
// Wait 100 ns for global reset to finish
#100;
// Add stimulus here :: Inverse of 2 should give 0.5
//$display("inv(%g) => %g || inv = %b",$itor(divisor)*2.0**-16, $itor(fractional)*2.0**-16, fractional); //gives zero
$monitor("inv(%d) => q = %d || inv = %b", divisor>>>16,fractional>>>16, fractional); //gives a wrong answer by a factor of 2
// Using the monitor i get inv(1) = 0.5 instead of 1.
#100;
end
endmodule
手册部分(第 4 页):
... 除法器可以用来实现X的倒数;这就是 1/X 函数。为此, 被除数位宽设置为 2 并选择小数模式。然后将股息输入绑定到 01 无符号或有符号运算,X 值通过除数输入提供。
使用的 IP 核心
【问题讨论】:
-
我建议将
#100;替换为#100ns;,这消除了对模拟时间设置的依赖。时钟源中的#5相同。