OpenCores
URL https://opencores.org/ocsvn/divider/divider/trunk

Subversion Repositories divider

Compare Revisions

  • This comparison shows the changes necessary to convert path
    /
    from Rev 1 to Rev 2
    Reverse comparison

Rev 1 → Rev 2

/trunk/bench/verilog/bench_div_top.v
0,0 → 1,163
/////////////////////////////////////////////////////////////////////
//// ////
//// Divider Testbench ////
//// ////
//// Author: Richard Herveille ////
//// richard@asics.ws ////
//// www.asics.ws ////
//// ////
/////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2002 Richard Herveille ////
//// richard@asics.ws ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer.////
//// ////
//// THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY ////
//// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED ////
//// TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS ////
//// FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR ////
//// OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, ////
//// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES ////
//// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE ////
//// GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR ////
//// BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF ////
//// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT ////
//// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT ////
//// OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE ////
//// POSSIBILITY OF SUCH DAMAGE. ////
//// ////
/////////////////////////////////////////////////////////////////////
 
// CVS Log
//
// $Id: bench_div_top.v,v 1.1.1.1 2002-10-29 20:29:08 rherveille Exp $
//
// $Date: 2002-10-29 20:29:08 $
// $Revision: 1.1.1.1 $
// $Author: rherveille $
// $Locker: $
// $State: Exp $
//
// Change History:
// $Log: not supported by cvs2svn $
// Revision 1.1.1.1 2002/03/26 07:25:12 rherveille
// First upload
//
//
 
`include "timescale.v"
 
module bench_div_top();
 
parameter z_width = 8;
parameter d_width = z_width /2;
 
parameter pipeline = 8;
 
parameter show_div0 = 0;
parameter show_ovf = 0;
 
//
// internal wires
//
reg clk;
 
integer z, d, n;
integer dz [pipeline-1:0];
integer dd [pipeline-1:0];
reg [d_width -1:0] di;
reg [z_width -1:0] zi;
 
integer sr, qr;
 
wire [d_width :0] s, q;
wire div0, ovf;
reg [d_width :0] sc, qc;
 
reg err_cnt;
 
//
// hookup division unit
//
div_su #(z_width) dut (
.clk(clk),
.ena(1'b1),
.z(zi),
.d(di),
.q(q),
.s(s),
.div0(div0),
.ovf(ovf)
);
 
always #2.5 clk <= ~clk;
 
always@(posedge clk)
for(n=1; n<=pipeline-1; n=n+1)
begin
dz[n] <= #1 dz[n-1];
dd[n] <= #1 dd[n-1];
end
 
initial
begin
$display("*");
$display("* Starting testbench");
$display("*");
err_cnt = 0;
 
clk = 0; // start with low-level clock
 
// wait a while
@(posedge clk);
 
// present data
for(z=-(1<<(z_width -1)); z < 1<<(z_width -1); z=z+1)
for(d=0; d< 1<<(z_width/2); d=d+1)
begin
zi <= z;
di <= d;
 
dz[0] <= z;
dd[0] <= d;
 
qr = dz[pipeline-1] / dd[pipeline-1];
qc = qr;
sr = dz[pipeline-1] - (dd[pipeline-1] * qc);
sc = sr;
 
if (!ovf)
if ( (qc !== q) || (sc !== s) )
begin
$display("Result error (z/d=%d/%d). Received (q,s) = (%d,%d), expected (%d,%d)",
dz[pipeline-1], dd[pipeline-1], q, s, qc, sc);
 
err_cnt = err_cnt +1;
end
 
if (show_div0)
if (div0)
$display("Division by zero (z/d=%d/%d)", dz[pipeline-1], dd[pipeline-1]);
 
if (show_ovf)
if (ovf)
$display("Overflow (z/d=%d/%d)", dz[pipeline-1], dd[pipeline-1]);
 
@(posedge clk);
end
 
// wait a while
repeat(20) @(posedge clk);
 
$display("*");
$display("* Testbench ended. Total errors = %d", err_cnt);
$display("*");
 
$stop;
end
 
endmodule
/trunk/rtl/verilog/div_uu.v
0,0 → 1,197
/////////////////////////////////////////////////////////////////////
//// ////
//// Non-restoring unsinged divider ////
//// ////
//// Author: Richard Herveille ////
//// richard@asics.ws ////
//// www.asics.ws ////
//// ////
/////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2002 Richard Herveille ////
//// richard@asics.ws ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer.////
//// ////
//// THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY ////
//// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED ////
//// TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS ////
//// FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR ////
//// OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, ////
//// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES ////
//// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE ////
//// GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR ////
//// BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF ////
//// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT ////
//// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT ////
//// OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE ////
//// POSSIBILITY OF SUCH DAMAGE. ////
//// ////
/////////////////////////////////////////////////////////////////////
 
// CVS Log
//
// $Id: div_uu.v,v 1.1.1.1 2002-10-29 20:29:10 rherveille Exp $
//
// $Date: 2002-10-29 20:29:10 $
// $Revision: 1.1.1.1 $
// $Author: rherveille $
// $Locker: $
// $State: Exp $
//
// Change History:
// $Log: not supported by cvs2svn $
//
 
//synopsys translate_off
`include "timescale.v"
//synopsys translate_on
 
module div_uu(clk, ena, z, d, q, s, div0, ovf);
 
//
// parameters
//
parameter z_width = 16;
parameter d_width = z_width /2;
//
// inputs & outputs
//
input clk; // system clock
input ena; // clock enable
 
input [z_width -1:0] z; // divident
input [d_width -1:0] d; // divisor
output [d_width -1:0] q; // quotient
reg [d_width-1:0] q;
output [d_width -1:0] s; // remainder
reg [d_width-1:0] s;
output div0;
reg div0;
output ovf;
reg ovf;
 
//
// functions
//
function [z_width:0] gen_s;
input [z_width:0] si;
input [z_width:0] di;
begin
if(si[z_width])
gen_s = {si[z_width-1:0], 1'b0} + di;
else
gen_s = {si[z_width-1:0], 1'b0} - di;
end
endfunction
 
function [d_width-1:0] gen_q;
input [d_width-1:0] qi;
input [z_width:0] si;
begin
gen_q = {qi[d_width-2:0], ~si[z_width]};
end
endfunction
 
function [d_width-1:0] assign_s;
input [z_width:0] si;
input [z_width:0] di;
reg [z_width:0] tmp;
begin
if(si[z_width])
tmp = si + di;
else
tmp = si;
 
assign_s = tmp[z_width-1:z_width-4];
end
endfunction
 
//
// variables
//
reg [d_width-1:0] q_pipe [d_width-1:0];
reg [z_width:0] s_pipe [d_width:0];
reg [z_width:0] d_pipe [d_width:0];
 
reg [d_width:0] div0_pipe, ovf_pipe;
//
// perform parameter checks
//
// synopsys translate_off
initial
begin
if(d_width !== z_width / 2)
$display("div.v parameter error (d_width != z_width/2).");
end
// synopsys translate_on
 
integer n0, n1, n2, n3;
 
// generate divisor (d) pipe
always @(d)
d_pipe[0] <= {1'b0, d, {(z_width-d_width){1'b0}} };
 
always @(posedge clk)
if(ena)
for(n0=1; n0 <= d_width; n0=n0+1)
d_pipe[n0] <= #1 d_pipe[n0-1];
 
// generate internal remainder pipe
always @(z)
s_pipe[0] <= z;
 
always @(posedge clk)
if(ena)
for(n1=1; n1 <= d_width; n1=n1+1)
s_pipe[n1] <= #1 gen_s(s_pipe[n1-1], d_pipe[n1-1]);
 
// generate quotient pipe
always @(posedge clk)
q_pipe[0] <= #1 0;
 
always @(posedge clk)
if(ena)
for(n2=1; n2 < d_width; n2=n2+1)
q_pipe[n2] <= #1 gen_q(q_pipe[n2-1], s_pipe[n2]);
 
 
// flags (divide_by_zero, overflow)
always @(z or d)
begin
ovf_pipe[0] <= !(z[z_width-1:d_width] < d);
div0_pipe[0] <= ~|d;
end
 
always @(posedge clk)
if(ena)
for(n3=1; n3 <= d_width; n3=n3+1)
begin
ovf_pipe[n3] <= #1 ovf_pipe[n3-1];
div0_pipe[n3] <= #1 div0_pipe[n3-1];
end
 
// assign outputs
always @(posedge clk)
if(ena)
ovf <= #1 ovf_pipe[d_width];
 
always @(posedge clk)
if(ena)
div0 <= #1 div0_pipe[d_width];
 
always @(posedge clk)
if(ena)
q <= #1 gen_q(q_pipe[d_width-1], s_pipe[d_width]);
 
always @(posedge clk)
if(ena)
s <= #1 assign_s(s_pipe[d_width], d_pipe[d_width]);
endmodule
 
 
 
/trunk/rtl/verilog/div.v
0,0 → 1,169
/////////////////////////////////////////////////////////////////////
//// ////
//// Non-restoring singed dividor ////
//// ////
//// Author: Richard Herveille ////
//// richard@asics.ws ////
//// www.asics.ws ////
//// ////
/////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2002 Richard Herveille ////
//// richard@asics.ws ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer.////
//// ////
//// THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY ////
//// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED ////
//// TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS ////
//// FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR ////
//// OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, ////
//// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES ////
//// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE ////
//// GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR ////
//// BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF ////
//// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT ////
//// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT ////
//// OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE ////
//// POSSIBILITY OF SUCH DAMAGE. ////
//// ////
/////////////////////////////////////////////////////////////////////
 
// CVS Log
//
// $Id: div.v,v 1.1.1.1 2002-10-29 20:29:11 rherveille Exp $
//
// $Date: 2002-10-29 20:29:11 $
// $Revision: 1.1.1.1 $
// $Author: rherveille $
// $Locker: $
// $State: Exp $
//
// Change History:
// $Log: not supported by cvs2svn $
//
 
`include "timescale.v"
 
module div(clk, ena, z, d, q, s);
 
//
// parameters
//
parameter z_width = 16;
parameter d_width = z_width /2;
 
//
// inputs & outputs
//
input clk; // system clock
input ena; // clock enable
 
input [z_width -1:0] z; // divident
input [d_width -1:0] d; // divisor
output [z_width -1:0] q; // quotient
output [z_width -1:0] s; // remainder
 
//
// functions
//
function sc;
input [z_width:0] si;
input [d_width:0] di;
begin
sc = si[z_width] ~^ di[d_width];
end
endfunction
 
function [z_width:0] gen_q;
input [z_width:0] q;
input q0;
begin
gen_q = {(q << 1), q0};
end
endfunction
 
function [z_width:0] gen_s;
input [z_width:0] si;
input [z_width:0] di;
input sel;
begin
if(sel)
gen_s = {si[z_width-1:0], 1'b0} - di;
else
gen_s = {si[z_width-1:0], 1'b0} + di;
end
endfunction
 
//
// variables
//
reg [z_width:0] q_pipe [z_width:0];
reg [z_width:0] s_pipe [z_width:0];
reg [z_width:0] d_pipe [z_width:0];
reg [z_width:0] qb_pipe;
 
//
// perform parameter checks
//
// synopsys translate_off
initial
begin
if(d_width > z_width)
$display("div.v parameter error (d_width > z_width). Divisor width larger than divident width.");
end
// synopsys translate_on
 
integer n;
 
// generate divisor (d) pipe
always @(d)
d_pipe[0] <= {d[d_width -1], d, {(z_width-d_width){1'b0}} };
 
always @(posedge clk)
if(ena)
for(n=1; n < z_width; n=n+1)
d_pipe[n] <= #1 d_pipe[n-1];
 
// generate sign comparator pipe
always
begin
#1;
for(n=0; n < z_width; n=n+1)
qb_pipe[n] <= sc(s_pipe[n], d_pipe[n]);
end
 
// generate internal remainder pipe
always@(z)
s_pipe[0] <= {z[z_width -1], z};
 
always @(posedge clk)
if(ena)
for(n=1; n < z_width; n=n+1)
s_pipe[n] <= #1 gen_s(s_pipe[n-1], d_pipe[n-1], qb_pipe[n-1]);
 
// generate quotient pipe
always @(qb_pipe[0])
q_pipe[0] <= #1 { {(z_width){1'b0}}, qb_pipe[0]};
 
always @(posedge clk)
if(ena)
for(n=1; n < z_width; n=n+1)
q_pipe[n] <= #1 {q_pipe[n-1], qb_pipe[n]};
 
wire [z_width:0] last_q;
assign last_q = q_pipe[z_width -1];
 
always @(posedge clk)
if(ena)
q_pipe[z_width] <= #1 {!last_q[z_width-1], last_q[z_width-2:0], 1'b1};
 
// assign outputs
assign q = q_pipe[z_width];
assign s = s_pipe[z_width];
endmodule
 
 
/trunk/rtl/verilog/div_su.v
0,0 → 1,152
/////////////////////////////////////////////////////////////////////
//// ////
//// Non-restoring signed by unsigned divider ////
//// Uses the non-restoring unsigned by unsigned divider ////
//// ////
//// Author: Richard Herveille ////
//// richard@asics.ws ////
//// www.asics.ws ////
//// ////
/////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2002 Richard Herveille ////
//// richard@asics.ws ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer.////
//// ////
//// THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY ////
//// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED ////
//// TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS ////
//// FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR ////
//// OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, ////
//// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES ////
//// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE ////
//// GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR ////
//// BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF ////
//// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT ////
//// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT ////
//// OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE ////
//// POSSIBILITY OF SUCH DAMAGE. ////
//// ////
/////////////////////////////////////////////////////////////////////
 
// CVS Log
//
// $Id: div_su.v,v 1.1.1.1 2002-10-29 20:29:09 rherveille Exp $
//
// $Date: 2002-10-29 20:29:09 $
// $Revision: 1.1.1.1 $
// $Author: rherveille $
// $Locker: $
// $State: Exp $
//
// Change History:
// $Log: not supported by cvs2svn $
//
 
//synopsys translate_off
`include "timescale.v"
//synopsys translate_on
 
module div_su(clk, ena, z, d, q, s, div0, ovf);
 
//
// parameters
//
parameter z_width = 16;
parameter d_width = z_width /2;
//
// inputs & outputs
//
input clk; // system clock
input ena; // clock enable
 
input [z_width-1:0] z; // divident
input [d_width-1:0] d; // divisor
output [d_width :0] q; // quotient
output [d_width-1:0] s; // remainder
output div0;
output ovf;
 
reg [d_width :0] q;
reg [d_width-1:0] s;
reg div0;
reg ovf;
 
//
// variables
//
reg [z_width -1:0] iz;
reg [d_width -1:0] id;
reg [d_width +1:0] spipe;
 
wire [d_width -1:0] iq, is;
wire idiv0, iovf;
 
//
// module body
//
 
// delay d
always @(posedge clk)
if (ena)
id <= #1 d;
 
// check z, take abs value
always @(posedge clk)
if (ena)
if (z[z_width-1])
iz <= #1 ~z +1'h1;
else
iz <= #1 z;
 
// generate spipe (sign bit pipe)
integer n;
always @(posedge clk)
if(ena)
begin
spipe[0] <= #1 z[z_width-1];
 
for(n=1; n <= d_width+1; n=n+1)
spipe[n] <= #1 spipe[n-1];
end
 
// hookup non-restoring divider
div_uu #(z_width, d_width)
divider (
.clk(clk),
.ena(ena),
.z(iz),
.d(id),
.q(iq),
.s(is),
.div0(idiv0),
.ovf(iovf)
);
 
// correct divider results if 'd' was negative
always @(posedge clk)
if(ena)
if(spipe[d_width+1])
begin
q <= #1 (~iq) + 1'h1;
s <= #1 (~is) + 1'h1;
end
else
begin
q <= #1 {1'b0, iq};
s <= #1 {1'b0, is};
end
 
// delay flags same as results
always @(posedge clk)
if(ena)
begin
div0 <= #1 idiv0;
ovf <= #1 iovf;
end
endmodule
/trunk/rtl/verilog/div_us.v
0,0 → 1,96
/////////////////////////////////////////////////////////////////////
//// ////
//// Non-restoring signed by unsigned divider ////
//// Uses the non-restoring unsigned by unsigned divider ////
//// ////
//// Author: Richard Herveille ////
//// richard@asics.ws ////
//// www.asics.ws ////
//// ////
/////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2002 Richard Herveille ////
//// richard@asics.ws ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer.////
//// ////
//// THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY ////
//// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED ////
//// TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS ////
//// FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL THE AUTHOR ////
//// OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, ////
//// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES ////
//// (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE ////
//// GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR ////
//// BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF ////
//// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT ////
//// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT ////
//// OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE ////
//// POSSIBILITY OF SUCH DAMAGE. ////
//// ////
/////////////////////////////////////////////////////////////////////
 
// CVS Log
//
// $Id: div_us.v,v 1.1.1.1 2002-10-29 20:29:10 rherveille Exp $
//
// $Date: 2002-10-29 20:29:10 $
// $Revision: 1.1.1.1 $
// $Author: rherveille $
// $Locker: $
// $State: Exp $
//
// Change History:
// $Log: not supported by cvs2svn $
//
 
`include "timescale.v"
 
module div_uu(clk, ena, z, d, q, s, div0, ovf);
 
//
// parameters
//
parameter z_width = 16;
parameter d_width = z_width /2;
//
// inputs & outputs
//
input clk; // system clock
input ena; // clock enable
 
input [z_width -1:0] z; // divident
input [d_width -1:0] d; // divisor
output [d_width -1:0] q; // quotient
reg [d_width-1:0] q;
output [d_width -1:0] s; // remainder
reg [d_width-1:0] s;
output div0;
reg div0;
output ovf;
reg ovf;
 
//
// functions
//
function [width-1:0] twos;
parameter width = 8;
 
input [width -1:0] d;
begin
twos = (~d) + 1'h1;
end
endfunction
 
//
// variables
//
reg [z_width -1:0] dz;
reg [d_width -1:0] dd;
 
endmodule
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.