/* -------------------------------------------------------------------- -- -- -- Copyright©2002 by the Institute of Electrical and Electronics Engineers, Inc. -- Three Park Avenue -- New York, NY 10016-5997, USA -- All rights reserved. -- -- This document is an unapproved draft of a proposed IEEE Standard. As such, -- this document is subject to change. USE AT YOUR OWN RISK! Because this -- is an unapproved draft, this document must not be utilized for any -- conformance/compliance purposes. Permission is hereby granted for IEEE -- Standards Committee participants to reproduce this document for purposes -- of IEEE standardization activities only. Prior to submitting this document -- to another standards development organization for standardization -- activities, permission must first be obtained from the Manager, Standards -- Licensing and Contracts, IEEE Standards Activities Department. Other -- entities seeking permission to reproduce this document, in whole or in -- part, must obtain permission from the Manager, Standards Licensing and -- Contracts, IEEE Standard Activities Department. -- -- IEEE Standards Activities Department -- Standards Licensing and Contracts -- 445 Hoes Lane, P.O. Box 1331 -- Piscataway, NJ 08855-1331, USA -- -- Title : FPHDL64_PKG < IEEE std # 1076.3 > -- -- Developers: VHDL Synthesis working group, PAR 1076.3 -- -- Purpose : Basic floating point operations for Verilog -- Calls the VHDL to perform operations. -- -- Limitation: Needs to co-simulate with VHDL floating point packages. -- -- -------------------------------------------------------------------- -- Last Modified $Date: 2003-10-20 15:01:08-04 $ $Id: fphdl64_vhdlcos_pkg.v,v 1.7 2003-10-20 15:01:08-04 bishop Exp $ -- modification history : $Log: fphdl64_vhdlcos_pkg.v,v $ -- modification history : Revision 1.7 2003-10-20 15:01:08-04 bishop -- modification history : Added a parameter to turn error checking off -- modification history : -- modification history : Revision 1.6 2003-07-29 15:34:01-04 bishop -- modification history : Added oneoverx, dividebyp2, polar_to_complex and complex_to_polar modules -- modification history : -- modification history : Revision 1.5 2003-01-15 09:04:30-05 bishop -- modification history : Modified to use a generic VHDL package -- modification history : -- modification history : Revision 1.4 2003-01-03 13:15:05-05 bishop -- modification history : Changed the parameter "size" to "width". -- modification history : -- modification history : Revision 1.3 2003-01-02 16:44:32-05 bishop -- modification history : Updated for the new parameters -- modification history : -- modification history : Revision 1.2 2003-01-02 09:41:57-05 bishop -- modification history : Updated taking into account that 64 bit is the percision of the -- modification history : Verilog "real" type. -- modification history : -- modification history : Revision 1.1 2002-12-31 16:28:59-05 bishop -- modification history : Initial revision -- modification history : -- -------------------------------------------------------------------- */ /* This version of the Verilog packages called the VHDL packages. */ /* suggested parameters parameter fraction_width = 52; //length of FP fraction parameter exponent_width = 11; //length of FP exponent parameter check_error = 1; //check error = true (turn NAN checking on) parameter ieee_extend = 1; //Use IEEE extended FP = true parameter round_style = 0; //rounding option = round_nearest */ /* Author: David Bishop dbishop@vhdl.org */ /* This version of the Verilog packages called the VHDL packages. */ module fp64_abs (res, arg); // absolute number output [63:0] res; input [63:0] arg; absolute_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_abs module fp64_neg (res, arg); // unary negative output [63:0] res; input [63:0] arg; negative_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_neg module fp64_add (res, l, r); // addition (l + r) output [63:0] res; input [63:0] l, r; addition_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_add module fp64_add_c (res_r, res_i, l_r, l_i, r_r, r_i); // complex add output [63:0] res_r, res_i; // _r = real _i = imaginary input [63:0] l_r, l_i, r_r, r_i; complex_add_ea #(52,11,1,1,0) u1 ( .res_r(res_r), .res_i(res_i), .l_r(l_r), .l_i(l_i), .r_r(r_r), .r_i(r_i)); endmodule // fp64_add_c module fp64_sub (res, l, r); // subtraction (l - r) output [63:0] res; input [63:0] l, r; subtract_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_sub module fp64_sub_c (res_r, res_i, l_r, l_i, r_r, r_i); // complex subtraction output [63:0] res_r, res_i; // _r = real _i = imaginary input [63:0] l_r, l_i, r_r, r_i; complex_subtract_ea #(52,11,1,1,0) u1 ( .res_r(res_r), .res_i(res_i), .l_r(l_r), .l_i(l_i), .r_r(r_r), .r_i(r_i)); endmodule // fp64_sub_c module fp64_mul (res, l, r); // multiplation (l * r) output [63:0] res; input [63:0] l, r; multiply_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_mul module fp64_mul_c (res_r, res_i, l_r, l_i, r_r, r_i); // complex multiplicaiton output [63:0] res_r, res_i; // _r = real _i = imaginary input [63:0] l_r, l_i, r_r, r_i; complex_multiply_ea #(52,11,1,1,0) u1 ( .res_r(res_r), .res_i(res_i), .l_r(l_r), .l_i(l_i), .r_r(r_r), .r_i(r_i)); endmodule // fp64_mul_c module fp64_div (res, l, r); // division (l / r) output [63:0] res; input [63:0] l, r; divide_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_div module fp64_div_c (res_r, res_i, l_r, l_i, r_r, r_i); // complex division output [63:0] res_r, res_i; // _r = real _i = imaginary input [63:0] l_r, l_i, r_r, r_i; complex_divide_ea #(52,11,1,1,0) u1 ( .res_r(res_r), .res_i(res_i), .l_r(l_r), .l_i(l_i), .r_r(r_r), .r_i(r_i)); endmodule // fp64_div_c module fp64_oneoverx (res, arg); // 1/arg output [63:0] res; input [63:0] arg; oneoverx_ea #(23,8,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_oneoverx module fp64_divbyp2 (res, l, r); // division (l / r) output [63:0] res; input [63:0] l, r; dividebyp2_ea #(23,8,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_divbyp2 module fp64_complex_to_polar (res_mag, res_angle, arg_r, arg_i); // complex_to_plar output [63:0] res_mag, res_angle; input [63:0] arg_r, arg_i; // _r = real _i = imaginary complex_to_polar_ea #(23,8,1,1,0) u1 ( .res_mag(res_mag), .res_angle(res_angle), .arg_r(arg_r), .arg_i(arg_i)); endmodule // fp64_complex_to_polar module fp64_polar_to_complex (res_r, res_i, arg_mag, arg_angle); // polar to complex output [63:0] res_r, res_i; // _r = real _i = imaginary input [63:0] arg_mag, arg_angle; polar_to_complex_ea #(23,8,1,1,0) u1 ( .res_r(res_r), .res_i(res_i), .arg_mag(arg_mag), .arg_angle(arg_angle)); endmodule // fp64_complex_to_polar module fp64_rem (res, l, r); // remainder output [63:0] res; input [63:0] l, r; remainder_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_rem module fp64_sqrt (res, arg); // square root output [63:0] res; input [63:0] arg; square_root_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_sqrt module fp64_log (res, base, arg); // log output [63:0] res; input [63:0] base; input [63:0] arg; log_ea #(52,11,1,1,0) u1 ( .res(res), .base(base), .arg(arg)); endmodule // fp64_log module fp64_ln (res, arg); // ln output [63:0] res; input [63:0] arg; natural_log_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_ln module fp64_pow_fp (res, l, r); // l**r, where l and r are fp64 output [63:0] res; input [63:0] l, r; power_of_fp_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_pow_fp module fp64_pow (res, l, r); // l**r, where l is fp64 and r is integer output [63:0] res; input [63:0] r; // integer input [63:0] l; power_of_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_pow module fp64_sin (res, arg); // sin output [63:0] res; input [63:0] arg; sine_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_sin module fp64_cos (res, arg); // cos output [63:0] res; input [63:0] arg; cosine_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_cos module fp64_tan (res, arg); // tan output [63:0] res; input [63:0] arg; tangent_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_tan module fp64_arc_sin (res, arg); // arcsin output [63:0] res; input [63:0] arg; arc_sine_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_arc_sin module fp64_arc_cos (res, arg); // arccos output [63:0] res; input [63:0] arg; arc_cosine_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_arc_cos module fp64_arc_tan (res, arg); // arctan output [63:0] res; input [63:0] arg; arc_tangent_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_arc_tan module fp64_equ (res, l, r); // = output res; input [63:0] l, r; equal_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_equ module fp64_not_equ (res, l, r); // != output res; input [63:0] l, r; not_equal_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_not_equ module fp64_gteq (res, l, r); // >= output res; input [63:0] l, r; greater_than_or_equal_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_gteq module fp64_lteq (res, l, r); // <= output res; input [63:0] l, r; less_than_or_equal_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_lteq module fp64_gt (res, l, r); // > output res; input [63:0] l, r; greater_than_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_gt module fp64_lt (res, l, r); // < output res; input [63:0] l, r; less_than_ea #(52,11,1,1,0) u1 ( .res(res), .l(l), .r(r)); endmodule // fp64_lt module integer_to_fp64 (res, arg); // integer input, fp64 output output [63:0] res; // floating point input [63:0] arg; // integer integer_to_fp_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // to_fp64 /* module real_to_fp64 (res, arg); // real input, fp64 output output [63:0] res; // floating point input [63:0] arg; // Verilog real number real_to_fp64_ea u1 ( .res(res), .arg(arg)); endmodule // to_fp64 use: assign res = $realtobits(arg); from Cadence's Verilog-XL Reference Manual chap. 11 : "Real Numbers in Port Connections The real data type cannot be directly connected to a port. Rather it must be connected indirectly, as shown in the following example. The system functions $realtobits and $bitstoreal are used for passing the bit patterns across the module ports. module driver (net_r); output net_r; real r; wire [64:1] net_r = $realtobits(r); endmodule module receiver (net_r); input net_r; wire [64:1] net_r; real r; initial assign r =$bitstoreal(net_r); endmodule " */ module signed_to_fp64 (res, arg);// signed, parameter: width parameter width = 32; output [63:0] res; // floating point input [width-1:0] arg; signed_to_fp_ea #(width,52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // signed_to_fp64 module unsigned_to_fp64 (res, arg); // unsigned, parameter: width parameter width = 32; output [63:0] res; // floating point input [width-1:0] arg; unsigned_to_fp_ea #(width,52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // unsigned_to_fp64 module fp64_to_integer (res, arg); // fp64 to integer output [63:0] res; // integer input [63:0] arg; // floating point fp_to_integer_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // to_integer module fp64_to_unsigned (res, arg); // fp64 to unsigned, parameter: width parameter width = 32; output [width-1:0] res; // floating point input [63:0] arg; fp_to_unsigned_ea #(width,52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_to_unsigned module fp64_to_signed (res, arg); // fp64 to signed, parameter: width parameter width = 32; output [width-1:0] res; // floating point input [63:0] arg; fp_to_signed_ea #(width,52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_to_signed /* module fp64_to_real (res, arg); // fp64 to real output [64:1] res; // Verilog real number input [63:0] arg; // floating point fp64_to_real_ea u1 ( .res(res), .arg(arg)); endmodule // fp64_to_real use: assign res = $bitstoreal(arg); See real_to_fp64 above */ module fp64_Copysign (res, x, y); // copies sign of x to y output [63:0] res; input [63:0] x, y; Copysign_ea #(52,11,1,1,0) u1 ( .res(res), .x(x), .y(y)); endmodule // fp64_Copysign module fp64_Scalb (res, y, n); // multiplies y by 2**n (where n is an integer) output [63:0] res; input [63:0] y; input [63:0] n; Scalb_ea #(52,11,1,1,0) u1 ( .res(res), .y(y), .n(n)); endmodule // fp64_Scalb module fp64_Logb (res, arg); // returns the log (base 2) of arg output [63:0] res; // integer input [63:0] arg; Logb_ea #(52,11,1,1,0) u1 ( .res(res), .arg(arg)); endmodule // fp64_Logb module fp64_Nextafter (res, x, y); // Gives you the next logical number after x output [63:0] res; input [63:0] x, y; Nextafter_ea #(52,11,1,1,0) u1 ( .res(res), .x(x), .y(y)); endmodule // fp64_Nextafter module fp64_Finite (res, x); // returns "1" if x is not infinity. output res; input [63:0] x; Finite_ea #(52,11,1,1,0) u1 ( .res(res), .x(x)); endmodule // fp64_Finite module fp64_Isnan (res, x); // returns "1" is x in any type of NAN output res; input [63:0] x; Isnan_ea #(52,11,1,1,0) u1 ( .res(res), .x(x)); endmodule // fp64_Isnan module fp64_Class (res, x); output [3:0] res; input [63:0] x; Class_ea #(52,11,1,1,0) u1 ( .res(res), .x(x)); endmodule // fp64_Class module fp64_Unordered (res, x, y); // returns "1" if x or y is a NAN. output res; input [63:0] x, y; Unordered_ea #(52,11,1,1,0) u1 ( .res(res), .x(x), .y(y)); endmodule // fp64_Unordered