Line 2... |
Line 2... |
//
|
//
|
// Filename: bigsmpy.v
|
// Filename: bigsmpy.v
|
//
|
//
|
// Project: OpenArty, an entirely open SoC based upon the Arty platform
|
// Project: OpenArty, an entirely open SoC based upon the Arty platform
|
//
|
//
|
// Purpose:
|
// Purpose: To multiply two 32-bit numbers into a 64-bit number. We try
|
|
// to use the hardware multiply to do this, but just what kind of
|
|
// hardware multiply is actually available ... can be used to determine
|
|
// how many clocks to take.
|
|
//
|
|
// If you look at the algorithm below, it's actually a series of a couple
|
|
// of independent algorithms dependent upon the parameter NCLOCKS. If your
|
|
// timing through here becomes a problem, set NCLOCKS to a higher number
|
|
// and see if that doesn't help things.
|
//
|
//
|
// Creator: Dan Gisselquist, Ph.D.
|
// Creator: Dan Gisselquist, Ph.D.
|
// Gisselquist Technology, LLC
|
// Gisselquist Technology, LLC
|
//
|
//
|
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
Line 34... |
Line 42... |
//
|
//
|
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
//
|
//
|
//
|
//
|
module bigsmpy(i_clk, i_sync, i_sgn, i_a, i_b, o_r, o_sync);
|
module bigsmpy(i_clk, i_sync, i_sgn, i_a, i_b, o_r, o_sync);
|
parameter CLOCKS = 1;
|
parameter NCLOCKS = 1;
|
input i_clk, i_sync, i_sgn;
|
input i_clk, i_sync, i_sgn;
|
input [31:0] i_a, i_b;
|
input [31:0] i_a, i_b;
|
output reg [63:0] o_r;
|
output reg [63:0] o_r;
|
output reg o_sync;
|
output reg o_sync;
|
|
|
generate
|
generate
|
if (CLOCKS == 1)
|
if (NCLOCKS == 1)
|
begin
|
begin
|
wire signed [31:0] w_sa, w_sb;
|
wire signed [31:0] w_sa, w_sb;
|
wire [31:0] w_ua, w_ub;
|
wire [31:0] w_ua, w_ub;
|
|
|
assign w_sa = i_a;
|
assign w_sa = i_a;
|
Line 60... |
Line 68... |
o_r <= w_sa * w_sb;
|
o_r <= w_sa * w_sb;
|
else
|
else
|
o_r <= w_ua * w_ub;
|
o_r <= w_ua * w_ub;
|
end
|
end
|
|
|
end else if (CLOCKS == 2)
|
end else if (NCLOCKS == 2)
|
begin
|
begin
|
|
reg r_sync;
|
reg signed [31:0] r_sa, r_sb;
|
reg signed [31:0] r_sa, r_sb;
|
wire [31:0] w_ua, w_ub;
|
wire [31:0] w_ua, w_ub;
|
|
|
|
initial r_sync = 1'b0;
|
always @(posedge i_clk)
|
always @(posedge i_clk)
|
begin
|
begin
|
r_sa = i_a;
|
r_sync <=i_sync;
|
r_sb = i_b;
|
r_sa <= i_a;
|
|
r_sb <= i_b;
|
end
|
end
|
|
|
assign w_ua = r_sa;
|
assign w_ua = r_sa;
|
assign w_ub = r_sb;
|
assign w_ub = r_sb;
|
|
|
always @(posedge i_clk)
|
always @(posedge i_clk)
|
begin
|
begin
|
o_sync <= i_sync;
|
o_sync <= r_sync;
|
if (i_sgn)
|
if (i_sgn)
|
o_r <= r_sa * r_sb;
|
o_r <= r_sa * r_sb;
|
else
|
else
|
o_r <= w_ua * w_ub;
|
o_r <= w_ua * w_ub;
|
end
|
end
|
|
|
|
|
end else if (CLOCKS == 5)
|
end else if (NCLOCKS == 5)
|
begin
|
begin
|
//
|
//
|
// A pipeline, shift register, to track our
|
// A pipeline, shift register, to track our
|
// synchronization pulse as it transits our pipeline
|
// synchronization pulse as it transits our pipeline
|
//
|
//
|