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

Subversion Repositories gng

Compare Revisions

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

Rev 1 → Rev 2

/gng/trunk/matlab/icdf_gen.c
0,0 → 1,71
/*
* Generate inverse of the normal cumulative distribution function
*
* The calling syntax is:
* x = icdf_gen(r)
*
* Input:
* z: pseudorandom numbers
*
* Output:
* x: Gaussian random numbers, n x 1 vector of 32-bit integer (s<16,11>)
*/
 
/*
* Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
*
* 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 source file is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 2.1 of the License,
* or (at your option) any later version.
*
* This source is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
* License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this source; if not, download it from
* http://www.opencores.org/lgpl.shtml
*/
 
 
#include "mex.h"
#include "icdf.h"
 
 
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
/* Local variables */
unsigned long long *r;
unsigned len;
long *x;
unsigned i;
 
/* Check for proper number of arguments */
if (nrhs != 1)
mexErrMsgTxt("One input arguments required.");
 
if (!mxIsUint64(prhs[0]) || (mxGetN(prhs[0]) != 1))
mexErrMsgTxt("icdf_gen requires that r be a column vector of unsigned 64-bit integer.");
 
len = mxGetM(prhs[0]);
if (len < 1)
mexErrMsgTxt("icdf_gen requires that vector length be a positive integer.");
 
/* Create a vector for the return argument */
plhs[0] = mxCreateNumericMatrix(len, 1, mxINT32_CLASS, 0);
 
/* Assign pointers to the various parameters */
r = (unsigned long long*)mxGetData(prhs[0]);
x = (long*)mxGetData(plhs[0]);
 
/* Call function icdf and assign return value */
for (i = 0; i < len; i++)
x[i] = icdf(r[i]);
}
/gng/trunk/matlab/ctg_gen.m
0,0 → 1,13
% CTG_GEN Generate Combined Tausworthe number
%
% The calling syntax is:
% x = ctg_gen(z, n)
% [x, zf] = ctg_gen(z, n)
%
% Input:
% z: initial internal state, 3 x 1 vector of unsigned 64-bit integer
% n: length of pseudorandom numbers
%
% Output:
% x: pseudorandom values, n x 1 vector of unsigned 64-bit integer
% zf: final internal state after output n numbers
/gng/trunk/matlab/build_mex.m
0,0 → 1,27
% Build mex files
 
% Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
%
% 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 source file is free software; you can redistribute it and/or modify it
% under the terms of the GNU Lesser General Public License as published by
% the Free Software Foundation; either version 2.1 of the License,
% or (at your option) any later version.
%
% This source is distributed in the hope that it will be useful, but
% WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
% or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
% License for more details.
%
% You should have received a copy of the GNU Lesser General Public License
% along with this source; if not, download it from
% http://www.opencores.org/lgpl.shtml
 
 
mex -I../c ctg_seed.c ../c/taus176.c
mex -I../c ctg_gen.c ../c/taus176.c
mex -I../c icdf_gen.c ../c/icdf.c
/gng/trunk/matlab/test_gng.m
0,0 → 1,37
% Test Gaussian noise generator
 
% Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
%
% 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 source file is free software; you can redistribute it and/or modify it
% under the terms of the GNU Lesser General Public License as published by
% the Free Software Foundation; either version 2.1 of the License,
% or (at your option) any later version.
%
% This source is distributed in the hope that it will be useful, but
% WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
% or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
% License for more details.
%
% You should have received a copy of the GNU Lesser General Public License
% along with this source; if not, download it from
% http://www.opencores.org/lgpl.shtml
 
 
clc; clear;
 
tic;
 
N = 10000000;
Seed = 1;
 
z = ctg_seed(Seed);
r = ctg_gen(z, N);
x = icdf_gen(r);
y = double(x)/2^11; % standard normal distribution
 
toc;
/gng/trunk/matlab/ctg_gen.c
0,0 → 1,97
/*
* Generate Combined Tausworthe number
*
* The calling syntax is:
* x = ctg_gen(z, n)
* [x, zf] = ctg_gen(z, n)
*
* Input:
* z: initial internal state, 3 x 1 vector of unsigned 64-bit integer
* n: length of pseudorandom numbers
*
* Output:
* x: pseudorandom values, n x 1 vector of unsigned 64-bit integer
* zf: final internal state after output n numbers
*/
 
/*
* Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
*
* 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 source file is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 2.1 of the License,
* or (at your option) any later version.
*
* This source is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
* License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this source; if not, download it from
* http://www.opencores.org/lgpl.shtml
*/
 
 
#include "mex.h"
#include "taus176.h"
 
 
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
/* Local variables */
taus_state_t state;
unsigned long long *z;
double *n;
unsigned len;
unsigned long long *x;
unsigned long long *zf;
unsigned i;
 
/* Check for proper number of arguments */
if (nrhs != 2)
mexErrMsgTxt("Two input arguments required.");
else if (nlhs > 2)
mexErrMsgTxt("Too many output arguments.");
 
if (!mxIsUint64(prhs[0]) || (mxGetM(prhs[0]) != 3) || (mxGetN(prhs[0]) != 1))
mexErrMsgTxt("ctg_gen requires that z be a 3 x 1 vector of unsigned 64-bit integer.");
 
if (!mxIsDouble(prhs[1]) || mxIsComplex(prhs[1]) ||
(mxGetM(prhs[1]) != 1) || (mxGetN(prhs[1]) != 1))
mexErrMsgTxt("ctg_gen requires that n be a positive integer.");
 
n = mxGetPr(prhs[1]);
len = (unsigned)(*n);
if (len < 1)
mexErrMsgTxt("ctg_gen requires that n be a positive integer.");
 
/* Create a vector for the return argument */
plhs[0] = mxCreateNumericMatrix(len, 1, mxUINT64_CLASS, 0);
if (nlhs == 2)
plhs[1] = mxCreateNumericMatrix(3, 1, mxUINT64_CLASS, 0);
 
/* Assign pointers to the various parameters */
z = (unsigned long long*)mxGetData(prhs[0]);
x = (unsigned long long*)mxGetData(plhs[0]);
if (nlhs == 2)
zf = (unsigned long long*)mxGetData(plhs[1]);
 
/* Call function taus_set and assign return value */
state.z1 = z[0];
state.z2 = z[1];
state.z3 = z[2];
for (i = 0; i < len; i++)
x[i] = taus_get(&state);
 
if (nlhs == 2) {
zf[0] = state.z1;
zf[1] = state.z2;
zf[2] = state.z3;
}
}
/gng/trunk/matlab/ctg_seed.m
0,0 → 1,31
% CTG_SEED Generate Combined Tausworthe Generator seed
%
% The calling syntax is:
% z = ctg_seed(s)
%
% Input:
% s: seed, unsigned 32-bit integer
%
% Output:
% z: initial internal state, 3 x 1 vector of unsigned 64-bit integer
 
% Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
%
% 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 source file is free software; you can redistribute it and/or modify it
% under the terms of the GNU Lesser General Public License as published by
% the Free Software Foundation; either version 2.1 of the License,
% or (at your option) any later version.
%
% This source is distributed in the hope that it will be useful, but
% WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
% or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
% License for more details.
%
% You should have received a copy of the GNU Lesser General Public License
% along with this source; if not, download it from
% http://www.opencores.org/lgpl.shtml
/gng/trunk/matlab/icdf_gen.m
0,0 → 1,32
% ICDF_GEN Generate inverse of the normal cumulative distribution function
%
% The calling syntax is:
% x = icdf_gen(r)
%
% Input:
% z: pseudorandom numbers
%
% Output:
% x: Gaussian random numbers, n x 1 vector of 32-bit integer (s<16,11>)
%
 
% Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
%
% 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 source file is free software; you can redistribute it and/or modify it
% under the terms of the GNU Lesser General Public License as published by
% the Free Software Foundation; either version 2.1 of the License,
% or (at your option) any later version.
%
% This source is distributed in the hope that it will be useful, but
% WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
% or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
% License for more details.
%
% You should have received a copy of the GNU Lesser General Public License
% along with this source; if not, download it from
% http://www.opencores.org/lgpl.shtml
/gng/trunk/matlab/ctg_seed.c
0,0 → 1,51
/*
* Generate Combined Tausworthe Generator seed
*
* The calling syntax is:
* z = ctg_seed(s)
*
* Input:
* s: seed, unsigned 32-bit integer
*
* Output:
* z: initial internal state, 3 x 1 vector of unsigned 64-bit integer
*/
 
#include "mex.h"
#include "taus176.h"
 
 
void mexFunction(int nlhs, mxArray *plhs[], int nrhs, const mxArray *prhs[])
{
/* Local variables */
taus_state_t state;
double *s;
unsigned seed;
unsigned long long *z;
/* Check for proper number of arguments */
if (nrhs != 1)
mexErrMsgTxt("One input arguments required.");
else if (nlhs > 1)
mexErrMsgTxt("Too many output arguments.");
if (!mxIsDouble(prhs[0]) || mxIsComplex(prhs[0]) ||
(mxGetM(prhs[0]) != 1) || (mxGetN(prhs[0]) != 1))
mexErrMsgTxt("ctg_seed requires that s be a unsigned 32-bit integer.");
/* Create a vector for the return argument */
plhs[0] = mxCreateNumericMatrix(3, 1, mxUINT64_CLASS, 0);
/* Assign pointers to the various parameters */
s = (unsigned *)mxGetPr(prhs[0]);
seed = (unsigned)(*s);
z = (unsigned long long*)mxGetData(plhs[0]);
/* Call function taus_set */
taus_set(&state, seed);
/* Assign return value */
z[0] = state.z1;
z[1] = state.z2;
z[2] = state.z3;
}
/gng/trunk/rtl/gng.v
0,0 → 1,83
//------------------------------------------------------------------------------
//
// gng.v
//
// This file is part of the Gaussian Noise Generator IP Core
//
// Description
// Top module of Gaussian noise generator.
//
//------------------------------------------------------------------------------
//
// Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
//
// 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 source file is free software; you can redistribute it and/or modify it
// under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation; either version 2.1 of the License,
// or (at your option) any later version.
//
// This source is distributed in the hope that it will be useful, but
// WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
// License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this source; if not, download it from
// http://www.opencores.org/lgpl.shtml
//
//------------------------------------------------------------------------------
 
 
`timescale 1 ns / 1 ps
 
 
module gng #(
parameter INIT_Z1 = 64'd5030521883283424767,
parameter INIT_Z2 = 64'd18445829279364155008,
parameter INIT_Z3 = 64'd18436106298727503359
)
(
// System signals
input clk, // system clock
input rstn, // system synchronous reset, active low
 
// Data interface
input ce, // clock enable
output valid_out, // output data valid
output [15:0] data_out // output data, s<16,11>
);
 
// Local variables
wire valid_out_ctg;
wire [63:0] data_out_ctg;
 
 
// Instances
gng_ctg #(
.INIT_Z1(INIT_Z1),
.INIT_Z2(INIT_Z2),
.INIT_Z3(INIT_Z3)
) u_gng_ctg (
.clk(clk),
.rstn(rstn),
.ce(ce),
.valid_out(valid_out_ctg),
.data_out(data_out_ctg)
);
 
gng_interp u_gng_interp (
.clk(clk),
.rstn(rstn),
.valid_in(valid_out_ctg),
.data_in(data_out_ctg),
.valid_out(valid_out),
.data_out(data_out)
);
 
 
endmodule
/gng/trunk/rtl/gng_interp.v
0,0 → 1,220
//------------------------------------------------------------------------------
//
// gng_interp.v
//
// This file is part of the Gaussian Noise Generator IP Core
//
// Description
// Polynomial interpolation.
//
//------------------------------------------------------------------------------
//
// Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
//
// 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 source file is free software; you can redistribute it and/or modify it
// under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation; either version 2.1 of the License,
// or (at your option) any later version.
//
// This source is distributed in the hope that it will be useful, but
// WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
// License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this source; if not, download it from
// http://www.opencores.org/lgpl.shtml
//
//------------------------------------------------------------------------------
 
 
`timescale 1 ns / 1 ps
 
 
module gng_interp (
// System signals
input clk, // system clock
input rstn, // system synchronous reset, active low
 
// Data interface
input valid_in, // input data valid
input [63:0] data_in, // input data
output reg valid_out, // output data valid
output reg [15:0] data_out // output data, s<16,11>
);
 
// Local variables
wire [5:0] num_lzd;
reg [5:0] num_lzd_r;
reg [14:0] mask;
reg [1:0] offset;
wire [7:0] addr;
wire [17:0] c0; // u<18,14>
wire [17:0] c1; // s<18,19>
wire [16:0] c2; // u<17,23>
reg [14:0] x; // u<15,15>
reg [14:0] x_r1, x_r2, x_r3, x_r4; // u<15,15>
reg [17:0] c1_r1; // s<18,19>
wire [37:0] sum1; // s<38,38>
wire [17:0] sum1_new; // s<18,18>
wire [33:0] mul1; // s<34,33>
wire signed [13:0] mul1_new; // s<14,14>
reg [17:0] c0_r1, c0_r2, c0_r3, c0_r4, c0_r5; // u<18,14>
reg signed [18:0] sum2; // s<19,14>
reg [14:0] sum2_rnd; // u<15,11>
reg [8:0] sign_r;
reg [8:0] valid_in_r;
 
 
// Leading zero detector
gng_lzd u_gng_lzd (
.data_in(data_in[63:3]),
.data_out(num_lzd)
);
 
always @ (posedge clk) begin
if (!rstn)
num_lzd_r <= 6'd0;
else
num_lzd_r <= num_lzd;
end
 
 
// Get mask for value x
always @ (posedge clk) begin
if (!rstn)
mask <= 15'b111111111111111;
else begin
case (num_lzd_r)
6'd61: mask <= 15'b111111111111111;
6'd60: mask <= 15'b011111111111111;
6'd59: mask <= 15'b101111111111111;
6'd58: mask <= 15'b110111111111111;
6'd57: mask <= 15'b111011111111111;
6'd56: mask <= 15'b111101111111111;
6'd55: mask <= 15'b111110111111111;
6'd54: mask <= 15'b111111011111111;
6'd53: mask <= 15'b111111101111111;
6'd52: mask <= 15'b111111110111111;
6'd51: mask <= 15'b111111111011111;
6'd50: mask <= 15'b111111111101111;
6'd49: mask <= 15'b111111111110111;
6'd48: mask <= 15'b111111111111011;
6'd47: mask <= 15'b111111111111101;
6'd46: mask <= 15'b111111111111110;
default: mask <= 15'b111111111111111;
endcase
end
end
 
 
// Generate table address and coefficients
always @ (posedge clk) begin
if (!rstn)
offset <= 2'd0;
else
offset <= {data_in[1], data_in[2]};
end
 
assign addr = {num_lzd_r, offset};
 
gng_coef u_gng_coef (
.clk(clk),
.addr(addr),
.c0(c0),
.c1(c1),
.c2(c2)
);
 
 
// Data delay
always @ (posedge clk) begin
if (!rstn)
x <= 15'd0;
else
x <= {data_in[3], data_in[4], data_in[5], data_in[6], data_in[7],
data_in[8], data_in[9], data_in[10], data_in[11], data_in[12],
data_in[13], data_in[14], data_in[15], data_in[16], data_in[17]};
end
 
always @ (posedge clk) begin
x_r1 <= x & mask;
x_r2 <= x_r1;
x_r3 <= x_r2;
x_r4 <= x_r3;
end
 
always @ (posedge clk) begin
c1_r1 <= c1;
end
 
always @ (posedge clk) begin
c0_r1 <= c0;
c0_r2 <= c0_r1;
c0_r3 <= c0_r2;
c0_r4 <= c0_r3;
c0_r5 <= c0_r4;
end
 
always @ (posedge clk) begin
sign_r <= {sign_r[7:0], data_in[0]};
end
 
always @ (posedge clk) begin
valid_in_r <= {valid_in_r[7:0], valid_in};
end
 
 
// Polynomial interpolation of order 2
gng_smul_16_18_sadd_37 u_gng_smul_16_18_sadd_37 (
.clk(clk),
.a({1'b0, x_r1}),
.b({1'b0, c2}),
.c({c1_r1, 19'd0}),
.p(sum1)
);
 
assign sum1_new = sum1[37:20];
 
gng_smul_16_18 u_gng_smul_16_18 (
.clk(clk),
.a({1'b0, x_r4}),
.b(sum1_new),
.p(mul1)
);
 
assign mul1_new = mul1[32:19];
 
always @ (posedge clk) begin
sum2 <= $signed({1'b0, c0_r5}) + mul1_new;
end
 
always @ (posedge clk) begin
sum2_rnd <= sum2[17:3] + sum2[2];
end
 
 
// Output data
always @ (posedge clk) begin
if (!rstn)
valid_out <= 1'b0;
else
valid_out <= valid_in_r[8];
end
 
always @ (posedge clk) begin
if (!rstn)
data_out <= 16'd0;
else if (sign_r[8])
data_out <= {1'b1, ~sum2_rnd} + 1'b1;
else
data_out <= {1'b0, sum2_rnd};
end
 
 
endmodule
/gng/trunk/rtl/gng_smul_16_18_sadd_37.v
0,0 → 1,78
//------------------------------------------------------------------------------
//
// gng_smul_16_18_sadd_37.v
//
// This file is part of the Gaussian Noise Generator IP Core
//
// Description
// Signed multiplier 16-bit x 18-bit follows signed adder 37-bit,
 
//
//------------------------------------------------------------------------------
//
// Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
//
// 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 source file is free software; you can redistribute it and/or modify it
// under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation; either version 2.1 of the License,
// or (at your option) any later version.
//
// This source is distributed in the hope that it will be useful, but
// WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
// License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this source; if not, download it from
// http://www.opencores.org/lgpl.shtml
//
//------------------------------------------------------------------------------
 
 
`timescale 1 ns / 1 ps
 
 
module gng_smul_16_18_sadd_37 (
// System signals
input clk, // system clock
 
// Data interface
input [15:0] a, // multiplicand
input [17:0] b, // multiplicator
input [36:0] c, // adder
output [37:0] p // result
);
 
// Behavioral model
reg signed [15:0] a_reg;
reg signed [17:0] b_reg;
reg signed [36:0] c_reg;
reg signed [33:0] prod;
wire signed [37:0] sum;
reg [37:0] result;
 
always @ (posedge clk) begin
a_reg <= a;
b_reg <= b;
c_reg <= c;
end
 
always @ (posedge clk) begin
prod <= a_reg * b_reg;
end
 
assign sum = c_reg + prod;
 
always @ (posedge clk) begin
result <= sum;
end
 
assign p = result;
 
 
endmodule
/gng/trunk/rtl/gng_lzd.v
0,0 → 1,199
//------------------------------------------------------------------------------
//
// gng_lzd.v
//
// This file is part of the Gaussian Noise Generator IP Core
//
// Description
// Leading zero detector of 61-bit number.
//
//------------------------------------------------------------------------------
//
// Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
//
// 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 source file is free software; you can redistribute it and/or modify it
// under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation; either version 2.1 of the License,
// or (at your option) any later version.
//
// This source is distributed in the hope that it will be useful, but
// WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
// License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this source; if not, download it from
// http://www.opencores.org/lgpl.shtml
//
//------------------------------------------------------------------------------
 
 
`timescale 1 ns / 1 ps
 
 
module gng_lzd (
// Data interface
input [60:0] data_in, // input data
output [5:0] data_out // output number of leading zeros
);
 
// Local variables
wire [63:0] d;
wire p1 [31:0];
wire [31:0] v1;
wire [1:0] p2 [15:0];
wire [15:0] v2;
wire [2:0] p3 [7:0];
wire [7:0] v3;
wire [3:0] p4 [3:0];
wire [3:0] v4;
wire [4:0] p5 [1:0];
wire [1:0] v5;
wire [5:0] p6;
 
 
// Parallel structure
assign d = {data_in, 3'b111}; // fill last 3 bits with '1'
 
assign p1[0 ] = ~d[1 ];
assign p1[1 ] = ~d[3 ];
assign p1[2 ] = ~d[5 ];
assign p1[3 ] = ~d[7 ];
assign p1[4 ] = ~d[9 ];
assign p1[5 ] = ~d[11];
assign p1[6 ] = ~d[13];
assign p1[7 ] = ~d[15];
assign p1[8 ] = ~d[17];
assign p1[9 ] = ~d[19];
assign p1[10] = ~d[21];
assign p1[11] = ~d[23];
assign p1[12] = ~d[25];
assign p1[13] = ~d[27];
assign p1[14] = ~d[29];
assign p1[15] = ~d[31];
assign p1[16] = ~d[33];
assign p1[17] = ~d[35];
assign p1[18] = ~d[37];
assign p1[19] = ~d[39];
assign p1[20] = ~d[41];
assign p1[21] = ~d[43];
assign p1[22] = ~d[45];
assign p1[23] = ~d[47];
assign p1[24] = ~d[49];
assign p1[25] = ~d[51];
assign p1[26] = ~d[53];
assign p1[27] = ~d[55];
assign p1[28] = ~d[57];
assign p1[29] = ~d[59];
assign p1[30] = ~d[61];
assign p1[31] = ~d[63];
assign v1[0 ] = d[0 ] | d[1 ];
assign v1[1 ] = d[2 ] | d[3 ];
assign v1[2 ] = d[4 ] | d[5 ];
assign v1[3 ] = d[6 ] | d[7 ];
assign v1[4 ] = d[8 ] | d[9 ];
assign v1[5 ] = d[10] | d[11];
assign v1[6 ] = d[12] | d[13];
assign v1[7 ] = d[14] | d[15];
assign v1[8 ] = d[16] | d[17];
assign v1[9 ] = d[18] | d[19];
assign v1[10] = d[20] | d[21];
assign v1[11] = d[22] | d[23];
assign v1[12] = d[24] | d[25];
assign v1[13] = d[26] | d[27];
assign v1[14] = d[28] | d[29];
assign v1[15] = d[30] | d[31];
assign v1[16] = d[32] | d[33];
assign v1[17] = d[34] | d[35];
assign v1[18] = d[36] | d[37];
assign v1[19] = d[38] | d[39];
assign v1[20] = d[40] | d[41];
assign v1[21] = d[42] | d[43];
assign v1[22] = d[44] | d[45];
assign v1[23] = d[46] | d[47];
assign v1[24] = d[48] | d[49];
assign v1[25] = d[50] | d[51];
assign v1[26] = d[52] | d[53];
assign v1[27] = d[54] | d[55];
assign v1[28] = d[56] | d[57];
assign v1[29] = d[58] | d[59];
assign v1[30] = d[60] | d[61];
assign v1[31] = d[62] | d[63];
 
assign p2[0 ] = {~v1[1 ], (v1[1 ] ? p1[1 ] : p1[0 ])};
assign p2[1 ] = {~v1[3 ], (v1[3 ] ? p1[3 ] : p1[2 ])};
assign p2[2 ] = {~v1[5 ], (v1[5 ] ? p1[5 ] : p1[4 ])};
assign p2[3 ] = {~v1[7 ], (v1[7 ] ? p1[7 ] : p1[6 ])};
assign p2[4 ] = {~v1[9 ], (v1[9 ] ? p1[9 ] : p1[8 ])};
assign p2[5 ] = {~v1[11], (v1[11] ? p1[11] : p1[10])};
assign p2[6 ] = {~v1[13], (v1[13] ? p1[13] : p1[12])};
assign p2[7 ] = {~v1[15], (v1[15] ? p1[15] : p1[14])};
assign p2[8 ] = {~v1[17], (v1[17] ? p1[17] : p1[16])};
assign p2[9 ] = {~v1[19], (v1[19] ? p1[19] : p1[18])};
assign p2[10] = {~v1[21], (v1[21] ? p1[21] : p1[20])};
assign p2[11] = {~v1[23], (v1[23] ? p1[23] : p1[22])};
assign p2[12] = {~v1[25], (v1[25] ? p1[25] : p1[24])};
assign p2[13] = {~v1[27], (v1[27] ? p1[27] : p1[26])};
assign p2[14] = {~v1[29], (v1[29] ? p1[29] : p1[28])};
assign p2[15] = {~v1[31], (v1[31] ? p1[31] : p1[30])};
assign v2[0 ] = v1[1 ] | v1[0 ];
assign v2[1 ] = v1[3 ] | v1[2 ];
assign v2[2 ] = v1[5 ] | v1[4 ];
assign v2[3 ] = v1[7 ] | v1[6 ];
assign v2[4 ] = v1[9 ] | v1[8 ];
assign v2[5 ] = v1[11] | v1[10];
assign v2[6 ] = v1[13] | v1[12];
assign v2[7 ] = v1[15] | v1[14];
assign v2[8 ] = v1[17] | v1[16];
assign v2[9 ] = v1[19] | v1[18];
assign v2[10] = v1[21] | v1[20];
assign v2[11] = v1[23] | v1[22];
assign v2[12] = v1[25] | v1[24];
assign v2[13] = v1[27] | v1[26];
assign v2[14] = v1[29] | v1[28];
assign v2[15] = v1[31] | v1[30];
 
assign p3[0] = {~v2[1 ], (v2[1 ] ? p2[1 ] : p2[0 ])};
assign p3[1] = {~v2[3 ], (v2[3 ] ? p2[3 ] : p2[2 ])};
assign p3[2] = {~v2[5 ], (v2[5 ] ? p2[5 ] : p2[4 ])};
assign p3[3] = {~v2[7 ], (v2[7 ] ? p2[7 ] : p2[6 ])};
assign p3[4] = {~v2[9 ], (v2[9 ] ? p2[9 ] : p2[8 ])};
assign p3[5] = {~v2[11], (v2[11] ? p2[11] : p2[10])};
assign p3[6] = {~v2[13], (v2[13] ? p2[13] : p2[12])};
assign p3[7] = {~v2[15], (v2[15] ? p2[15] : p2[14])};
assign v3[0] = v2[1 ] | v2[0 ];
assign v3[1] = v2[3 ] | v2[2 ];
assign v3[2] = v2[5 ] | v2[4 ];
assign v3[3] = v2[7 ] | v2[6 ];
assign v3[4] = v2[9 ] | v2[8 ];
assign v3[5] = v2[11] | v2[10];
assign v3[6] = v2[13] | v2[12];
assign v3[7] = v2[15] | v2[14];
 
assign p4[0] = {~v3[1], (v3[1] ? p3[1] : p3[0])};
assign p4[1] = {~v3[3], (v3[3] ? p3[3] : p3[2])};
assign p4[2] = {~v3[5], (v3[5] ? p3[5] : p3[4])};
assign p4[3] = {~v3[7], (v3[7] ? p3[7] : p3[6])};
assign v4[0] = v3[1] | v3[0];
assign v4[1] = v3[3] | v3[2];
assign v4[2] = v3[5] | v3[4];
assign v4[3] = v3[7] | v3[6];
 
assign p5[0] = {~v4[1], (v4[1] ? p4[1] : p4[0])};
assign p5[1] = {~v4[3], (v4[3] ? p4[3] : p4[2])};
assign v5[0] = v4[1] | v4[0];
assign v5[1] = v4[3] | v4[2];
 
assign p6 = {~v5[1], (v5[1] ? p5[1] : p5[0])};
 
 
// Output data
assign data_out = p6;
 
 
endmodule
/gng/trunk/rtl/gng_coef.v
0,0 → 1,318
//------------------------------------------------------------------------------
//
// gng_coef.v
//
// This file is part of the Gaussian Noise Generator IP Core
//
// Description
// Coefficients ROM table for polynomial interpolation.
//
//------------------------------------------------------------------------------
//
// Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
//
// 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 source file is free software; you can redistribute it and/or modify it
// under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation; either version 2.1 of the License,
// or (at your option) any later version.
//
// This source is distributed in the hope that it will be useful, but
// WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
// License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this source; if not, download it from
// http://www.opencores.org/lgpl.shtml
//
//------------------------------------------------------------------------------
 
 
`timescale 1 ns / 1 ps
 
 
module gng_coef (
// System signals
input clk, // system clock
 
// Data interface
input [7:0] addr, // read address
output reg [17:0] c0, // coefficient c0, u<18,14>
output reg [17:0] c1, // coefficient c1, s<18,19>
output reg [16:0] c2 // coefficient c2, u<17,23>
);
 
// Local variables
reg [52:0] d; // {c0, c1, c2}
 
 
// Table
always @ (*) begin
case (addr)
8'd0 : d = 53'b000010101100101001_100110111110001110_10100011110000000;
8'd1 : d = 53'b000001111101000111_101001011111011001_01011111011110011;
8'd2 : d = 53'b000001010001100100_101010111101101110_00110010101000000;
8'd3 : d = 53'b000000101000010001_101011101111111001_00001111111010011;
8'd4 : d = 53'b000100100110011110_101100101100100010_10101101110011100;
8'd5 : d = 53'b000100000010100011_101111010111110111_01110101000001100;
8'd6 : d = 53'b000011100011000111_110001001011101011_01010011011010011;
8'd7 : d = 53'b000011000110110001_110010011110011100_00111101101011001;
8'd8 : d = 53'b000110001000101110_101111110110101010_10100011001000110;
8'd9 : d = 53'b000101101010111101_110010010111100001_01101111010111011;
8'd10 : d = 53'b000101010001011010_110100000101110001_01010000111111000;
8'd11 : d = 53'b000100111010110110_110101010110001001_00111101100100011;
8'd12 : d = 53'b000111011100110110_110001111001100101_10010111001100011;
8'd13 : d = 53'b000111000010111111_110100001110101001_01100111010010101;
8'd14 : d = 53'b000110101101000010_110101110100111010_01001011010000101;
8'd15 : d = 53'b000110011001110111_110110111111100110_00111001011001010;
8'd16 : d = 53'b001000100111011000_110011010110100101_10001100100110110;
8'd17 : d = 53'b001000010000010000_110101100001001100_01011111111010010;
8'd18 : d = 53'b000111111100110010_110111000000001000_01000101110011111;
8'd19 : d = 53'b000111101011110111_111000000101011011_00110101001101001;
8'd20 : d = 53'b001001101010111000_110100011100101111_10000011100100011;
8'd21 : d = 53'b001001010101110100_110110011110011100_01011001100101001;
8'd22 : d = 53'b001001000100001010_110111110111000110_01000001000110100;
8'd23 : d = 53'b001000110100111000_111000110111101101_00110001100011100;
8'd24 : d = 53'b001010101000111110_110101010011111110_01111011110111110;
8'd25 : d = 53'b001010010101100000_110111001110000100_01010100001100011;
8'd26 : d = 53'b001010000101010000_111000100001011001_00111101000110010;
8'd27 : d = 53'b001001110111001111_111001011110000001_00101110011100100;
8'd28 : d = 53'b001011100010101101_110110000000110101_01110101010001000;
8'd29 : d = 53'b001011010000100011_110111110100011001_01001111100101010;
8'd30 : d = 53'b001011000001011011_111001000011001010_00111001101011010;
8'd31 : d = 53'b001010110100011010_111001111100011001_00101011110010110;
8'd32 : d = 53'b001100011000111001_110110100110001001_01101111100010101;
8'd33 : d = 53'b001100000111110011_111000010100000101_01001011100110010;
8'd34 : d = 53'b001011111001100110_111001011110111001_00110110101110100;
8'd35 : d = 53'b001011101101011011_111010010101001100_00101001100000110;
8'd36 : d = 53'b001101001100000100_110111000101110100_01101010100010001;
8'd37 : d = 53'b001100111011111001_111000101110110010_01001000000111110;
8'd38 : d = 53'b001100101110011110_111001110110001010_00110100001010001;
8'd39 : d = 53'b001100100010111110_111010101001111011_00100111100001111;
8'd40 : d = 53'b001101111100101100_110111100001000101_01100110000110111;
8'd41 : d = 53'b001101101101010011_111001000101101101_01000101000011110;
8'd42 : d = 53'b001101100000100011_111010001010000011_00110001111001101;
8'd43 : d = 53'b001101010101101000_111010111011100011_00100101110010101;
8'd44 : d = 53'b001110101011000101_110111111000111001_01100010001010110;
8'd45 : d = 53'b001110011100011000_111001011001101000_01000010010101101;
8'd46 : d = 53'b001110010000001101_111010011011010001_00101111111001101;
8'd47 : d = 53'b001110000101110011_111011001010110011_00100100010000001;
8'd48 : d = 53'b001111010111100001_111000001101111010_01011110101000100;
8'd49 : d = 53'b001111001001011011_111001101011001001_00111111111001110;
8'd50 : d = 53'b001110111101110000_111010101010011000_00101110000111001;
8'd51 : d = 53'b001110110011110011_111011011000001000_00100010111000010;
8'd52 : d = 53'b010000000010001111_111000100000100111_01011011011100010;
8'd53 : d = 53'b001111110100101011_111001111010101101_00111101101101001;
8'd54 : d = 53'b001111101001011101_111010110111110001_00101100100000001;
8'd55 : d = 53'b001111011111111001_111011100011111010_00100001101001010;
8'd56 : d = 53'b010000101011011010_111000110001011010_01011000100010101;
8'd57 : d = 53'b010000011110010100_111010001000101001_00111011101101101;
8'd58 : d = 53'b010000010011100000_111011000011101110_00101011000010110;
8'd59 : d = 53'b010000001010010010_111011101110011011_00100000100001110;
8'd60 : d = 53'b010001010011001011_111001000000100110_01010101111001000;
8'd61 : d = 53'b010001000110100001_111010010101001110_00111001111001011;
8'd62 : d = 53'b010000111100000101_111011001110100000_00101001101101110;
8'd63 : d = 53'b010000110011001011_111011110111111001_00011111100000110;
8'd64 : d = 53'b010001111001101011_111001001110011010_01010011011101011;
8'd65 : d = 53'b010001101101011010_111010100000101000_00111000001110110;
8'd66 : d = 53'b010001100011010011_111011011000010001_00101000011111111;
8'd67 : d = 53'b010001011010101100_111100000000011100_00011110100101010;
8'd68 : d = 53'b010010011111000010_111001011011000010_01010001001101111;
8'd69 : d = 53'b010010010011001000_111010101011000011_00110110101100101;
8'd70 : d = 53'b010010001001010100_111011100001001011_00100111011000011;
8'd71 : d = 53'b010010000000111110_111100001000001111_00011101101110101;
8'd72 : d = 53'b010011000011010100_111001100110101010_01001111001001001;
8'd73 : d = 53'b010010110111110000_111010110100101000_00110101010001111;
8'd74 : d = 53'b010010101110001110_111011101001010101_00100110010110010;
8'd75 : d = 53'b010010100110000111_111100001111011000_00011100111100001;
8'd76 : d = 53'b010011100110101001_111001110001011000_01001101001101110;
8'd77 : d = 53'b010011011011011000_111010111101011100_00110011111101110;
8'd78 : d = 53'b010011010010000110_111011110000110110_00100101011000111;
8'd79 : d = 53'b010011001010001101_111100010101111100_00011100001101100;
8'd80 : d = 53'b010100001001000100_111001111011010100_01001011011010110;
8'd81 : d = 53'b010011111110000101_111011000101100111_00110010101111010;
8'd82 : d = 53'b010011110101000010_111011110111110011_00100100011111111;
8'd83 : d = 53'b010011101101010110_111100011100000001_00011011100010000;
8'd84 : d = 53'b010100101010101001_111010000100100011_01001001101111010;
8'd85 : d = 53'b010100011111111011_111011001101001100_00110001100110000;
8'd86 : d = 53'b010100010111000110_111011111110010000_00100011101010101;
8'd87 : d = 53'b010100001111100110_111100100001101001_00011010111001100;
8'd88 : d = 53'b010101001011011100_111010001101001011_01001000001010100;
8'd89 : d = 53'b010101000000111110_111011010100010000_00110000100001100;
8'd90 : d = 53'b010100111000010110_111100000100010001_00100010111000110;
8'd91 : d = 53'b010100110001000001_111100100110111000_00011010010011100;
8'd92 : d = 53'b010101101011100000_111010010101001111_01000110101011110;
8'd93 : d = 53'b010101100001010001_111011011010111000_00101111100001000;
8'd94 : d = 53'b010101011000110110_111100001001111000_00100010001010000;
8'd95 : d = 53'b010101010001101011_111100101011110001_00011001110000000;
8'd96 : d = 53'b010110001010111001_111010011100110100_01000101010010101;
8'd97 : d = 53'b010110000000110111_111011100001000100_00101110100100011;
8'd98 : d = 53'b010101111000101000_111100001111001001_00100001011110000;
8'd99 : d = 53'b010101110001100111_111100110000010110_00011001001110100;
8'd100: d = 53'b010110101001101001_111010100011111100_01000011111110011;
8'd101: d = 53'b010110011111110100_111011100110111001_00101101101011001;
8'd102: d = 53'b010110010111101111_111100010100000101_00100000110100100;
8'd103: d = 53'b010110010000111000_111100110100101001_00011000101111000;
8'd104: d = 53'b010111000111110010_111010101010101010_01000010101110101;
8'd105: d = 53'b010110111110001010_111011101100011001_00101100110101000;
8'd106: d = 53'b010110110110001111_111100011000101111_00100000001101010;
8'd107: d = 53'b010110101111100000_111100111000101100_00011000010001010;
8'd108: d = 53'b010111100101010111_111010110001000000_01000001100011001;
8'd109: d = 53'b010111011011111010_111011110001100101_00101100000001110;
8'd110: d = 53'b010111010100001000_111100011101001000_00011111101000001;
8'd111: d = 53'b010111001101100010_111100111100100000_00010111110101000;
8'd112: d = 53'b011000000010011001_111010110111000001_01000000011011011;
8'd113: d = 53'b010111111001000111_111011110110011111_00101011010001001;
8'd114: d = 53'b010111110001011110_111100100001010011_00011111000100111;
8'd115: d = 53'b010111101011000000_111101000000000111_00010111011010010;
8'd116: d = 53'b011000011110111010_111010111100101110_00111111010111001;
8'd117: d = 53'b011000010101110010_111011111011001001_00101010100010111;
8'd118: d = 53'b011000001110010011_111100100101001111_00011110100011011;
8'd119: d = 53'b011000000111111011_111101000011100010_00010111000000111;
8'd120: d = 53'b011000111010111100_111011000010001010_00111110010110001;
8'd121: d = 53'b011000110001111110_111011111111100100_00101001110110111;
8'd122: d = 53'b011000101010100111_111100101000111110_00011110000011100;
8'd123: d = 53'b011000100100010110_111101000110110010_00010110101000110;
8'd124: d = 53'b011001010110100001_111011000111010100_00111101011000001;
8'd125: d = 53'b011001001101101100_111100000011110001_00101001001100110;
8'd126: d = 53'b011001000110011100_111100101100100010_00011101100101001;
8'd127: d = 53'b011001000000010011_111101001001111000_00010110010001110;
8'd128: d = 53'b011001110001101001_111011001100001111_00111100011100111;
8'd129: d = 53'b011001101000111101_111100000111110010_00101000100100101;
8'd130: d = 53'b011001100001110101_111100101111111011_00011101001000001;
8'd131: d = 53'b011001011011110010_111101001100110100_00010101111011110;
8'd132: d = 53'b011010001100010110_111011010000111100_00111011100100001;
8'd133: d = 53'b011010000011110011_111100001011100111_00100111111110010;
8'd134: d = 53'b011001111100110010_111100110011001001_00011100101100011;
8'd135: d = 53'b011001110110110101_111101001111100111_00010101100110101;
8'd136: d = 53'b011010100110101010_111011010101011011_00111010101101111;
8'd137: d = 53'b011010011110001111_111100001111010001_00100111011001101;
8'd138: d = 53'b011010010111010101_111100110110001111_00011100010001111;
8'd139: d = 53'b011010010001011101_111101010010010010_00010101010010101;
8'd140: d = 53'b011011000000100101_111011011001101110_00111001111001110;
8'd141: d = 53'b011010111000010010_111100010010110001_00100110110110011;
8'd142: d = 53'b011010110001011110_111100111001001100_00011011111000011;
8'd143: d = 53'b011010101011101100_111101010100110110_00010100111111010;
8'd144: d = 53'b011011011010001001_111011011101110110_00111001000111110;
8'd145: d = 53'b011011010001111101_111100010110000111_00100110010100100;
8'd146: d = 53'b011011001011001111_111100111100000001_00011011100000000;
8'd147: d = 53'b011011000101100010_111101010111010011_00010100101100111;
8'd148: d = 53'b011011110011010110_111011100001110011_00111000010111101;
8'd149: d = 53'b011011101011010001_111100011001010101_00100101110100000;
8'd150: d = 53'b011011100100101001_111100111110101111_00011011001000100;
8'd151: d = 53'b011011011111000010_111101011001101010_00010100011011000;
8'd152: d = 53'b011100001100001101_111011100101100111_00110111101001100;
8'd153: d = 53'b011100000100001111_111100011100011011_00100101010100110;
8'd154: d = 53'b011011111101101101_111101000001010110_00011010110001111;
8'd155: d = 53'b011011111000001010_111101011011111010_00010100001010000;
8'd156: d = 53'b011100100100110000_111011101001010001_00110110111100111;
8'd157: d = 53'b011100011100111000_111100011111011001_00100100110110110;
8'd158: d = 53'b011100010110011100_111101000011110110_00011010011100010;
8'd159: d = 53'b011100010000111110_111101011110000101_00010011111001101;
8'd160: d = 53'b011100111100111110_111011101100110010_00110110010010000;
8'd161: d = 53'b011100110101001101_111100100010001111_00100100011001110;
8'd162: d = 53'b011100101110110110_111101000110010000_00011010000111010;
8'd163: d = 53'b011100101001011100_111101100000001010_00010011101001110;
8'd164: d = 53'b011101010100111001_111011110000001011_00110101101000101;
8'd165: d = 53'b011101001101001110_111100100101000000_00100011111101110;
8'd166: d = 53'b011101000110111100_111101001000100101_00011001110011001;
8'd167: d = 53'b011101000001100111_111101100010001010_00010011011010100;
8'd168: d = 53'b011101101100100001_111011110011011100_00110101000000101;
8'd169: d = 53'b011101100100111101_111100100111101001_00100011100010111;
8'd170: d = 53'b011101011110101111_111101001010110100_00011001011111101;
8'd171: d = 53'b011101011001011110_111101100100000110_00010011001011110;
8'd172: d = 53'b011110000011111000_111011110110100110_00110100011010000;
8'd173: d = 53'b011101111100011001_111100101010001101_00100011001000110;
8'd174: d = 53'b011101110110010000_111101001100111110_00011001001100111;
8'd175: d = 53'b011101110001000011_111101100101111110_00010010111101101;
8'd176: d = 53'b011110011010111101_111011111001101001_00110011110100110;
8'd177: d = 53'b011110010011100100_111100101100101011_00100010101111100;
8'd178: d = 53'b011110001101011111_111101001111000011_00011000111010110;
8'd179: d = 53'b011110001000010110_111101100111110001_00010010101111111;
8'd180: d = 53'b011110110001110001_111011111100100101_00110011010000101;
8'd181: d = 53'b011110101010011101_111100101111000100_00100010010111001;
8'd182: d = 53'b011110100100011101_111101010001000100_00011000101001001;
8'd183: d = 53'b011110011111011000_111101101001100000_00010010100010100;
8'd184: d = 53'b011111001000010110_111011111111011011_00110010101101101;
8'd185: d = 53'b011111000001000111_111100110001011000_00100001111111101;
8'd186: d = 53'b011110111011001011_111101010011000000_00011000011000001;
8'd187: d = 53'b011110110110001001_111101101011001100_00010010010101110;
8'd188: d = 53'b011111011110101010_111100000010001100_00110010001011110;
8'd189: d = 53'b011111010111100000_111100110011100111_00100001101000110;
8'd190: d = 53'b011111010001101001_111101010100111001_00011000000111101;
8'd191: d = 53'b011111001100101010_111101101100110100_00010010001001010;
8'd192: d = 53'b011111110100101111_111100000100110111_00110001101011000;
8'd193: d = 53'b011111101101101010_111100110101110010_00100001010010101;
8'd194: d = 53'b011111100111110111_111101010110101101_00010111110111110;
8'd195: d = 53'b011111100010111100_111101101110011001_00010001111101010;
8'd196: d = 53'b100000001010100110_111100000111011101_00110001001011010;
8'd197: d = 53'b100000000011100101_111100110111111000_00100000111101010;
8'd198: d = 53'b011111111101110110_111101011000011110_00010111101000010;
8'd199: d = 53'b011111111000111110_111101101111111010_00010001110001100;
8'd200: d = 53'b100000100000001110_111100001001111101_00110000101100101;
8'd201: d = 53'b100000011001010010_111100111001111010_00100000101000100;
8'd202: d = 53'b100000010011100110_111101011010001100_00010111011001011;
8'd203: d = 53'b100000001110110010_111101110001011001_00010001100110010;
8'd204: d = 53'b100000110101101001_111100001100011001_00110000001111001;
8'd205: d = 53'b100000101110110001_111100111011111000_00100000010100101;
8'd206: d = 53'b100000101001001001_111101011011110110_00010111001011000;
8'd207: d = 53'b100000100100011000_111101110010110101_00010001011011011;
8'd208: d = 53'b100001001010110110_111100001110110000_00101111110011010;
8'd209: d = 53'b100001000100000010_111100111101110011_00100000000001101;
8'd210: d = 53'b100000111110011110_111101011101011101_00010110111101010;
8'd211: d = 53'b100000111001101111_111101110100001110_00010001010001000;
8'd212: d = 53'b100001011111110110_111100010001000010_00101111011001100;
8'd213: d = 53'b100001011001000111_111100111111101001_00011111101111111;
8'd214: d = 53'b100001010011100101_111101011111000001_00010110110000010;
8'd215: d = 53'b100001001110111010_111101110101100100_00010001000111001;
8'd216: d = 53'b100001110100101001_111100010011001110_00101111000011000;
8'd217: d = 53'b100001101101111110_111101000001011100_00011111100000001;
8'd218: d = 53'b100001101000100000_111101100000100010_00010110100100101;
8'd219: d = 53'b100001100011110111_111101110110111000_00010000111110001;
8'd220: d = 53'b100010001001010000_111100010101010100_00101110110010010;
8'd221: d = 53'b100010000010101001_111101000011001010_00011111010011101;
8'd222: d = 53'b100001111101001110_111101100001111111_00010110011011000;
8'd223: d = 53'b100001111000101000_111101111000001001_00010000110110100;
8'd224: d = 53'b100010011101101011_111100010111010010_00101110101100100;
8'd225: d = 53'b100010010111000111_111101000100110010_00011111001101001;
8'd226: d = 53'b100010010001110000_111101100011011000_00010110010101000;
8'd227: d = 53'b100010001101001101_111101111001010110_00010000110001010;
8'd228: d = 53'b100010110001111010_111100011001000101_00101110111011101;
8'd229: d = 53'b100010101011011010_111101000110010011_00011111010010001;
8'd230: d = 53'b100010100110000110_111101100100101100_00010110010110000;
8'd231: d = 53'b100010100001100101_111101111010100000_00010000110000101;
8'd232: d = 53'b100011000101111110_111100011010100111_00101111110100001;
8'd233: d = 53'b100010111111100010_111101000111101011_00011111101101110;
8'd234: d = 53'b100010111010010000_111101100101111001_00010110100100111;
8'd235: d = 53'b100010110101110010_111101111011100101_00010000111001000;
8'd236: d = 53'b100011011001110111_111100101000100000_00000000000000000;
8'd237: d = 53'b100011010011011110_111101010001001010_00000000000000000;
8'd238: d = 53'b100011001110010000_111101101100110110_00000000000000000;
8'd239: d = 53'b100011001001110100_111110000000111011_00000000000000000;
8'd240: d = 53'b100011101101100101_000000000000000000_00000000000000000;
8'd241: d = 53'b100011100111010000_000000000000000000_00000000000000000;
8'd242: d = 53'b100011100010000100_000000000000000000_00000000000000000;
8'd243: d = 53'b100011011101101011_000000000000000000_00000000000000000;
8'd244: d = 53'b100100100111110000_000000000000000000_00000000000000000;
8'd245: d = 53'b100100010100100001_000000000000000000_00000000000000000;
8'd246: d = 53'b100100000001001000_000000000000000000_00000000000000000;
8'd247: d = 53'b100011110101101101_000000000000000000_00000000000000000;
default: d = 53'd0;
endcase
end
 
 
// Output data
always @ (posedge clk) begin
c0 <= d[52:35];
c1 <= d[34:17];
c2 <= d[16:0];
end
 
 
endmodule
/gng/trunk/rtl/gng_ctg.v
0,0 → 1,97
//------------------------------------------------------------------------------
//
// gng_ctg.v
//
// This file is part of the Gaussian Noise Generator IP Core
//
// Description
// Maximally equidistributed combined Tausworthe generator with
// (k1,k2,k3) = (63,58,55); (q1,q2,q3) = (5,19,24); (s1,s2,s3) = (24,13,7).
// Period is approximately 2^176.
//
//------------------------------------------------------------------------------
//
// Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
//
// 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 source file is free software; you can redistribute it and/or modify it
// under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation; either version 2.1 of the License,
// or (at your option) any later version.
//
// This source is distributed in the hope that it will be useful, but
// WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
// License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this source; if not, download it from
// http://www.opencores.org/lgpl.shtml
//
//------------------------------------------------------------------------------
 
 
`timescale 1 ns / 1 ps
 
 
module gng_ctg #(
parameter INIT_Z1 = 64'd5030521883283424767,
parameter INIT_Z2 = 64'd18445829279364155008,
parameter INIT_Z3 = 64'd18436106298727503359
)
(
// System signals
input clk, // system clock
input rstn, // system synchronous reset, active low
 
// Data interface
input ce, // clock enable
output reg valid_out, // output data valid
output reg [63:0] data_out // output data
);
 
// Local variables
reg [63:0] z1, z2, z3;
wire [63:0] z1_next, z2_next, z3_next;
 
 
// Update state
assign z1_next = {z1[39:1], z1[58:34] ^ z1[63:39]};
assign z2_next = {z2[50:6], z2[44:26] ^ z2[63:45]};
assign z3_next = {z3[56:9], z3[39:24] ^ z3[63:48]};
 
always @ (posedge clk) begin
if (!rstn) begin
z1 <= INIT_Z1;
z2 <= INIT_Z2;
z3 <= INIT_Z3;
end
else if (ce) begin
z1 <= z1_next;
z2 <= z2_next;
z3 <= z3_next;
end
end
 
 
// Output data
always @ (posedge clk) begin
if (!rstn)
valid_out <= 1'b0;
else
valid_out <= ce;
end
 
always @ (posedge clk) begin
if (!rstn)
data_out <= 64'd0;
else
data_out <= z1_next ^ z2_next ^ z3_next;
end
 
 
endmodule
/gng/trunk/rtl/gng_smul_16_18.v
0,0 → 1,66
//------------------------------------------------------------------------------
//
// gng_smul_16_18.v
//
// This file is part of the Gaussian Noise Generator IP Core
//
// Description
// Signed multiplier 16-bit x 18-bit, delay 2 cycles.
//
//------------------------------------------------------------------------------
//
// Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
//
// 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 source file is free software; you can redistribute it and/or modify it
// under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation; either version 2.1 of the License,
// or (at your option) any later version.
//
// This source is distributed in the hope that it will be useful, but
// WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
// License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this source; if not, download it from
// http://www.opencores.org/lgpl.shtml
//
//------------------------------------------------------------------------------
 
 
`timescale 1 ns / 1 ps
 
 
module gng_smul_16_18 (
// System signals
input clk, // system clock
 
// Data interface
input [15:0] a, // multiplicand
input [17:0] b, // multiplicator
output [33:0] p // result
);
 
// Behavioral model
reg signed [15:0] a_reg;
reg signed [17:0] b_reg;
reg signed [33:0] prod;
 
always @ (posedge clk) begin
a_reg <= a;
b_reg <= b;
end
 
always @ (posedge clk) begin
prod <= a_reg * b_reg;
end
 
assign p = prod;
 
 
endmodule
/gng/trunk/c/taus176.h
0,0 → 1,54
/*
* Maximally equidistributed combined Tausworthe generator
* (k1,k2,k3) = (63,58,55); (q1,q2,q3) = (5,19,24); (s1,s2,s3) = (24,13,7)
* Period is approximately 2^176
*/
 
/*
* Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
*
* 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 source file is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 2.1 of the License,
* or (at your option) any later version.
*
* This source is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
* License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this source; if not, download it from
* http://www.opencores.org/lgpl.shtml
*/
 
 
#ifndef TAUS176_H
#define TAUS176_H
 
#ifdef __cplusplus
extern "C" {
#endif
 
/* Generator internal state */
typedef struct {
unsigned long long z1, z2, z3;
} taus_state_t;
 
/* Update state */
unsigned long long taus_get(taus_state_t *state);
 
/* Set state using seed */
void taus_set(taus_state_t *state, unsigned long s);
 
 
#ifdef __cplusplus
}
#endif
 
#endif
/gng/trunk/c/icdf.c
0,0 → 1,176
/*
* Piecewise polynomial approximation of
* inverse of the normal cumulative distribution function (CDF)
*/
 
/*
* Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
*
* 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 source file is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 2.1 of the License,
* or (at your option) any later version.
*
* This source is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
* License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this source; if not, download it from
* http://www.opencores.org/lgpl.shtml
*/
 
 
#include "icdf.h"
 
 
/* Coefficients table */
static const long C0[248] = {
11049, 8007, 5220, 2577, 18846, 16547, 14535, 12721, 25134, 23229,
21594, 20150, 30518, 28863, 27458, 26231, 35288, 33808, 32562, 31479,
39608, 38260, 37130, 36152, 43582, 42336, 41296, 40399, 47277, 46115,
45147, 44314, 50745, 49651, 48742, 47963, 54020, 52985, 52126, 51390,
57132, 56147, 55331, 54632, 60101, 59160, 58381, 57715, 62945, 62043,
61296, 60659, 65679, 64811, 64093, 63481, 68314, 67476, 66784, 66194,
70859, 70049, 69381, 68811, 73323, 72538, 71891, 71340, 75714, 74952,
74324, 73790, 78036, 77296, 76686, 76167, 80297, 79576, 78982, 78477,
82500, 81797, 81218, 80726, 84649, 83963, 83398, 82918, 86748, 86078,
85526, 85057, 88800, 88145, 87606, 87147, 90809, 90167, 89640, 89191,
92777, 92148, 91631, 91192, 94706, 94090, 93583, 93152, 96599, 95994,
95496, 95074, 98457, 97863, 97374, 96960, 100282, 99698, 99219, 98811,
102076, 101502, 101031, 100630, 103841, 103276, 102812, 102419, 105577, 105021,
104565, 104178, 107286, 106739, 106290, 105909, 108970, 108431, 107989, 107613,
110629, 110098, 109662, 109292, 112265, 111741, 111311, 110946, 113878, 113361,
112937, 112578, 115469, 114959, 114541, 114186, 117040, 116536, 116124, 115774,
118590, 118093, 117686, 117340, 120121, 119630, 119228, 118887, 121633, 121149,
120751, 120414, 123128, 122649, 122256, 121923, 124605, 124132, 123743, 123414,
126065, 125597, 125213, 124888, 127510, 127047, 126667, 126345, 128938, 128480,
128105, 127786, 130351, 129898, 129527, 129212, 131750, 131301, 130934, 130622,
133134, 132690, 132326, 132018, 134505, 134065, 133705, 133400, 135862, 135426,
135070, 134767, 137206, 136775, 136421, 136122, 138537, 138110, 137760, 137463,
139856, 139433, 139086, 138792, 141163, 140743, 140400, 140109, 142458, 142042,
141702, 141413, 143742, 143330, 142992, 142706, 145015, 144606, 144272, 143988,
146277, 145872, 145540, 145259, 150000, 148769, 147528, 146797
};
 
static const long C1[248] = {
-102514, -92199, -86162, -82951, -79070, -68105, -60693, -55396, -66134, -55839,
-48783, -43639, -57755, -48215, -41670, -36890, -51803, -42932, -36856, -32421,
-47313, -39012, -33338, -29203, -43778, -35964, -30631, -26751, -40907, -33511,
-28470, -24807, -38519, -31483, -26695, -23220, -36492, -29774, -25206, -21893,
-34747, -28307, -23933, -20765, -33223, -27032, -22831, -19789, -31878, -25911,
-21864, -18936, -30681, -24915, -21007, -18182, -29606, -24023, -20242, -17509,
-28634, -23218, -19552, -16903, -27750, -22488, -18927, -16356, -26942, -21821,
-18357, -15857, -26198, -21208, -17835, -15400, -25512, -20644, -17354, -14980,
-24876, -20121, -16909, -14591, -24285, -19636, -16496, -14231, -23733, -19184,
-16111, -13896, -23217, -18760, -15752, -13583, -22732, -18364, -15415, -13290,
-22276, -17991, -15099, -13015, -21846, -17639, -14801, -12756, -21440, -17307,
-14520, -12512, -21055, -16993, -14253, -12281, -20690, -16695, -14001, -12062,
-20342, -16412, -13762, -11854, -20012, -16143, -13534, -11656, -19697, -15886,
-13317, -11468, -19396, -15641, -13111, -11289, -19109, -15407, -12913, -11118,
-18834, -15183, -12724, -10954, -18570, -14969, -12543, -10797, -18317, -14763,
-12369, -10646, -18073, -14565, -12202, -10502, -17839, -14375, -12042, -10363,
-17614, -14193, -11888, -10230, -17397, -14016, -11739, -10102, -17188, -13847,
-11596, -9978, -16986, -13683, -11458, -9858, -16791, -13525, -11325, -9743,
-16603, -13372, -11196, -9632, -16421, -13224, -11072, -9524, -16244, -13081,
-10951, -9420, -16073, -12942, -10835, -9319, -15907, -12808, -10722, -9222,
-15747, -12678, -10612, -9127, -15591, -12552, -10506, -9035, -15440, -12429,
-10403, -8946, -15294, -12311, -10303, -8860, -15154, -12196, -10206, -8776,
-15020, -12086, -10113, -8695, -14894, -11982, -10024, -8618, -14779, -11885,
-9940, -8544, -14681, -11797, -9863, -8475, -13792, -11190, -9418, -8133,
0, 0, 0, 0, 0, 0, 0, 0
};
 
static const long C2[248] = {
83840, 48883, 25920, 8147, 88988, 59916, 42707, 31577, 83526, 57019,
41464, 31523, 77411, 52885, 38533, 29386, 71990, 49106, 35743, 27241,
67363, 45865, 33332, 25372, 63422, 43107, 31282, 23780, 60040, 40746,
29530, 22422, 57109, 38706, 28020, 21254, 54545, 36926, 26705, 20239,
52279, 35358, 25549, 19349, 50262, 33965, 24525, 18561, 48452, 32718,
23609, 17858, 46818, 31593, 22785, 17226, 45333, 30573, 22038, 16654,
43976, 29643, 21358, 16134, 42731, 28790, 20735, 15658, 41583, 28005,
20163, 15221, 40521, 27279, 19634, 14817, 39534, 26606, 19143, 14444,
38614, 25978, 18687, 14096, 37754, 25392, 18261, 13772, 36948, 24844,
17862, 13468, 36190, 24328, 17488, 13184, 35477, 23843, 17136, 12916,
34803, 23385, 16804, 12664, 34165, 22952, 16490, 12426, 33561, 22542,
16193, 12200, 32987, 22153, 15911, 11986, 32441, 21783, 15643, 11783,
31921, 21431, 15388, 11590, 31425, 21094, 15145, 11406, 30951, 20773,
14913, 11230, 30497, 20466, 14691, 11061, 30063, 20173, 14479, 10901,
29646, 19891, 14275, 10746, 29246, 19620, 14080, 10599, 28861, 19360,
13892, 10456, 28492, 19110, 13711, 10320, 28135, 18870, 13538, 10189,
27792, 18638, 13370, 10062, 27461, 18414, 13209, 9940, 27141, 18199,
13053, 9822, 26832, 17990, 12903, 9709, 26534, 17788, 12758, 9599,
26245, 17593, 12617, 9492, 25965, 17405, 12481, 9390, 25694, 17222,
12349, 9290, 25432, 17045, 12222, 9194, 25178, 16874, 12098, 9100,
24933, 16708, 11979, 9010, 24697, 16549, 11864, 8923, 24474, 16397,
11754, 8840, 24268, 16255, 11650, 8761, 24088, 16129, 11557, 8689,
23954, 16029, 11480, 8628, 23908, 15977, 11432, 8586, 24029, 16017,
11440, 8581, 24481, 16238, 11559, 8648, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0
};
 
 
/* Calculate Inverse of the normal CDF */
long icdf(unsigned long long n)
{
unsigned long long t;
int i;
unsigned num_lzd;
unsigned addr;
long c0, c1, c2;
long x;
long long y;
int carry;
 
t = n;
num_lzd = 0;
for (i = 0; i < 61; i++) {
if (t & 0x8000000000000000ULL)
break;
else {
++num_lzd;
t <<= 1;
}
}
addr = num_lzd << 2;
if (n & 2ULL)
addr += 2;
if (n & 4ULL)
++addr;
 
c0 = C0[addr];
c1 = C1[addr];
c2 = C2[addr];
 
if (num_lzd <= 60)
n &= ~(1ULL << (63 - num_lzd));
 
t = n >> 3;
x = 0;
for (i = 0; i < 15; i++) {
x <<= 1;
if (t & 1ULL)
++x;
t >>= 1;
}
 
y = (long long)c2 * (long long)x;
y += ((long long)c1 << 19);
y >>= 20;
y *= (long long)x;
y >>= 19;
y += (long long)c0;
carry = (y & 4ULL) ? 1 : 0;
y >>= 3;
y += carry;
if (n & 1ULL)
y = -y;
 
return (long)y;
}
/gng/trunk/c/taus176.c
0,0 → 1,71
/* Maximally equidistributed combined Tausworthe generator */
 
/*
* Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
*
* 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 source file is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 2.1 of the License,
* or (at your option) any later version.
*
* This source is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
* License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this source; if not, download it from
* http://www.opencores.org/lgpl.shtml
*/
#include "taus176.h"
 
 
/* Update state */
unsigned long long taus_get(taus_state_t *state)
{
unsigned long long b;
b = (((state->z1 << 5) ^ state->z1) >> 39);
state->z1 = (((state->z1 & 18446744073709551614ULL) << 24) ^ b);
b = (((state->z2 << 19) ^ state->z2) >> 45);
state->z2 = (((state->z2 & 18446744073709551552ULL) << 13) ^ b);
b = (((state->z3 << 24) ^ state->z3) >> 48);
state->z3 = (((state->z3 & 18446744073709551104ULL) << 7) ^ b);
return (state->z1 ^ state->z2 ^ state->z3);
}
 
 
/* Set state using seed */
#define LCG(n) (4294967291ULL * n)
 
void taus_set(taus_state_t *state, unsigned long s)
{
if (s == 0) s = 1; /* default seed is 1 */
state->z1 = LCG(s);
if (state->z1 < 2ULL) state->z1 += 2ULL;
state->z2 = LCG(state->z1);
if (state->z2 < 64ULL) state->z2 += 64ULL;
state->z3 = LCG(state->z2);
if (state->z3 < 512ULL) state->z3 += 512ULL;
/* "warm it up" */
taus_get(state);
taus_get(state);
taus_get(state);
taus_get(state);
taus_get(state);
taus_get(state);
taus_get(state);
taus_get(state);
taus_get(state);
taus_get(state);
}
/gng/trunk/c/icdf.h
0,0 → 1,45
/*
* Piecewise polynomial approximation of
* inverse of the normal cumulative distribution function (CDF)
*/
 
/*
* Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
*
* 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 source file is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation; either version 2.1 of the License,
* or (at your option) any later version.
*
* This source is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
* License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this source; if not, download it from
* http://www.opencores.org/lgpl.shtml
*/
 
 
#ifndef ICDF_H
#define ICDF_H
 
#ifdef __cplusplus
extern "C" {
#endif
 
/* Calculate Inverse of the normal CDF */
long icdf(unsigned long long x);
 
 
#ifdef __cplusplus
}
#endif
 
#endif
/gng/trunk/tb/tb_gng_lzd.sv
0,0 → 1,98
// Testbench for gng_lzd
 
 
`timescale 1 ns / 1 ps
 
 
module tb_gng_lzd;
 
// Parameters
parameter ClkPeriod = 10;
parameter N = 1000000;
 
 
// Signals
logic [60:0] data_in;
logic [5:0] data_out;
logic clk;
 
 
// Random data class
class RandData;
rand bit [60:0] x;
endclass
 
 
// Local variables
int num_all;
int num_error;
int res;
RandData d;
 
 
// Instances
gng_lzd u_gng_lzd (.*);
 
 
// System signals
initial begin
clk <= 1'b0;
forever #(ClkPeriod/2) clk = ~clk;
end
 
 
// Self-test task
task test_num(bit [60:0] din);
 
int i;
int lzd_num;
 
lzd_num = 0;
for (i = 60; i >= 0; i--) begin
if (din[i] == 0)
lzd_num++;
else
break;
end
 
@(posedge clk);
data_in = din;
#(ClkPeriod/2);
num_all++;
if (lzd_num != data_out) begin
num_error++;
$write("Error: %b, Ref = %0d, Res = %0d\n", din, lzd_num, data_out);
end
 
endtask
 
 
// Main process
initial begin
// Initialize
data_in = 0;
num_all = 0;
num_error = 0;
d = new;
 
// Direct test
test_num({61{1'b0}}); // all 0s
test_num({61{1'b1}}); // all 1s
 
// Random test
repeat(N) begin
res = d.randomize();
test_num(d.x);
end
 
// Result
#(ClkPeriod*5);
if (num_error == 0) $write("PASSED!");
else $write("FAILED!");
$write(" Total(%0d) / Error(%0d)\n", num_all, num_error);
 
$stop;
end
 
 
endmodule
/gng/trunk/tb/tb_gng_ctg.sv
0,0 → 1,72
// Testbench for gng_ctg
 
 
`timescale 1 ns / 1 ps
 
 
module tb_gng_ctg;
 
// Parameters
parameter ClkPeriod = 10;
parameter N = 1000000;
 
 
// Local variables
logic clk;
logic rstn;
logic ce;
logic valid_out;
logic [63:0] data_out;
 
 
// Instances
gng_ctg #(
.INIT_Z1(64'd5030521883283424767),
.INIT_Z2(64'd18445829279364155008),
.INIT_Z3(64'd18436106298727503359)
)
u_gng_ctg (.*);
 
 
// System signals
initial begin
clk <= 1'b0;
forever #(ClkPeriod/2) clk = ~clk;
end
 
initial begin
rstn <= 1'b0;
#(ClkPeriod*2) rstn = 1'b1;
end
 
 
// Main process
int fpOut;
 
initial begin
fpOut = $fopen("ctg_data_out.txt", "w");
 
ce = 0;
 
#(ClkPeriod*10)
repeat (N) begin
@(posedge clk);
ce = 1;
end
@(posedge clk);
ce = 0;
 
#(ClkPeriod*10)
$fclose(fpOut);
$stop;
end
 
 
// Record data
always_ff @ (negedge clk) begin
if (valid_out)
$fwrite(fpOut, "%0d\n", data_out);
end
 
 
endmodule
/gng/trunk/tb/tb_gng.sv
0,0 → 1,105
//------------------------------------------------------------------------------
//
// tb_gng.sv
//
// This file is part of the Gaussian Noise Generator IP Core
//
// Description
// Systemverilog testbench for module gng. Generate noise sequences of
// length N and output to file.
//
//------------------------------------------------------------------------------
//
// Copyright (C) 2014, Guangxi Liu <guangxi.liu@opencores.org>
//
// 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 source file is free software; you can redistribute it and/or modify it
// under the terms of the GNU Lesser General Public License as published by
// the Free Software Foundation; either version 2.1 of the License,
// or (at your option) any later version.
//
// This source is distributed in the hope that it will be useful, but
// WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
// or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
// License for more details.
//
// You should have received a copy of the GNU Lesser General Public License
// along with this source; if not, download it from
// http://www.opencores.org/lgpl.shtml
//
//------------------------------------------------------------------------------
 
 
`timescale 1 ns / 1 ps
 
 
module tb_gng;
 
// Parameters
parameter ClkPeriod = 10.0;
parameter N = 10000000;
 
 
// Local variables
logic clk;
logic rstn;
logic ce;
logic valid_out;
logic [15:0] data_out;
 
 
// Instances
gng #(
.INIT_Z1(64'd5030521883283424767),
.INIT_Z2(64'd18445829279364155008),
.INIT_Z3(64'd18436106298727503359)
)
u_gng (.*);
 
 
// System signals
initial begin
clk <= 1'b0;
forever #(ClkPeriod/2) clk = ~clk;
end
 
initial begin
rstn <= 1'b0;
#(ClkPeriod*2) rstn = 1'b1;
end
 
 
// Main process
int fpOut;
 
initial begin
fpOut = $fopen("gng_data_out.txt", "w");
 
ce = 0;
 
#(ClkPeriod*10)
repeat (N) begin
@(posedge clk);
ce = 1;
end
@(posedge clk);
ce = 0;
 
#(ClkPeriod*20)
$fclose(fpOut);
$stop;
end
 
 
// Record data
always_ff @ (negedge clk) begin
if (valid_out)
$fwrite(fpOut, "%0d\n", $signed(data_out));
end
 
 
endmodule

powered by: WebSVN 2.1.0

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