extension_pack

M

My Name

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : natural := 30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := CFT_BASE_SIZE*4;


------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural;

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value
function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that


-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector;
-- synopsys translate_on

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency

-- synopsys translate_off
function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
function to_string(realVal : real) return string; -- returns a string value for an real value passed
function to_string(vectorVal : std_logic_vector) return string;
-- synopsys translate_on

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
-- synthesis translate_off
--alias cft is count_for_time[string,string return std_logic_vector]; -- synplify doesn't like "[" or "]"
--alias cfth is count_for_time_high[string,string return integer];
-- synthesis translate_on
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce(timeVar/freqStrVar)'length;
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count_for_time_high)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;



-- synthesizable version
--function dpfi(intVal : integer) return natural is
-- variable resultVar : natural;
--begin
-- if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
-- resultVar := 10;
-- elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
-- resultVar := 9;
-- elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
-- resultVar := 8;
-- elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
-- resultVar := 7;
-- elsif (intVal <= -100_000 or intVal >= 100_000) then
-- resultVar := 6;
-- elsif (intVal <= -10_000 or intVal >= 10_000) then
-- resultVar := 5;
-- elsif (intVal <= -1_000 or intVal >= 1_000) then
-- resultVar := 4;
-- elsif (intVal <= -100 or intVal >= 100) then
-- resultVar := 3;
-- elsif (intVal <= -10 or intVal >= 10) then
-- resultVar := 2;
-- else
-- resultVar := 1;
-- end if;
-- return resultVar;
--end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- Add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := intVal;
decPntFndVar := false;
decPlacesVar := 0;
expFndVar := false;
expVar := 0;
freqUnitFndVar := false;
negVar := false;
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false;
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar;
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : time_to_slv (convert time to slv)
--
-- DESCRIPTION : converts a time value referenced to a clock frequency
-- to a standard logic vector value large enough to
-- represent it as a signed integer value
--
-- NOTES
-- This function does not work with Synplify
------------------------------------------------------------------------------
-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector is
variable resultVar : std_logic_vector(int_to_slv(timeVal/to_period(clkFreqVal))'range);
begin
resultVar := int_to_slv(timeVal/to_period(clkFreqVal));
return resultVar;
end time_to_slv;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(intVal : integer) return string is
variable lineVar : line;
variable resultVar : string(1 to cfi(intVal));
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, intVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(realVal : real) return string is
variable lengthVar : natural;
variable lineVar : line;
-- variable resultVar : string(1 to cfr(realVal));
variable resultVar : string(1 to 50);
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, realVal);
lengthVar := lineVar.all'length;
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar(1 to lengthVar);
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, vectorVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector
) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;
 
M

My Name

update

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : natural := 30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := CFT_BASE_SIZE*4;


------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural;

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector; -- create a 50% duty cycle count time using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value
function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that


-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector;
-- synopsys translate_on

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency

-- synopsys translate_off
function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
function to_string(realVal : real) return string; -- returns a string value for an real value passed
function to_string(vectorVal : std_logic_vector) return string;
-- synopsys translate_on

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
-- synthesis translate_off
--alias cft is count_for_time[string,string return std_logic_vector]; -- synplify doesn't like "[" or "]"
--alias cfth is count_for_time_high[string,string return integer];
-- synthesis translate_on
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce(timeVar/freqStrVar)'length;
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count_for_time_high)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : clkcnt (50% duty cycle clock count)
--
-- DESCRIPTION : This function takes a string based frequency value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector is
variable freq1StrVar : std_logic_vector(str_to_slv_var_base_high(freq1StrVal,CFT_BASE_SIZE) downto 0);
variable freq2StrVar : std_logic_vector(str_to_slv_var_base_high(freq2StrVal,CFT_BASE_SIZE) downto 0);
begin
freq1StrVar := str_to_slv(freq1StrVal,CFT_BASE_SIZE);
freq2StrVar := str_to_slv(freq2StrVal,CFT_BASE_SIZE);
return reduce((freq1StrVar/freq2StrVar)/2-2);
end clkcnt;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;



-- synthesizable version
--function dpfi(intVal : integer) return natural is
-- variable resultVar : natural;
--begin
-- if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
-- resultVar := 10;
-- elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
-- resultVar := 9;
-- elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
-- resultVar := 8;
-- elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
-- resultVar := 7;
-- elsif (intVal <= -100_000 or intVal >= 100_000) then
-- resultVar := 6;
-- elsif (intVal <= -10_000 or intVal >= 10_000) then
-- resultVar := 5;
-- elsif (intVal <= -1_000 or intVal >= 1_000) then
-- resultVar := 4;
-- elsif (intVal <= -100 or intVal >= 100) then
-- resultVar := 3;
-- elsif (intVal <= -10 or intVal >= 10) then
-- resultVar := 2;
-- else
-- resultVar := 1;
-- end if;
-- return resultVar;
--end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- Add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := intVal;
decPntFndVar := false;
decPlacesVar := 0;
expFndVar := false;
expVar := 0;
freqUnitFndVar := false;
negVar := false;
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false;
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar;
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : time_to_slv (convert time to slv)
--
-- DESCRIPTION : converts a time value referenced to a clock frequency
-- to a standard logic vector value large enough to
-- represent it as a signed integer value
--
-- NOTES
-- This function does not work with Synplify
------------------------------------------------------------------------------
-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector is
variable resultVar : std_logic_vector(int_to_slv(timeVal/to_period(clkFreqVal))'range);
begin
resultVar := int_to_slv(timeVal/to_period(clkFreqVal));
return resultVar;
end time_to_slv;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(intVal : integer) return string is
variable lineVar : line;
variable resultVar : string(1 to cfi(intVal));
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, intVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(realVal : real) return string is
variable lengthVar : natural;
variable lineVar : line;
-- variable resultVar : string(1 to cfr(realVal));
variable resultVar : string(1 to 50);
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, realVal);
lengthVar := lineVar.all'length;
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar(1 to lengthVar);
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, vectorVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector
) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;
 
M

My Name

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : natural := 30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := CFT_BASE_SIZE*4;


------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural;

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft2(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cft2(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 2) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function cfth2(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector; -- create a 50% duty cycle count time using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value
function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_length(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that


-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector;
-- synopsys translate_on

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency

-- synopsys translate_off
function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
function to_string(realVal : real) return string; -- returns a string value for an real value passed
function to_string(vectorVal : std_logic_vector) return string;
-- synopsys translate_on

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
-- synthesis translate_off
--alias cft is count_for_time[string,string return std_logic_vector]; -- synplify doesn't like "[" or "]"
--alias cfth is count_for_time_high[string,string return integer];
-- synthesis translate_on
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length(timeVar/freqStrVar);
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft2 (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft2(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce((timeVar/freqStrVar) - 2);
end cft2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft2 (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- counting down to an underflow) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft2(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth2(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length((timeVar/freqStrVar) - 2);
if (lengthVar >= natVal) then
return reduce((timeVar/freqStrVar) - 2);
else
return zeroVar & reduce((timeVar/freqStrVar) - 2);
end if;
end cft2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count_for_time_high)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth2 (count_for_time_high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 2
-- for use in counting down to underflow) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth2(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high((timeVar/freqStrVar) - 2);
end cfth2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : clkcnt (50% duty cycle clock count)
--
-- DESCRIPTION : This function takes a string based frequency value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector is
variable freq1StrVar : std_logic_vector(str_to_slv_var_base_high(freq1StrVal,CFT_BASE_SIZE) downto 0);
variable freq2StrVar : std_logic_vector(str_to_slv_var_base_high(freq2StrVal,CFT_BASE_SIZE) downto 0);
begin
freq1StrVar := str_to_slv(freq1StrVal,CFT_BASE_SIZE);
freq2StrVar := str_to_slv(freq2StrVal,CFT_BASE_SIZE);
return reduce((freq1StrVar/freq2StrVar)/2-2);
end clkcnt;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;



-- synthesizable version
--function dpfi(intVal : integer) return natural is
-- variable resultVar : natural;
--begin
-- if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
-- resultVar := 10;
-- elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
-- resultVar := 9;
-- elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
-- resultVar := 8;
-- elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
-- resultVar := 7;
-- elsif (intVal <= -100_000 or intVal >= 100_000) then
-- resultVar := 6;
-- elsif (intVal <= -10_000 or intVal >= 10_000) then
-- resultVar := 5;
-- elsif (intVal <= -1_000 or intVal >= 1_000) then
-- resultVar := 4;
-- elsif (intVal <= -100 or intVal >= 100) then
-- resultVar := 3;
-- elsif (intVal <= -10 or intVal >= 10) then
-- resultVar := 2;
-- else
-- resultVar := 1;
-- end if;
-- return resultVar;
--end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- Add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length(vectorVal : std_logic_vector) return integer is
begin
return reduce_high(vectorVal) + 1;
end reduce_length;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := intVal;
decPntFndVar := false;
decPlacesVar := 0;
expFndVar := false;
expVar := 0;
freqUnitFndVar := false;
negVar := false;
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false;
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar;
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : time_to_slv (convert time to slv)
--
-- DESCRIPTION : converts a time value referenced to a clock frequency
-- to a standard logic vector value large enough to
-- represent it as a signed integer value
--
-- NOTES
-- This function does not work with Synplify
------------------------------------------------------------------------------
-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector is
variable resultVar : std_logic_vector(int_to_slv(timeVal/to_period(clkFreqVal))'range);
begin
resultVar := int_to_slv(timeVal/to_period(clkFreqVal));
return resultVar;
end time_to_slv;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(intVal : integer) return string is
variable lineVar : line;
variable resultVar : string(1 to cfi(intVal));
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, intVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(realVal : real) return string is
variable lengthVar : natural;
variable lineVar : line;
-- variable resultVar : string(1 to cfr(realVal));
variable resultVar : string(1 to 50);
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, realVal);
lengthVar := lineVar.all'length;
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar(1 to lengthVar);
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, vectorVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector
) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;
 
M

My Name

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : natural := 30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := CFT_BASE_SIZE*4;


------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural; -- This function returns a natural representing the number of characters required to reprsent an integer value. It is essentially an integer'length function for the characters.

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cft2(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function cft2(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 2) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function cfth2(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector; -- create a 50% duty cycle count time using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfi_syn(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

-- synopsys translate_off
impure function now return string; -- returns a string representation of the current simulation time
-- synopsys translate_on

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_length(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that


-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector;
-- synopsys translate_on

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency

-- synopsys translate_off
function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
function to_string(realVal : real) return string; -- returns a string value for an real value passed
function to_string(vectorVal : std_logic_vector) return string;
-- synopsys translate_on

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
-- synthesis translate_off
--alias cft is count_for_time[string,string return std_logic_vector]; -- synplify doesn't like "[" or "]"
--alias cfth is count_for_time_high[string,string return integer];
-- synthesis translate_on
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length(timeVar/freqStrVar);
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft2 (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft2(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce((timeVar/freqStrVar) - 2);
end cft2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft2 (count_for_time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- counting down to an underflow) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft2(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth2(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length((timeVar/freqStrVar) - 2);
if (lengthVar >= natVal) then
return reduce((timeVar/freqStrVar) - 2);
else
return zeroVar & reduce((timeVar/freqStrVar) - 2);
end if;
end cft2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count_for_time_high)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth2 (count_for_time_high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 2
-- for use in counting down to underflow) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth2(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high((timeVar/freqStrVar) - 2);
end cfth2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : clkcnt (50% duty cycle clock count)
--
-- DESCRIPTION : This function takes a string based frequency value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector is
variable freq1StrVar : std_logic_vector(str_to_slv_var_base_high(freq1StrVal,CFT_BASE_SIZE) downto 0);
variable freq2StrVar : std_logic_vector(str_to_slv_var_base_high(freq2StrVal,CFT_BASE_SIZE) downto 0);
begin
freq1StrVar := str_to_slv(freq1StrVal,CFT_BASE_SIZE);
freq2StrVar := str_to_slv(freq2StrVal,CFT_BASE_SIZE);
return reduce((freq1StrVar/freq2StrVar)/2-2);
end clkcnt;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi_syn (decimal places for integer (synthesizeable))
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi_syn(intVal : integer) return natural is
variable resultVar : natural;
begin
if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
resultVar := 10;
elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
resultVar := 9;
elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
resultVar := 8;
elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
resultVar := 7;
elsif (intVal <= -100_000 or intVal >= 100_000) then
resultVar := 6;
elsif (intVal <= -10_000 or intVal >= 10_000) then
resultVar := 5;
elsif (intVal <= -1_000 or intVal >= 1_000) then
resultVar := 4;
elsif (intVal <= -100 or intVal >= 100) then
resultVar := 3;
elsif (intVal <= -10 or intVal >= 10) then
resultVar := 2;
else
resultVar := 1;
end if;
return resultVar;
end dpfi_syn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : now
--
-- DESCRIPTION : This function returns a string representation
-- of the current simulation time
--
-- NOTES :
--
------------------------------------------------------------------------------
-- synopsys translate_off
impure function now return string is
variable lineVar : line;
variable resultVar : string(1 to time'image(now)'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, time'image(now));
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end now;
-- synopsys translate_on



------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- Add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length(vectorVal : std_logic_vector) return integer is
begin
return reduce_high(vectorVal) + 1;
end reduce_length;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := intVal;
decPntFndVar := false;
decPlacesVar := 0;
expFndVar := false;
expVar := 0;
freqUnitFndVar := false;
negVar := false;
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false;
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar;
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : time_to_slv (convert time to slv)
--
-- DESCRIPTION : converts a time value referenced to a clock frequency
-- to a standard logic vector value large enough to
-- represent it as a signed integer value
--
-- NOTES
-- This function does not work with Synplify
------------------------------------------------------------------------------
-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector is
variable resultVar : std_logic_vector(int_to_slv(timeVal/to_period(clkFreqVal))'range);
begin
resultVar := int_to_slv(timeVal/to_period(clkFreqVal));
return resultVar;
end time_to_slv;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(intVal : integer) return string is
variable lineVar : line;
variable resultVar : string(1 to cfi(intVal));
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, intVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(realVal : real) return string is
variable lengthVar : natural;
variable lineVar : line;
-- variable resultVar : string(1 to cfr(realVal));
variable resultVar : string(1 to 50);
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, realVal);
lengthVar := lineVar.all'length;
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar(1 to lengthVar);
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, vectorVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector
) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;
 
M

My Name

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : natural := 30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := CFT_BASE_SIZE*4;


------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference

function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cdfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural; -- This function returns a natural representing the number of characters required to reprsent an integer value. It is essentially an integer'length function for the characters.

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference


function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector; -- create a 50% duty cycle count time using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference

function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cufth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfi_syn(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

-- synopsys translate_off
impure function now return string; -- returns a string representation of the current simulation time
-- synopsys translate_on

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_length(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that


-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector;
-- synopsys translate_on

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency

-- synopsys translate_off
function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
function to_string(realVal : real) return string; -- returns a string value for an real value passed
function to_string(vectorVal : std_logic_vector) return string;
-- synopsys translate_on

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
-- synthesis translate_off
--alias cft is count_for_time[string,string return std_logic_vector]; -- synplify doesn't like "[" or "]"
--alias cfth is count_for_time_high[string,string return integer];
-- synthesis translate_on
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce((timeVar/freqStrVar) - 2);
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cdfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length((timeVar/freqStrVar) - 2);
if (lengthVar >= natVal) then
return reduce((timeVar/freqStrVar) - 2);
else
return zeroVar & reduce((timeVar/freqStrVar) - 2);
end if;
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdfth (count down for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 2
-- for use in counting down to underflow) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cdfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high((timeVar/freqStrVar) - 2);
end cdfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length(timeVar/freqStrVar);
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : clkcnt (50% duty cycle clock count)
--
-- DESCRIPTION : This function takes a string based frequency value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector is
variable freq1StrVar : std_logic_vector(str_to_slv_var_base_high(freq1StrVal,CFT_BASE_SIZE) downto 0);
variable freq2StrVar : std_logic_vector(str_to_slv_var_base_high(freq2StrVal,CFT_BASE_SIZE) downto 0);
begin
freq1StrVar := str_to_slv(freq1StrVal,CFT_BASE_SIZE);
freq2StrVar := str_to_slv(freq2StrVal,CFT_BASE_SIZE);
return reduce((freq1StrVar/freq2StrVar)/2-2);
end clkcnt;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce((timeVar/freqStrVar) - 1);
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cufth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length((timeVar/freqStrVar) - 1);
if (lengthVar >= natVal) then
return reduce((timeVar/freqStrVar) - 1);
else
return zeroVar & reduce((timeVar/freqStrVar) - 1);
end if;
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cufth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 1
-- for use in counting up from zero to the proper value) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cufth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high((timeVar/freqStrVar) - 1);
end cufth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi_syn (decimal places for integer (synthesizeable))
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi_syn(intVal : integer) return natural is
variable resultVar : natural;
begin
if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
resultVar := 10;
elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
resultVar := 9;
elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
resultVar := 8;
elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
resultVar := 7;
elsif (intVal <= -100_000 or intVal >= 100_000) then
resultVar := 6;
elsif (intVal <= -10_000 or intVal >= 10_000) then
resultVar := 5;
elsif (intVal <= -1_000 or intVal >= 1_000) then
resultVar := 4;
elsif (intVal <= -100 or intVal >= 100) then
resultVar := 3;
elsif (intVal <= -10 or intVal >= 10) then
resultVar := 2;
else
resultVar := 1;
end if;
return resultVar;
end dpfi_syn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : now
--
-- DESCRIPTION : This function returns a string representation
-- of the current simulation time
--
-- NOTES :
--
------------------------------------------------------------------------------
-- synopsys translate_off
impure function now return string is
variable lineVar : line;
variable resultVar : string(1 to time'image(now)'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, time'image(now));
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end now;
-- synopsys translate_on



------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- Add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length(vectorVal : std_logic_vector) return integer is
begin
return reduce_high(vectorVal) + 1;
end reduce_length;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := intVal;
decPntFndVar := false;
decPlacesVar := 0;
expFndVar := false;
expVar := 0;
freqUnitFndVar := false;
negVar := false;
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false;
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar;
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : time_to_slv (convert time to slv)
--
-- DESCRIPTION : converts a time value referenced to a clock frequency
-- to a standard logic vector value large enough to
-- represent it as a signed integer value
--
-- NOTES
-- This function does not work with Synplify
------------------------------------------------------------------------------
-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector is
variable resultVar : std_logic_vector(int_to_slv(timeVal/to_period(clkFreqVal))'range);
begin
resultVar := int_to_slv(timeVal/to_period(clkFreqVal));
return resultVar;
end time_to_slv;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(intVal : integer) return string is
variable lineVar : line;
variable resultVar : string(1 to cfi(intVal));
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, intVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(realVal : real) return string is
variable lengthVar : natural;
variable lineVar : line;
-- variable resultVar : string(1 to cfr(realVal));
variable resultVar : string(1 to 50);
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, realVal);
lengthVar := lineVar.all'length;
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar(1 to lengthVar);
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, vectorVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector
) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------
















-- end of extension pack
-- start of test bench



























































------------------------------------------------------------------------------
-- Extension Pack test bench
------------------------------------------------------------------------------

library ieee, extension_lib;
use ieee.std_logic_1164.all;
use ieee.std_logic_unsigned.all;
use ieee.std_logic_arith.all;
use extension_lib.extension_pack.all;
use ieee.std_logic_textio.all;
use std.textio.all;

entity extension_pack_tb is
end extension_pack_tb;


------------------------------------------------------------------------------
architecture rtl of extension_pack_tb is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Global Component/Function/Procedure Declarations
------------------------------------------------------------------------------
begin


star_operator_test : process
variable slvVar : slv(2 downto 0) := "111";
begin

assert (7*slvVar = "0110001") -- 7*7 = 49
report "* error # 1 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(7*slvVar) & " : actual"
severity error;

assert (slvVar*7 = "0110001") -- 7*7 = 49
report "* error # 2 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(slvVar*7) & " : actual"
severity error;

wait;
end process;




--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : std_logic_vector) return std_logic_vector;
slash1_operator_test : process
constant slvVar : slv := "0110001";
begin

assert ("0110001"/"111" = "0000111") -- 49/7 = 7
report "slash1_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string("0110001"/"111") & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : integer) return std_logic_vector;
slash2_operator_test : process
constant slvVar : slv := "0110001";
begin

assert (slvVar/7 = "0000111") -- 49/7 = 7
report "slash2_operator_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(slvVar/7) & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : string;
-- DivisorVal : integer) return std_logic_vector;
slash3_operator_test : process
constant var : string := "49";
begin

assert (var/7 = "0000111") -- 49/7 = 7
report "slash3_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(var/7) & " : actual"
severity error;

wait;
end process;



--function bcd_to_led(slvVal : std_logic_vector ;
-- CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion
bcd_to_led1_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_led(slvVar,true) = "0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") -- 123456789ABCDEF =
report "bcd_to_led_test error # 1 " & LF &
to_string("0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") & " : expected" & LF &
to_string(bcd_to_led(slvVar,true)) & " : actual"
severity error;

assert (bcd_to_led(slvVar,false) = "1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") -- 123456789ABCDEF =
report "bcd_to_led_test error # 2 " & LF &
to_string("1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") & " : expected" & LF &
to_string(bcd_to_led(slvVar,false)) & " : actual"
severity error;

wait;
end process;







--function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed
bcd_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_slv(slvVar) = "011100000100100010000110000111101101001110111111") -- 123456789ABCDEF = 123456790123455
report "bcd_to_slv_test error # 1 " & LF &
to_string("011100000100100010000110000111101101001110111111") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("00000001001000110100010101100111100010010000") = "01001001100101100000001011010010") -- 1234567890 =
report "bcd_to_slv_test error # 2 " & LF &
to_string("01001001100101100000001011010010") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("101010111100110111101111") = "100010010010001111111") -- ABCDEF (1123455)
report "bcd_to_slv_test error # 3 " & LF &
to_string("100010010010001111111") & " : expected" & LF &
to_string(bcd_to_slv("101010111100110111101111")) & " : actual"
severity error;


wait;
end process;


--function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value




--function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function
bv_to_slv_test : process
constant bvVar : bv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bv_to_slv(bvVar) = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 1 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(bvVar)) & " : actual"
severity error;

assert (bv_to_slv(X"123456789ABCDEF") = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 2 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(X"123456789ABCDEF")) & " : actual"
severity error;

wait;
end process;


--function cdft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdft("8 ms ","1 kHz") = slvVar)
report "count_down_for_time2_test error # 1 " & LF &
to_string("0111") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz")) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz")) = "0110")
report "count_down_for_time2_test error # 2 " & LF &
to_string("0110") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length = 4)
report "count_down_for_time2_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length) & " : actual"
severity error;

wait;
end process;




--function cdfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high_test : process
begin

assert (cdfth("1 us ","1E-15 yHz") = 10)
report "count_down_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cdfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;

--function cdfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdfth("8 ms ","1 kHz") = 3)
report "count_down_for_time_high_test2 error # 1 " & LF &
to_string(3) & " : expected" & LF &
to_string(cdfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;





--function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer
ceil_test : process
begin

assert (ceil(-9.999999) = -9.0)
report "ceil_test error # 1 " & LF &
to_string(-9.0) & " : expected" & LF &
to_string(ceil(-9.999999)) & " : actual"
severity error;

assert (ceil(9.999999) = 10.0)
report "ceil_test error # 2 " & LF &
to_string(10.0) & " : expected" & LF &
to_string(ceil(9.999999)) & " : actual"
severity error;

wait;
end process;



--function cfi(intVal : integer) return natural;
cfi_test : process
begin

assert (cfi(-1000) = 5)
report "cfi_test error # 1 " & LF &
"5 : expected" & LF &
to_string(cfi(-1000)) & " : actual"
severity error;

assert (cfi(-10000) = 6)
report "cfi_test error # 2 " & LF &
"6 : expected" & LF &
to_string(cfi(-10000)) & " : actual"
severity error;


assert (cfi(1000) = 4)
report "cfi_test error # 3 " & LF &
"4 : expected" & LF &
to_string(cfi(1000)) & " : actual"
severity error;


assert (cfi(-100_000) = 7)
report "cfi_test error # 4 " & LF &
"7 : expected" & LF &
to_string(cfi(-100_000)) & " : actual"
severity error;


assert (cfi(100_000) = 6)
report "cfi_test error # 5 " & LF &
"6 : expected" & LF &
to_string(cfi(100_000)) & " : actual"
severity error;

assert (cfi(-9999999) = 8)
report "cfi_test error # 6 " & LF &
to_string(8) & " : expected" & LF &
to_string(cfi(-9999999)) & " : actual"
severity error;

assert (cfi(9999999) = 7)
report "cfi_test error # 7 " & LF &
to_string(7) & " : expected" & LF &
to_string(cfi(9999999)) & " : actual"
severity error;

wait;
end process;


--function cft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cft(CNTTIME,SYSCLKFREQ) = "100111010101101100110100000000")
report "count_for_time_test error # 1 " & LF &
to_string("100111010101101100110100000000") & " : expected" & LF &
to_string(cft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cft("1 min","66MHz") = "11101100000010001100111000000000")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100111000000000") & " : expected" & LF &
to_string(cft("1 min","66MHz")) & " : actual"
severity error;


assert (cft("1 hr","66MHz") = "11011101010010000100000100100000000000")
report "count_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100100000000000") & " : expected" & LF &
to_string(cft("1 hr","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz") = "01010010111110110001100001101100000000000000")
report "count_for_time_test error # 4 " & LF &
to_string("01010010111110110001100001101100000000000000") & " : expected" & LF &
to_string(cft("1 day","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 5 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz")) & " : actual"
severity error;


assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 6 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")+cft("1 as","66MHz")+cft("1 zs","66MHz")+cft("1 ys","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 7 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "011100011100110011110110101000101011010000000101001")
report "count_for_time_test error # 8 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-3 kHz") = "01")
report "count_for_time_test error # 9 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-18 eHz") = "01")
report "count_for_time_test error # 10 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cft("1 ns ","1E-15 yHz") = "01")
report "count_for_time_test error # 11 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cft("1 us ","1E-15 yHz") = "01111101000")
report "count_for_time_test error # 12 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(cft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cft("20 ms ","50 MHz"),21);

assert (ext(cft("20 ms ","50 MHz"),21) = "011110100001001000000")
report "count_for_time_test error # 13 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(ext(cft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test : process
begin

assert (cfth("1 us ","1E-15 yHz") = 10)
report "count_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cfth("8 ms ","1 kHz") = 4)
report "count__for_time_high_test2 error # 1 " & LF &
to_string(4) & " : expected" & LF &
to_string(cfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;



--function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
conv_to_hex_test1 : process
variable testVar : bv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test1 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
conv_to_hex_test2 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test2 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion
conv_to_hex_test3 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test3 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function cslv(int1Val : integer;
-- int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(sigVal : signed;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(usgVal : unsigned;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested


--function cuft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cuft(CNTTIME,SYSCLKFREQ) = "0100111010101101100110011111111")
report "count_up_for_time_test error # 1 " & LF &
to_string("0100111010101101100110011111111") & " : expected" & LF &
to_string(cuft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cuft("1 min","66MHz") = "011101100000010001100110111111111")
report "count_for_time_test error # 2 " & LF &
to_string("011101100000010001100110111111111") & " : expected" & LF &
to_string(cuft("1 min","66MHz")) & " : actual"
severity error;


assert (cuft("1 hr","66MHz") = "011011101010010000100000100011111111111")
report "count_up_for_time_test error # 3 " & LF &
to_string("011011101010010000100000100011111111111") & " : expected" & LF &
to_string(cuft("1 hr","66MHz")) & " : actual"
severity error;


assert (cuft("1 day","66MHz") = "01010010111110110001100001101011111111111111")
report "count_up_for_time_test error # 4 " & LF &
to_string("01010010111110110001100001101011111111111111") & " : expected" & LF &
to_string(cuft("1 day","66MHz")) & " : actual"
severity error;




assert (cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "01010110011111110011100011111110110010010001")
report "count_up_for_time_test error # 6 " & LF &
to_string("01010110011111110011100011111110110010010001") & " : expected" & LF &
to_string(cuft("1 day","66MHz")+cuft("1 hr","66MHz")+cuft("1 min","66MHz")+cuft("1 sec","66MHz")+cuft("1 ms","66MHz")+cuft("1 us","66MHz")+cuft("1 ns","66MHz")+cuft("1 ps","66MHz")+cuft("1 fs","66MHz")+cuft("1 as","66MHz")+cuft("1 zs","66MHz")+cuft("1 ys","66MHz")) & " : actual" & LF &
to_string(cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;



assert (cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "011100011100110011110110101000101011010000000101000")
report "count_up_for_time_test error # 8 " & LF &
to_string("011100011100110011110110101000101011010000000101000") & " : expected" & LF &
to_string(cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-3 kHz") = "00")
report "count_up_for_time_test error # 9 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-18 eHz") = "00")
report "count_up_for_time_test error # 10 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cuft("1 ns ","1E-15 yHz") = "00")
report "count_up_for_time_test error # 11 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cuft("1 us ","1E-15 yHz") = "01111100111")
report "count_up_for_time_test error # 12 " & LF &
to_string("01111100111") & " : expected" & LF &
to_string(cuft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cuft("20 ms ","50 MHz"),21);

assert (ext(cuft("20 ms ","50 MHz"),21) = "0000011110100001000111111")
report "count_up_for_time_test error # 13 " & LF &
to_string("0000011110100001000111111") & " : expected" & LF &
to_string(ext(cuft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test : process
begin

assert (cufth("1 us ","1E-15 yHz") = 10)
report "count_up_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cufth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cufth("8 ms ","1 kHz") = 3)
report "count__for_time_high_test2 error # 1 " & LF &
to_string(3) & " : expected" & LF &
to_string(cufth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;

--function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value


--function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value



--function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed


--function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

--function ext(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector;
ext_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);

assert (ext2(slvVar,7) = "0000111") -- 7 bits
report "ext_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,7)) & " : actual"
severity error;

assert (ext2(slvVar,4) = "0111") -- 4 bits
report "ext_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,4)) & " : actual"
severity error;

assert (ext2(slvVar,4)'length = 4) -- 4 bits
report "ext_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(ext2(slvVar,4)'length) & " : actual"
severity error;

wait;
end process;



--function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order


--function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order



--function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order


--function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector



--function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed



--function mult_s(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply



--function mult_us(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply



--function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed



--function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value


--function now return string; -- returns a string representation of the current simulation time
now_test : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

wait for 3 sec;

assert FALSE
report "now_test error # 1 " & LF &
now & " : expected" & LF
severity error;

wait;
end process;


--function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function reduce_high(vectorVal : std_logic_vector) return integer; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function seq(str1Val : string;
-- str2Val : string) return boolean;



--function shl(vectorVal : std_logic_vector;
-- natVal : natural) return std_logic_vector;



--function slv_to_bcd(vectorVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified



--function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed



--function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
-- MSB_Val : std_logic;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value



--function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer



--function str_to_led(stringVal : string;
-- CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs



--function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
str_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (str_to_slv("1") = "01") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("0") = "0") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("00") & " : expected" & LF &
to_string(str_to_slv("0")) & " : actual"
severity error;

assert (str_to_slv("-1") = "11") -- -1
report "bcd_to_led_test error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(str_to_slv("-1")) & " : actual"
severity error;

assert (str_to_slv("10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 1 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv("10 us"))
severity error;

assert (str_to_slv(" 10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 2 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us"))
severity error;

assert (str_to_slv(" 10 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 3 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us "))
severity error;

assert (str_to_slv(" 10.0 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 4 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0 us "))
severity error;

assert (str_to_slv(" 0.0100 ms ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 5 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0100 ms "))
severity error;

assert (str_to_slv(" 0.0000100sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0000100sec "))
severity error;

assert (str_to_slv(" 10E-6 sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E-6 sec "))
severity error;


assert (str_to_slv(" 10,000,000,000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 7 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10,000,000,000 "))
severity error;

assert (str_to_slv(" 100,000Hz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 8 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100,000Hz "))
severity error;


assert (str_to_slv(" 100kHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100kHz "))
severity error;

assert (str_to_slv(" 0.1MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.1MHz "))
severity error;

assert (str_to_slv(" .1 MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" .1 MHz "))
severity error;

assert (str_to_slv(" 0.0001GHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 10 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0001GHz "))
severity error;


assert (str_to_slv(" 10E 9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 11 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E 9 "))
severity error;


assert (str_to_slv(" 10E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 12 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9.000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9.000 "))
severity error;

assert (str_to_slv(" 100E+3 HZ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 14 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;


assert (str_to_slv(" 1") = "01")
report "str_to_slv_test error # 15a " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(str_to_slv(" 1"))
severity error;

assert (str_to_slv(" -1") = "11")
report "str_to_slv_test error # 15b " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(str_to_slv(" -1"))
severity error;


assert (str_to_slv("1") = "01")
report "str_to_slv_test error # 16 " & LF &
to_string("01") & " : expected"
& LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("10") = "01010")
report "str_to_slv_test error # 17 " & LF &
to_string("01010") & " : expected"
& LF &
to_string(str_to_slv("10")) & " : actual"
severity error;

assert (str_to_slv(" 100E+3 HZ ps ns MHz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 18 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100E+3 HZ Hz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 19 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100,000 HZ 234sec") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 20 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ 234sec"))
severity error;

assert (str_to_slv("1 day") = "01001010111100001010011101100011101110110001110000000000000000000000") -- 0
report "bcd_to_led_test error # 21 " & LF &
to_string("01001010111100001010011101100011101110110001110000000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 day")) & " : actual"
severity error;

assert (str_to_slv("1 hr") = "011000111110101110001001110110100100111011010000000000000000000") -- 0
report "bcd_to_led_test error # 22 " & LF &
to_string("011000111110101110001001110110100100111011010000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 hr")) & " : actual"
severity error;

assert (str_to_slv("1 min") = "011010101001010011010111010011110100001100000000000000000") -- 0
report "bcd_to_led_test error # 23 " & LF &
to_string("011010101001010011010111010011110100001100000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 min")) & " : actual"
severity error;

assert (str_to_slv("1 sec") = "011100011010111111010100100110001101000000000000000") -- 0
report "bcd_to_led_test error # 24 " & LF &
to_string("011100011010111111010100100110001101000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 sec")) & " : actual"
severity error;

assert (str_to_slv("1 ms") = "01110100011010100101001010001000000000000") -- 0
report "bcd_to_led_test error # 25 " & LF &
to_string("01110100011010100101001010001000000000000") & " : expected" & LF &
to_string(str_to_slv("1 ms")) & " : actual"
severity error;

assert (str_to_slv("1 us") = "0111011100110101100101000000000") -- 0
report "bcd_to_led_test error # 26 " & LF &
to_string("0111011100110101100101000000000") & " : expected" & LF &
to_string(str_to_slv("1 us")) & " : actual"
severity error;

assert (str_to_slv("1 ns") = "011110100001001000000") -- 0
report "bcd_to_led_test error # 27 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 ns")) & " : actual"
severity error;

assert (str_to_slv("1 ps") = "01111101000") -- 0
report "bcd_to_led_test error # 28 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 ps")) & " : actual"
severity error;

assert (str_to_slv("1 fs") = "01") -- 0
report "bcd_to_led_test error # 29 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 fs")) & " : actual"
severity error;

assert (str_to_slv("1 as",24) = "011110100001001000000") -- 0
report "bcd_to_led_test error # 30 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 as",24)) & " : actual"
severity error;

assert (str_to_slv("1 zs",24) = "01111101000") -- 0
report "bcd_to_led_test error # 31 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 zs",24)) & " : actual"
severity error;

assert (str_to_slv("1 ys",24) = "01") -- 0
report "bcd_to_led_test error # 32 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 ys",24)) & " : actual"
severity error;


assert (str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs") = "01001110000111011000111100110011111100101100110000111010000000101001") -- 0
report "bcd_to_led_test error # 33 " & LF &
to_string("01001110000111011000111100110011111100101100110000111010000000101001") & " : expected" & LF &
to_string(str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs")) & " : actual"
severity error;


wait;
end process;


--function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed



--function str_to_slv_var_base(stringVal : string;
-- intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed



--function str_to_slv_var_base_high(stringVal : string;
-- intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value



--function strh(stringVal : string) return integer;

sxt_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := sxt2(int_to_slv(-1000),slv1Var'length);
slv2Var := sxt2(int_to_slv(-6),slv2Var'length);

assert (sxt2(slvVar,7) = "0000111") -- 7 bits
report "sxt2_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,7)) & " : actual"
severity error;

assert (sxt2(slvVar,4) = "0111") -- 4 bits
report "sxt2_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,4)) & " : actual"
severity error;

assert (sxt2("1001",7) = "1111001") -- 7 bits
report "sxt2_test error # 3 " & LF &
to_string("1111001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;

assert (sxt2("00",7) = "0000000") -- 4 bits
report "sxt2_test error # 4 " & LF &
to_string("0000000") & " : expected" & LF &
to_string(sxt2("00",7)) & " : actual"
severity error;

assert (sxt2("1001",4) = "1001") -- 7 bits
report "sxt2_test error # 5 " & LF &
to_string("1001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;


wait;
end process;

---- synopsys translate_off
--function time_to_slv(timeVal : time;
-- clkFreqVal : frequency) return std_logic_vector;
---- synopsys translate_on
--
--function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function
--
--function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency
--
---- synopsys translate_off
--function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
--function to_string(realVal : real) return string; -- returns a string value for an real value passed
--function to_string(vectorVal : std_logic_vector) return string;
---- synopsys translate_on
--
--function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--
--function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
--function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed
--
--function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed
--
--function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed
--
--------------------------------------------------------------------------------
---- Procedure Declarations
--------------------------------------------------------------------------------
---- synopsys translate_off
--procedure clkgen(
-- constant clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkPeriodSig : in time;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
---- synopsys translate_on
--
--procedure FF(
-- signal Clk : in std_logic;
-- signal Rst : in std_logic;
-- signal D : in std_logic_vector;
-- signal Q : out std_logic_vector);
--
--procedure slv_to_bcd(
-- signal BCD_RIn : in std_logic_vector;
-- signal BinIn : in std_logic_vector;
-- signal BinFBIn : in std_logic_vector;
-- signal ClkIn : in std_logic;
-- constant BCD_DigitsVal : in integer;
-- signal EnIn : in std_logic;
-- signal RstLowIn : in std_logic;
-- signal BCD_ROut : out std_logic_vector;
-- signal Bin_ROut : out std_logic_vector;
-- signal DoneOut : out std_logic);











































divider_test : process
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);
begin
slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);
slv3Var := slv1Var/slv2Var;
-- assert FALSE
-- report "divider output :" & LF & to_string(to_int(slv1Var)) & " / " & to_string(to_int(slv2Var)) & " = " & to_string(to_int(slv3Var))
-- severity note;
wait;
end process;


bcd_to_led_test : process
variable slvVar : slv(27 downto 0);
begin





slvVar := bcd_to_led("0011001000010000",False); -- 3210
assert (slvVar = "1111001110110101100001111110")
report "bcd_to_led_test error # 1 "
severity error;
slvVar := bcd_to_led("0111011001010100",False); -- 7654
assert (slvVar = "1110010101111110110110110011")
report "bcd_to_led_test error # 2 "
severity error;
slvVar := bcd_to_led("0001000010011000",False); -- 1098
assert (slvVar = "0110000111111011100111111111")
report "bcd_to_led_test error # 3 "
severity error;
slvVar := bcd_to_led("0011001000010000",True); -- 3210
assert (slvVar = "0000110001001010011110000001")
report "bcd_to_led_test error # 4 "
severity error;
slvVar := bcd_to_led("0111011001010100",True); -- 7654
assert (slvVar = "0001101010000001001001001100")
report "bcd_to_led_test error # 5 "
severity error;
slvVar := bcd_to_led("0001000010011000",True); -- 1098
assert (slvVar = "1001111000000100011000000000")
report "bcd_to_led_test error # 6 "
severity error;
wait;
end process;











str_to_int_test : process
variable intVar : integer;
begin
intVar := str_to_int("10"); -- 3210
assert (intVar = 10)
report "str_to_int_test error # 1 " & LF &
"expected : 10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-10 sec"); -- 3210
assert (intVar = -10)
report "str_to_int_test error # 2 " & LF &
"expected : -10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-6 sec"); -- 3210
assert (intVar = -6)
report "str_to_int_test error # 3 " & LF &
"expected : -6" & LF &
"actual : " & to_string(intVar)
severity error;

wait;
end process;




reduce_test : process

begin

assert (reduce("00000") = "00") -- 0
report "reduce error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(reduce("00000")) & " : actual"
severity error;

assert (reduce("00001") = "01") -- 1
report "reduce error # 2 " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(reduce("00001"))
severity error;

assert (reduce("11111") = "11") -- -1
report "reduce error # 3 " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(reduce("11111"))
severity error;

assert (reduce("10000") = "10000") -- -16
report "reduce error # 4 " & LF &
"expected : " & to_string("10000") & LF &
"actual : " & to_string(reduce("10000"))
severity error;

wait;

end process;











--exp_test : process
--variable timeBaseVar : slv(500 downto 0);
--variable lineVar : line;
--begin
-- timeBaseVar := ext("01",timeBaseVar'length);
-- for loopVar in 1 to 50 loop
-- timeBaseVar := timeBaseVar(timeBaseVar'high-4 downto 0) * "1010";
--
---- write(lineVar,to_string(real(reduce_high(timeBaseVar))/real(loopVar)));
---- write(lineVar,LF);
-- assert FALSE
-- report
-- to_string(real(reduce_high(timeBaseVar))/real(loopVar)) & LF
-- severity note;
-- end loop;
--
-- wait;
--end process;



unsigned_mult_test : process

begin

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

assert (mult_us("000","011") = "000000") -- 0
report "mult error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","011")) & " : actual"
severity error;

assert (mult_us("011","000") = "000000") -- 0
report "mult error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("011","000")) & " : actual"
severity error;

assert (mult_us("000","101") = "000000") -- 0
report "mult error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","101")) & " : actual"
severity error;

assert (mult_us("101","000") = "000000") -- 0
report "mult error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("101","000")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 7 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

wait;

end process;








signed_mult_test : process

begin

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("000","011") = "000000") -- 0
report "mult_s error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","011")) & " : actual"
severity error;

assert (mult_s("011","000") = "000000") -- 0
report "mult_s error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("011","000")) & " : actual"
severity error;

assert (mult_s("000","101") = "000000") -- 0
report "mult_s error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","101")) & " : actual"
severity error;

assert (mult_s("101","000") = "000000") -- 0
report "mult_s error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("101","000")) & " : actual"
severity error;

assert (mult_s("011","101") = "110111") -- 3 * (-3) = -9
report "mult_s error # 7 " & LF &
to_string("110111") & " : expected" & LF &
to_string(mult_s("011","101")) & " : actual"
severity error;

assert (mult_s("011","100") = "110100") -- 3 * (-4) = -12
report "mult_s error # 8 " & LF &
to_string("110100") & " : expected" & LF &
to_string(mult_s("011","100")) & " : actual"
severity error;

assert (mult_s("101","101") = "001001") -- (-3) * (-3) = 9
report "mult_s error # 9 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("101","101")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 10 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 11 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;


assert (mult_s("100","100") = "010000") -- -4 * -4 = 16
report "mult_s error # 11 " & LF &
to_string("010000") & " : expected" & LF &
to_string(mult_s("100","100")) & " : actual"
severity error;



wait;

end process;








conv_to_hex_test : process
constant slvVar : slv(11 downto 0) := "101011110000";

begin

assert (conv_to_hex(slvVar) = "AF0") -- 0
report "mult_s error # 1 " & LF &
"AF0 : expected" & LF &
conv_to_hex(slvVar) & " : actual"
severity error;


wait;

end process;


--assert FALSE
--report "THIS IS THE END OF SIMULATION" & LF
--severity failure;
 
M

My Name

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : natural := 30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := CFT_BASE_SIZE*4;


------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference

function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cdfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural; -- This function returns a natural representing the number of characters required to reprsent an integer value. It is essentially an integer'length function for the characters.

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference


function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector; -- create a 50% duty cycle count time using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference

function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cufth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfi_syn(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

-- synopsys translate_off
impure function now return string; -- returns a string representation of the current simulation time
-- synopsys translate_on

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed
function reduce_length(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that


-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector;
-- synopsys translate_on

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency

-- synopsys translate_off
function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
function to_string(realVal : real) return string; -- returns a string value for an real value passed
function to_string(vectorVal : std_logic_vector) return string;
-- synopsys translate_on

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
-- synthesis translate_off
--alias cft is count_for_time[string,string return std_logic_vector]; -- synplify doesn't like "[" or "]"
--alias cfth is count_for_time_high[string,string return integer];
-- synthesis translate_on
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce((timeVar/freqStrVar) - 2);
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cdfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length((timeVar/freqStrVar) - 2);
if (lengthVar >= natVal) then
return reduce((timeVar/freqStrVar) - 2);
else
return zeroVar & reduce((timeVar/freqStrVar) - 2);
end if;
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdfth (count down for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 2
-- for use in counting down to underflow) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cdfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high((timeVar/freqStrVar) - 2);
end cdfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length(timeVar/freqStrVar);
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : clkcnt (50% duty cycle clock count)
--
-- DESCRIPTION : This function takes a string based frequency value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector is
variable freq1StrVar : std_logic_vector(str_to_slv_var_base_high(freq1StrVal,CFT_BASE_SIZE) downto 0);
variable freq2StrVar : std_logic_vector(str_to_slv_var_base_high(freq2StrVal,CFT_BASE_SIZE) downto 0);
begin
freq1StrVar := str_to_slv(freq1StrVal,CFT_BASE_SIZE);
freq2StrVar := str_to_slv(freq2StrVal,CFT_BASE_SIZE);
return reduce((freq1StrVar/freq2StrVar)/2-2);
end clkcnt;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_unsigned((timeVar/freqStrVar) - 1);
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to:
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cufth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length_unsigned((timeVar/freqStrVar) - 1);
if (lengthVar >= natVal) then
return reduce_unsigned((timeVar/freqStrVar) - 1);
else
return zeroVar & reduce_unsigned((timeVar/freqStrVar) - 1);
end if;
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cufth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 1
-- for use in counting up from zero to the proper value) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cufth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high_unsigned((timeVar/freqStrVar) - 1);
end cufth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi_syn (decimal places for integer (synthesizeable))
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi_syn(intVal : integer) return natural is
variable resultVar : natural;
begin
if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
resultVar := 10;
elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
resultVar := 9;
elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
resultVar := 8;
elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
resultVar := 7;
elsif (intVal <= -100_000 or intVal >= 100_000) then
resultVar := 6;
elsif (intVal <= -10_000 or intVal >= 10_000) then
resultVar := 5;
elsif (intVal <= -1_000 or intVal >= 1_000) then
resultVar := 4;
elsif (intVal <= -100 or intVal >= 100) then
resultVar := 3;
elsif (intVal <= -10 or intVal >= 10) then
resultVar := 2;
else
resultVar := 1;
end if;
return resultVar;
end dpfi_syn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : now
--
-- DESCRIPTION : This function returns a string representation
-- of the current simulation time
--
-- NOTES :
--
------------------------------------------------------------------------------
-- synopsys translate_off
impure function now return string is
variable lineVar : line;
variable resultVar : string(1 to time'image(now)'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, time'image(now));
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end now;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- And add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_unsigned
--
-- DESCRIPTION : This function returns a vector with all sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length(vectorVal : std_logic_vector) return integer is
begin
return reduce_high(vectorVal) + 1;
end reduce_length;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer is
begin
return reduce_high_unsigned(vectorVal) + 1;
end reduce_length_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := intVal;
decPntFndVar := false;
decPlacesVar := 0;
expFndVar := false;
expVar := 0;
freqUnitFndVar := false;
negVar := false;
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false;
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar;
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : time_to_slv (convert time to slv)
--
-- DESCRIPTION : converts a time value referenced to a clock frequency
-- to a standard logic vector value large enough to
-- represent it as a signed integer value
--
-- NOTES
-- This function does not work with Synplify
------------------------------------------------------------------------------
-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector is
variable resultVar : std_logic_vector(int_to_slv(timeVal/to_period(clkFreqVal))'range);
begin
resultVar := int_to_slv(timeVal/to_period(clkFreqVal));
return resultVar;
end time_to_slv;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(intVal : integer) return string is
variable lineVar : line;
variable resultVar : string(1 to cfi(intVal));
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, intVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(realVal : real) return string is
variable lengthVar : natural;
variable lineVar : line;
-- variable resultVar : string(1 to cfr(realVal));
variable resultVar : string(1 to 50);
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, realVal);
lengthVar := lineVar.all'length;
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar(1 to lengthVar);
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, vectorVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector
) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------
















-- end of extension pack
-- start of test bench























































-- synopsys translate_off



------------------------------------------------------------------------------
-- Extension Pack test bench
------------------------------------------------------------------------------

library ieee, extension_lib;
use ieee.std_logic_1164.all;
use ieee.std_logic_unsigned.all;
use ieee.std_logic_arith.all;
use extension_lib.extension_pack.all;
use ieee.std_logic_textio.all;
use std.textio.all;

entity extension_pack_tb is
end extension_pack_tb;


------------------------------------------------------------------------------
architecture behavioral of extension_pack_tb is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Global Component/Function/Procedure Declarations
------------------------------------------------------------------------------
begin


star_operator_test : process
variable slvVar : slv(2 downto 0) := "111";
begin

assert (7*slvVar = "0110001") -- 7*7 = 49
report "* error # 1 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(7*slvVar) & " : actual"
severity error;

assert (slvVar*7 = "0110001") -- 7*7 = 49
report "* error # 2 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(slvVar*7) & " : actual"
severity error;

wait;
end process;




--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : std_logic_vector) return std_logic_vector;
slash1_operator_test : process
constant slvVar : slv := "0110001";
begin

assert ("0110001"/"111" = "0000111") -- 49/7 = 7
report "slash1_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string("0110001"/"111") & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : integer) return std_logic_vector;
slash2_operator_test : process
constant slvVar : slv := "0110001";
begin

assert (slvVar/7 = "0000111") -- 49/7 = 7
report "slash2_operator_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(slvVar/7) & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : string;
-- DivisorVal : integer) return std_logic_vector;
slash3_operator_test : process
constant var : string := "49";
begin

assert (var/7 = "0000111") -- 49/7 = 7
report "slash3_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(var/7) & " : actual"
severity error;

wait;
end process;



--function bcd_to_led(slvVal : std_logic_vector ;
-- CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion
bcd_to_led1_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_led(slvVar,true) = "0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") -- 123456789ABCDEF =
report "bcd_to_led_test error # 1 " & LF &
to_string("0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") & " : expected" & LF &
to_string(bcd_to_led(slvVar,true)) & " : actual"
severity error;

assert (bcd_to_led(slvVar,false) = "1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") -- 123456789ABCDEF =
report "bcd_to_led_test error # 2 " & LF &
to_string("1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") & " : expected" & LF &
to_string(bcd_to_led(slvVar,false)) & " : actual"
severity error;

wait;
end process;







--function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed
bcd_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_slv(slvVar) = "011100000100100010000110000111101101001110111111") -- 123456789ABCDEF = 123456790123455
report "bcd_to_slv_test error # 1 " & LF &
to_string("011100000100100010000110000111101101001110111111") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("00000001001000110100010101100111100010010000") = "01001001100101100000001011010010") -- 1234567890 =
report "bcd_to_slv_test error # 2 " & LF &
to_string("01001001100101100000001011010010") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("101010111100110111101111") = "100010010010001111111") -- ABCDEF (1123455)
report "bcd_to_slv_test error # 3 " & LF &
to_string("100010010010001111111") & " : expected" & LF &
to_string(bcd_to_slv("101010111100110111101111")) & " : actual"
severity error;


wait;
end process;


--function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value




--function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function
bv_to_slv_test : process
constant bvVar : bv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bv_to_slv(bvVar) = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 1 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(bvVar)) & " : actual"
severity error;

assert (bv_to_slv(X"123456789ABCDEF") = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 2 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(X"123456789ABCDEF")) & " : actual"
severity error;

wait;
end process;


--function cdft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdft("8 ms ","1 kHz") = slvVar)
report "count_down_for_time2_test error # 1 " & LF &
to_string("0111") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz")) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz")) = "0110")
report "count_down_for_time2_test error # 2 " & LF &
to_string("0110") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length = 4)
report "count_down_for_time2_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length) & " : actual"
severity error;

wait;
end process;




--function cdfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high_test : process
begin

assert (cdfth("1 us ","1E-15 yHz") = 10)
report "count_down_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cdfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;

--function cdfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdfth("8 ms ","1 kHz") = 3)
report "count_down_for_time_high_test2 error # 1 " & LF &
to_string(3) & " : expected" & LF &
to_string(cdfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;





--function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer
ceil_test : process
begin

assert (ceil(-9.999999) = -9.0)
report "ceil_test error # 1 " & LF &
to_string(-9.0) & " : expected" & LF &
to_string(ceil(-9.999999)) & " : actual"
severity error;

assert (ceil(9.999999) = 10.0)
report "ceil_test error # 2 " & LF &
to_string(10.0) & " : expected" & LF &
to_string(ceil(9.999999)) & " : actual"
severity error;

wait;
end process;



--function cfi(intVal : integer) return natural;
cfi_test : process
begin

assert (cfi(-1000) = 5)
report "cfi_test error # 1 " & LF &
"5 : expected" & LF &
to_string(cfi(-1000)) & " : actual"
severity error;

assert (cfi(-10000) = 6)
report "cfi_test error # 2 " & LF &
"6 : expected" & LF &
to_string(cfi(-10000)) & " : actual"
severity error;


assert (cfi(1000) = 4)
report "cfi_test error # 3 " & LF &
"4 : expected" & LF &
to_string(cfi(1000)) & " : actual"
severity error;


assert (cfi(-100_000) = 7)
report "cfi_test error # 4 " & LF &
"7 : expected" & LF &
to_string(cfi(-100_000)) & " : actual"
severity error;


assert (cfi(100_000) = 6)
report "cfi_test error # 5 " & LF &
"6 : expected" & LF &
to_string(cfi(100_000)) & " : actual"
severity error;

assert (cfi(-9999999) = 8)
report "cfi_test error # 6 " & LF &
to_string(8) & " : expected" & LF &
to_string(cfi(-9999999)) & " : actual"
severity error;

assert (cfi(9999999) = 7)
report "cfi_test error # 7 " & LF &
to_string(7) & " : expected" & LF &
to_string(cfi(9999999)) & " : actual"
severity error;

wait;
end process;


--function cft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cft(CNTTIME,SYSCLKFREQ) = "100111010101101100110100000000")
report "count_for_time_test error # 1 " & LF &
to_string("100111010101101100110100000000") & " : expected" & LF &
to_string(cft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cft("1 min","66MHz") = "11101100000010001100111000000000")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100111000000000") & " : expected" & LF &
to_string(cft("1 min","66MHz")) & " : actual"
severity error;


assert (cft("1 hr","66MHz") = "11011101010010000100000100100000000000")
report "count_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100100000000000") & " : expected" & LF &
to_string(cft("1 hr","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz") = "01010010111110110001100001101100000000000000")
report "count_for_time_test error # 4 " & LF &
to_string("01010010111110110001100001101100000000000000") & " : expected" & LF &
to_string(cft("1 day","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 5 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz")) & " : actual"
severity error;


assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 6 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")+cft("1 as","66MHz")+cft("1 zs","66MHz")+cft("1 ys","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 7 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "011100011100110011110110101000101011010000000101001")
report "count_for_time_test error # 8 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-3 kHz") = "01")
report "count_for_time_test error # 9 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-18 eHz") = "01")
report "count_for_time_test error # 10 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cft("1 ns ","1E-15 yHz") = "01")
report "count_for_time_test error # 11 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cft("1 us ","1E-15 yHz") = "01111101000")
report "count_for_time_test error # 12 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(cft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cft("20 ms ","50 MHz"),21);

assert (ext(cft("20 ms ","50 MHz"),21) = "011110100001001000000")
report "count_for_time_test error # 13 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(ext(cft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test : process
begin

assert (cfth("1 us ","1E-15 yHz") = 10)
report "count_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cfth("8 ms ","1 kHz") = 4)
report "count_for_time_high_test2 error # 1 " & LF &
to_string(4) & " : expected" & LF &
to_string(cfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;



--function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
conv_to_hex_test1 : process
variable testVar : bv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test1 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
conv_to_hex_test2 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test2 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion
conv_to_hex_test3 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test3 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function cslv(int1Val : integer;
-- int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(sigVal : signed;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(usgVal : unsigned;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested


--function cuft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cuft(CNTTIME,SYSCLKFREQ) = "100111010101101100110011111111")
report "count_up_for_time_test error # 1 " & LF &
to_string("100111010101101100110011111111") & " : expected" & LF &
to_string(cuft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cuft("1 min","66MHz") = "11101100000010001100110111111111")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100110111111111") & " : expected" & LF &
to_string(cuft("1 min","66MHz")) & " : actual"
severity error;


assert (cuft("1 hr","66MHz") = "11011101010010000100000100011111111111")
report "count_up_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100011111111111") & " : expected" & LF &
to_string(cuft("1 hr","66MHz")) & " : actual"
severity error;


assert (cuft("1 day","66MHz") = "1010010111110110001100001101011111111111111")
report "count_up_for_time_test error # 4 " & LF &
to_string("1010010111110110001100001101011111111111111") & " : expected" & LF &
to_string(cuft("1 day","66MHz")) & " : actual"
severity error;




assert (cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "1010110011111110011100011111110110010010001")
report "count_up_for_time_test error # 6 " & LF &
to_string("1010110011111110011100011111110110010010001") & " : expected" & LF &
to_string(cuft("1 day","66MHz")+cuft("1 hr","66MHz")+cuft("1 min","66MHz")+cuft("1 sec","66MHz")+cuft("1 ms","66MHz")+cuft("1 us","66MHz")+cuft("1 ns","66MHz")+cuft("1 ps","66MHz")+cuft("1 fs","66MHz")+cuft("1 as","66MHz")+cuft("1 zs","66MHz")+cuft("1 ys","66MHz")) & " : actual" & LF &
to_string(cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;



assert (cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "11100011100110011110110101000101011010000000101000")
report "count_up_for_time_test error # 8 " & LF &
to_string("11100011100110011110110101000101011010000000101000") & " : expected" & LF &
to_string(cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-3 kHz") = "0")
report "count_up_for_time_test error # 9 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-18 eHz") = "0")
report "count_up_for_time_test error # 10 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cuft("1 ns ","1E-15 yHz") = "0")
report "count_up_for_time_test error # 11 " & LF &
to_string("0") & " : expected" & LF &
to_string(cuft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cuft("1 us ","1E-15 yHz") = "1111100111")
report "count_up_for_time_test error # 12 " & LF &
to_string("1111100111") & " : expected" & LF &
to_string(cuft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cuft("20 ms ","50 MHz"),21);

assert (ext(cuft("20 ms ","50 MHz"),25) = "0000011110100001000111111")
report "count_up_for_time_test error # 13 " & LF &
to_string("0000011110100001000111111") & " : expected" & LF &
to_string(ext(cuft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test : process
begin

assert (cufth("1 us ","1E-15 yHz") = 9)
report "count_up_for_time_high_test error # 1 " & LF &
to_string(9) & " : expected" & LF &
to_string(cufth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cufth("8 ms ","1 kHz") = 2)
report "count_up_for_time_high_test2 error # 1 " & LF &
to_string(2) & " : expected" & LF &
to_string(cufth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;

--function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value


--function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value



--function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed


--function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

--function ext(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector;
ext_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);

assert (ext2(slvVar,7) = "0000111") -- 7 bits
report "ext_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,7)) & " : actual"
severity error;

assert (ext2(slvVar,4) = "0111") -- 4 bits
report "ext_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,4)) & " : actual"
severity error;

assert (ext2(slvVar,4)'length = 4) -- 4 bits
report "ext_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(ext2(slvVar,4)'length) & " : actual"
severity error;

wait;
end process;



--function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order


--function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order



--function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order


--function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector



--function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed



--function mult_s(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply



--function mult_us(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply



--function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed



--function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value


--function now return string; -- returns a string representation of the current simulation time
now_test : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

wait for 3 sec;

assert FALSE
report "now_test error # 1 " & LF &
now & " : expected" & LF
severity error;

wait;
end process;


--function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function reduce_high(vectorVal : std_logic_vector) return integer; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function seq(str1Val : string;
-- str2Val : string) return boolean;



--function shl(vectorVal : std_logic_vector;
-- natVal : natural) return std_logic_vector;



--function slv_to_bcd(vectorVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified



--function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed



--function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
-- MSB_Val : std_logic;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value



--function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer



--function str_to_led(stringVal : string;
-- CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs



--function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
str_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (str_to_slv("1") = "01") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("0") = "0") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("00") & " : expected" & LF &
to_string(str_to_slv("0")) & " : actual"
severity error;

assert (str_to_slv("-1") = "11") -- -1
report "bcd_to_led_test error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(str_to_slv("-1")) & " : actual"
severity error;

assert (str_to_slv("10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 1 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv("10 us"))
severity error;

assert (str_to_slv(" 10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 2 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us"))
severity error;

assert (str_to_slv(" 10 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 3 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us "))
severity error;

assert (str_to_slv(" 10.0 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 4 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0 us "))
severity error;

assert (str_to_slv(" 0.0100 ms ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 5 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0100 ms "))
severity error;

assert (str_to_slv(" 0.0000100sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0000100sec "))
severity error;

assert (str_to_slv(" 10E-6 sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E-6 sec "))
severity error;


assert (str_to_slv(" 10,000,000,000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 7 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10,000,000,000 "))
severity error;

assert (str_to_slv(" 100,000Hz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 8 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100,000Hz "))
severity error;


assert (str_to_slv(" 100kHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100kHz "))
severity error;

assert (str_to_slv(" 0.1MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.1MHz "))
severity error;

assert (str_to_slv(" .1 MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" .1 MHz "))
severity error;

assert (str_to_slv(" 0.0001GHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 10 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0001GHz "))
severity error;


assert (str_to_slv(" 10E 9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 11 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E 9 "))
severity error;


assert (str_to_slv(" 10E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 12 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9.000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9.000 "))
severity error;

assert (str_to_slv(" 100E+3 HZ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 14 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;


assert (str_to_slv(" 1") = "01")
report "str_to_slv_test error # 15a " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(str_to_slv(" 1"))
severity error;

assert (str_to_slv(" -1") = "11")
report "str_to_slv_test error # 15b " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(str_to_slv(" -1"))
severity error;


assert (str_to_slv("1") = "01")
report "str_to_slv_test error # 16 " & LF &
to_string("01") & " : expected"
& LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("10") = "01010")
report "str_to_slv_test error # 17 " & LF &
to_string("01010") & " : expected"
& LF &
to_string(str_to_slv("10")) & " : actual"
severity error;

assert (str_to_slv(" 100E+3 HZ ps ns MHz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 18 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100E+3 HZ Hz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 19 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100,000 HZ 234sec") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 20 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ 234sec"))
severity error;

assert (str_to_slv("1 day") = "01001010111100001010011101100011101110110001110000000000000000000000") -- 0
report "bcd_to_led_test error # 21 " & LF &
to_string("01001010111100001010011101100011101110110001110000000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 day")) & " : actual"
severity error;

assert (str_to_slv("1 hr") = "011000111110101110001001110110100100111011010000000000000000000") -- 0
report "bcd_to_led_test error # 22 " & LF &
to_string("011000111110101110001001110110100100111011010000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 hr")) & " : actual"
severity error;

assert (str_to_slv("1 min") = "011010101001010011010111010011110100001100000000000000000") -- 0
report "bcd_to_led_test error # 23 " & LF &
to_string("011010101001010011010111010011110100001100000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 min")) & " : actual"
severity error;

assert (str_to_slv("1 sec") = "011100011010111111010100100110001101000000000000000") -- 0
report "bcd_to_led_test error # 24 " & LF &
to_string("011100011010111111010100100110001101000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 sec")) & " : actual"
severity error;

assert (str_to_slv("1 ms") = "01110100011010100101001010001000000000000") -- 0
report "bcd_to_led_test error # 25 " & LF &
to_string("01110100011010100101001010001000000000000") & " : expected" & LF &
to_string(str_to_slv("1 ms")) & " : actual"
severity error;

assert (str_to_slv("1 us") = "0111011100110101100101000000000") -- 0
report "bcd_to_led_test error # 26 " & LF &
to_string("0111011100110101100101000000000") & " : expected" & LF &
to_string(str_to_slv("1 us")) & " : actual"
severity error;

assert (str_to_slv("1 ns") = "011110100001001000000") -- 0
report "bcd_to_led_test error # 27 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 ns")) & " : actual"
severity error;

assert (str_to_slv("1 ps") = "01111101000") -- 0
report "bcd_to_led_test error # 28 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 ps")) & " : actual"
severity error;

assert (str_to_slv("1 fs") = "01") -- 0
report "bcd_to_led_test error # 29 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 fs")) & " : actual"
severity error;

assert (str_to_slv("1 as",24) = "011110100001001000000") -- 0
report "bcd_to_led_test error # 30 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 as",24)) & " : actual"
severity error;

assert (str_to_slv("1 zs",24) = "01111101000") -- 0
report "bcd_to_led_test error # 31 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 zs",24)) & " : actual"
severity error;

assert (str_to_slv("1 ys",24) = "01") -- 0
report "bcd_to_led_test error # 32 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 ys",24)) & " : actual"
severity error;


assert (str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs") = "01001110000111011000111100110011111100101100110000111010000000101001") -- 0
report "bcd_to_led_test error # 33 " & LF &
to_string("01001110000111011000111100110011111100101100110000111010000000101001") & " : expected" & LF &
to_string(str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs")) & " : actual"
severity error;


wait;
end process;


--function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed



--function str_to_slv_var_base(stringVal : string;
-- intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed



--function str_to_slv_var_base_high(stringVal : string;
-- intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value



--function strh(stringVal : string) return integer;

sxt_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := sxt2(int_to_slv(-1000),slv1Var'length);
slv2Var := sxt2(int_to_slv(-6),slv2Var'length);

assert (sxt2(slvVar,7) = "0000111") -- 7 bits
report "sxt2_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,7)) & " : actual"
severity error;

assert (sxt2(slvVar,4) = "0111") -- 4 bits
report "sxt2_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,4)) & " : actual"
severity error;

assert (sxt2("1001",7) = "1111001") -- 7 bits
report "sxt2_test error # 3 " & LF &
to_string("1111001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;

assert (sxt2("00",7) = "0000000") -- 4 bits
report "sxt2_test error # 4 " & LF &
to_string("0000000") & " : expected" & LF &
to_string(sxt2("00",7)) & " : actual"
severity error;

assert (sxt2("1001",4) = "1001") -- 7 bits
report "sxt2_test error # 5 " & LF &
to_string("1001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;


wait;
end process;

---- synopsys translate_off
--function time_to_slv(timeVal : time;
-- clkFreqVal : frequency) return std_logic_vector;
---- synopsys translate_on
--
--function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function
--
--function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency
--
---- synopsys translate_off
--function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
--function to_string(realVal : real) return string; -- returns a string value for an real value passed
--function to_string(vectorVal : std_logic_vector) return string;
---- synopsys translate_on
--
--function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--
--function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
--function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed
--
--function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed
--
--function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed
--
--------------------------------------------------------------------------------
---- Procedure Declarations
--------------------------------------------------------------------------------
---- synopsys translate_off
--procedure clkgen(
-- constant clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkPeriodSig : in time;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
---- synopsys translate_on
--
--procedure FF(
-- signal Clk : in std_logic;
-- signal Rst : in std_logic;
-- signal D : in std_logic_vector;
-- signal Q : out std_logic_vector);
--
--procedure slv_to_bcd(
-- signal BCD_RIn : in std_logic_vector;
-- signal BinIn : in std_logic_vector;
-- signal BinFBIn : in std_logic_vector;
-- signal ClkIn : in std_logic;
-- constant BCD_DigitsVal : in integer;
-- signal EnIn : in std_logic;
-- signal RstLowIn : in std_logic;
-- signal BCD_ROut : out std_logic_vector;
-- signal Bin_ROut : out std_logic_vector;
-- signal DoneOut : out std_logic);











































divider_test : process
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);
begin
slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);
slv3Var := slv1Var/slv2Var;
-- assert FALSE
-- report "divider output :" & LF & to_string(to_int(slv1Var)) & " / " & to_string(to_int(slv2Var)) & " = " & to_string(to_int(slv3Var))
-- severity note;
wait;
end process;


bcd_to_led_test : process
variable slvVar : slv(27 downto 0);
begin





slvVar := bcd_to_led("0011001000010000",False); -- 3210
assert (slvVar = "1111001110110101100001111110")
report "bcd_to_led_test error # 1 "
severity error;
slvVar := bcd_to_led("0111011001010100",False); -- 7654
assert (slvVar = "1110010101111110110110110011")
report "bcd_to_led_test error # 2 "
severity error;
slvVar := bcd_to_led("0001000010011000",False); -- 1098
assert (slvVar = "0110000111111011100111111111")
report "bcd_to_led_test error # 3 "
severity error;
slvVar := bcd_to_led("0011001000010000",True); -- 3210
assert (slvVar = "0000110001001010011110000001")
report "bcd_to_led_test error # 4 "
severity error;
slvVar := bcd_to_led("0111011001010100",True); -- 7654
assert (slvVar = "0001101010000001001001001100")
report "bcd_to_led_test error # 5 "
severity error;
slvVar := bcd_to_led("0001000010011000",True); -- 1098
assert (slvVar = "1001111000000100011000000000")
report "bcd_to_led_test error # 6 "
severity error;
wait;
end process;











str_to_int_test : process
variable intVar : integer;
begin
intVar := str_to_int("10"); -- 3210
assert (intVar = 10)
report "str_to_int_test error # 1 " & LF &
"expected : 10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-10 sec"); -- 3210
assert (intVar = -10)
report "str_to_int_test error # 2 " & LF &
"expected : -10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-6 sec"); -- 3210
assert (intVar = -6)
report "str_to_int_test error # 3 " & LF &
"expected : -6" & LF &
"actual : " & to_string(intVar)
severity error;

wait;
end process;




reduce_test : process

begin

assert (reduce("00000") = "00") -- 0
report "reduce error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(reduce("00000")) & " : actual"
severity error;

assert (reduce("00001") = "01") -- 1
report "reduce error # 2 " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(reduce("00001"))
severity error;

assert (reduce("11111") = "11") -- -1
report "reduce error # 3 " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(reduce("11111"))
severity error;

assert (reduce("10000") = "10000") -- -16
report "reduce error # 4 " & LF &
"expected : " & to_string("10000") & LF &
"actual : " & to_string(reduce("10000"))
severity error;

wait;

end process;











--exp_test : process
--variable timeBaseVar : slv(500 downto 0);
--variable lineVar : line;
--begin
-- timeBaseVar := ext("01",timeBaseVar'length);
-- for loopVar in 1 to 50 loop
-- timeBaseVar := timeBaseVar(timeBaseVar'high-4 downto 0) * "1010";
--
---- write(lineVar,to_string(real(reduce_high(timeBaseVar))/real(loopVar)));
---- write(lineVar,LF);
-- assert FALSE
-- report
-- to_string(real(reduce_high(timeBaseVar))/real(loopVar)) & LF
-- severity note;
-- end loop;
--
-- wait;
--end process;



unsigned_mult_test : process

begin

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

assert (mult_us("000","011") = "000000") -- 0
report "mult error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","011")) & " : actual"
severity error;

assert (mult_us("011","000") = "000000") -- 0
report "mult error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("011","000")) & " : actual"
severity error;

assert (mult_us("000","101") = "000000") -- 0
report "mult error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","101")) & " : actual"
severity error;

assert (mult_us("101","000") = "000000") -- 0
report "mult error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("101","000")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 7 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

wait;

end process;








signed_mult_test : process

begin

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("000","011") = "000000") -- 0
report "mult_s error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","011")) & " : actual"
severity error;

assert (mult_s("011","000") = "000000") -- 0
report "mult_s error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("011","000")) & " : actual"
severity error;

assert (mult_s("000","101") = "000000") -- 0
report "mult_s error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","101")) & " : actual"
severity error;

assert (mult_s("101","000") = "000000") -- 0
report "mult_s error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("101","000")) & " : actual"
severity error;

assert (mult_s("011","101") = "110111") -- 3 * (-3) = -9
report "mult_s error # 7 " & LF &
to_string("110111") & " : expected" & LF &
to_string(mult_s("011","101")) & " : actual"
severity error;

assert (mult_s("011","100") = "110100") -- 3 * (-4) = -12
report "mult_s error # 8 " & LF &
to_string("110100") & " : expected" & LF &
to_string(mult_s("011","100")) & " : actual"
severity error;

assert (mult_s("101","101") = "001001") -- (-3) * (-3) = 9
report "mult_s error # 9 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("101","101")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 10 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 11 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;


assert (mult_s("100","100") = "010000") -- -4 * -4 = 16
report "mult_s error # 11 " & LF &
to_string("010000") & " : expected" & LF &
to_string(mult_s("100","100")) & " : actual"
severity error;



wait;

end process;








conv_to_hex_test : process
constant slvVar : slv(11 downto 0) := "101011110000";

begin

assert (conv_to_hex(slvVar) = "AF0") -- 0
report "mult_s error # 1 " & LF &
"AF0 : expected" & LF &
conv_to_hex(slvVar) & " : actual"
severity error;


wait;

end process;


--assert FALSE
--report "THIS IS THE END OF SIMULATION" & LF
--severity failure;

------------------------------------------------------------------------------
end behavioral;
-----------------------------------------------------------------------------




-- synopsys translate_on
 
M

My Name

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


--type StringArray is array (0 to 9) of string(1 to 1);


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : natural := 30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := CFT_BASE_SIZE*4;



--constant IntString : StringArray := ("0","1","2","3","4","5","6","7","8","9");



------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference

function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cdfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural; -- This function returns a natural representing the number of characters required to reprsent an integer value. It is essentially an integer'length function for the characters.

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference


function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector; -- create a 50% duty cycle count time using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference

function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cufth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfi_syn(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function itoa(intVal : integer) return string;

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

-- synopsys translate_off
impure function now return string; -- returns a string representation of the current simulation time
-- synopsys translate_on

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed
function reduce_length(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that


-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector;
-- synopsys translate_on

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency

-- synopsys translate_off
function to_string(intVal : integer) return string; -- returns the string image of an integer value passed
function to_string(realVal : real) return string; -- returns the string image of a real value passed
function to_string(timeVal : time) return string; -- returns the string image of a time value passed
function to_string(vectorVal : std_logic_vector) return string; -- returns the string image of a std_logic_vector value passed
-- synopsys translate_on

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
-- synthesis translate_off
--alias cft is count_for_time[string,string return std_logic_vector]; -- synplify doesn't like "[" or "]"
--alias cfth is count_for_time_high[string,string return integer];
-- synthesis translate_on
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce((timeVar/freqStrVar) - 2);
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cdfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length((timeVar/freqStrVar) - 2);
if (lengthVar >= natVal) then
return reduce((timeVar/freqStrVar) - 2);
else
return zeroVar & reduce((timeVar/freqStrVar) - 2);
end if;
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdfth (count down for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 2
-- for use in counting down to underflow) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cdfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high((timeVar/freqStrVar) - 2);
end cdfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length(timeVar/freqStrVar);
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : clkcnt (50% duty cycle clock count)
--
-- DESCRIPTION : This function takes a string based frequency value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector is
variable freq1StrVar : std_logic_vector(str_to_slv_var_base_high(freq1StrVal,CFT_BASE_SIZE) downto 0);
variable freq2StrVar : std_logic_vector(str_to_slv_var_base_high(freq2StrVal,CFT_BASE_SIZE) downto 0);
begin
freq1StrVar := str_to_slv(freq1StrVal,CFT_BASE_SIZE);
freq2StrVar := str_to_slv(freq2StrVal,CFT_BASE_SIZE);
return reduce((freq1StrVar/freq2StrVar)/2-2);
end clkcnt;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_unsigned((timeVar/freqStrVar) - 1);
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to:
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cufth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length_unsigned((timeVar/freqStrVar) - 1);
if (lengthVar >= natVal) then
return reduce_unsigned((timeVar/freqStrVar) - 1);
else
return zeroVar & reduce_unsigned((timeVar/freqStrVar) - 1);
end if;
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cufth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 1
-- for use in counting up from zero to the proper value) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cufth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high_unsigned((timeVar/freqStrVar) - 1);
end cufth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi_syn (decimal places for integer (synthesizeable))
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi_syn(intVal : integer) return natural is
variable resultVar : natural;
begin
if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
resultVar := 10;
elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
resultVar := 9;
elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
resultVar := 8;
elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
resultVar := 7;
elsif (intVal <= -100_000 or intVal >= 100_000) then
resultVar := 6;
elsif (intVal <= -10_000 or intVal >= 10_000) then
resultVar := 5;
elsif (intVal <= -1_000 or intVal >= 1_000) then
resultVar := 4;
elsif (intVal <= -100 or intVal >= 100) then
resultVar := 3;
elsif (intVal <= -10 or intVal >= 10) then
resultVar := 2;
else
resultVar := 1;
end if;
return resultVar;
end dpfi_syn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : itoa
--
-- DESCRIPTION : commonly used integer-to-string type converter
--
-- NOTES
--
------------------------------------------------------------------------------
--function itoa(intVal : integer) return string is
-- variable IntVar : integer := intVal;
--begin
-- if (IntVar < 0) then
-- return "-" & itoa(-IntVar);
-- elsif IntVar < 10 then
-- return IntString(IntVar);
-- else
-- return itoa(IntVar/10) & IntString(IntVar rem 10);
-- end if;
--end function itoa;


function itoa(intVal : integer) return string is
begin
return to_string(intVal);
end function itoa;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : now
--
-- DESCRIPTION : This function returns a string representation
-- of the current simulation time
--
-- NOTES :
--
------------------------------------------------------------------------------
-- synopsys translate_off
impure function now return string is
variable lineVar : line;
variable resultVar : string(1 to time'image(now)'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, time'image(now));
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end now;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- And add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_unsigned
--
-- DESCRIPTION : This function returns a vector with all sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length(vectorVal : std_logic_vector) return integer is
begin
return reduce_high(vectorVal) + 1;
end reduce_length;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer is
begin
return reduce_high_unsigned(vectorVal) + 1;
end reduce_length_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := intVal;
decPntFndVar := false;
decPlacesVar := 0;
expFndVar := false;
expVar := 0;
freqUnitFndVar := false;
negVar := false;
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false;
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar;
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : time_to_slv (convert time to slv)
--
-- DESCRIPTION : converts a time value referenced to a clock frequency
-- to a standard logic vector value large enough to
-- represent it as a signed integer value
--
-- NOTES
-- This function does not work with Synplify
------------------------------------------------------------------------------
-- synopsys translate_off
function time_to_slv(timeVal : time;
clkFreqVal : frequency) return std_logic_vector is
variable resultVar : std_logic_vector(int_to_slv(timeVal/to_period(clkFreqVal))'range);
begin
resultVar := int_to_slv(timeVal/to_period(clkFreqVal));
return resultVar;
end time_to_slv;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(intVal : integer) return string is
variable lineVar : line;
variable resultVar : string(1 to integer'Image(intVal)'length);
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, integer'Image(intVal));
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(realVal : real) return string is
variable lengthVar : natural;
variable lineVar : line;
variable resultVar : string(1 to real'Image(realVal)'length);
begin
--Std.TextIO.Write(lineVar, intVal);
Write(lineVar, real'Image(realVal));
lengthVar := lineVar.all'length;
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (time)
--
-- DESCRIPTION : This function returns a string value representing the
-- time value passed to it.
--
-- NOTES :
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(timeVal : time) return string is
variable lineVar : line;
variable resultVar : string(1 to time'image(timeVal)'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, time'image(timeVal));
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, vectorVal);
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end to_string;
-- synopsys translate_on


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic
) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic
) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector
) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------
















-- end of extension pack
-- start of test bench























































-- synopsys translate_off



------------------------------------------------------------------------------
-- Extension Pack test bench
------------------------------------------------------------------------------

library ieee, extension_lib;
use ieee.std_logic_1164.all;
use ieee.std_logic_unsigned.all;
use ieee.std_logic_arith.all;
use extension_lib.extension_pack.all;
use ieee.std_logic_textio.all;
use std.textio.all;

entity extension_pack_tb is
end extension_pack_tb;


------------------------------------------------------------------------------
architecture behavioral of extension_pack_tb is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Global Component/Function/Procedure Declarations
------------------------------------------------------------------------------
begin


star_operator_test : process
variable slvVar : slv(2 downto 0) := "111";
begin

assert (7*slvVar = "0110001") -- 7*7 = 49
report "* error # 1 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(7*slvVar) & " : actual"
severity error;

assert (slvVar*7 = "0110001") -- 7*7 = 49
report "* error # 2 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(slvVar*7) & " : actual"
severity error;

wait;
end process;




--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : std_logic_vector) return std_logic_vector;
slash1_operator_test : process
constant slvVar : slv := "0110001";
begin

assert ("0110001"/"111" = "0000111") -- 49/7 = 7
report "slash1_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string("0110001"/"111") & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : integer) return std_logic_vector;
slash2_operator_test : process
constant slvVar : slv := "0110001";
begin

assert (slvVar/7 = "0000111") -- 49/7 = 7
report "slash2_operator_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(slvVar/7) & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : string;
-- DivisorVal : integer) return std_logic_vector;
slash3_operator_test : process
constant var : string := "49";
begin

assert (var/7 = "0000111") -- 49/7 = 7
report "slash3_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(var/7) & " : actual"
severity error;

wait;
end process;



--function bcd_to_led(slvVal : std_logic_vector ;
-- CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion
bcd_to_led1_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_led(slvVar,true) = "0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") -- 123456789ABCDEF =
report "bcd_to_led_test error # 1 " & LF &
to_string("0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") & " : expected" & LF &
to_string(bcd_to_led(slvVar,true)) & " : actual"
severity error;

assert (bcd_to_led(slvVar,false) = "1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") -- 123456789ABCDEF =
report "bcd_to_led_test error # 2 " & LF &
to_string("1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") & " : expected" & LF &
to_string(bcd_to_led(slvVar,false)) & " : actual"
severity error;

wait;
end process;







--function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed
bcd_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_slv(slvVar) = "011100000100100010000110000111101101001110111111") -- 123456789ABCDEF = 123456790123455
report "bcd_to_slv_test error # 1 " & LF &
to_string("011100000100100010000110000111101101001110111111") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("00000001001000110100010101100111100010010000") = "01001001100101100000001011010010") -- 1234567890 =
report "bcd_to_slv_test error # 2 " & LF &
to_string("01001001100101100000001011010010") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("101010111100110111101111") = "100010010010001111111") -- ABCDEF (1123455)
report "bcd_to_slv_test error # 3 " & LF &
to_string("100010010010001111111") & " : expected" & LF &
to_string(bcd_to_slv("101010111100110111101111")) & " : actual"
severity error;


wait;
end process;


--function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value




--function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function
bv_to_slv_test : process
constant bvVar : bv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bv_to_slv(bvVar) = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 1 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(bvVar)) & " : actual"
severity error;

assert (bv_to_slv(X"123456789ABCDEF") = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 2 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(X"123456789ABCDEF")) & " : actual"
severity error;

wait;
end process;


--function cdft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdft("8 ms ","1 kHz") = slvVar)
report "count_down_for_time2_test error # 1 " & LF &
to_string("0111") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz")) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz")) = "0110")
report "count_down_for_time2_test error # 2 " & LF &
to_string("0110") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length = 4)
report "count_down_for_time2_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length) & " : actual"
severity error;

wait;
end process;




--function cdfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high_test : process
begin

assert (cdfth("1 us ","1E-15 yHz") = 10)
report "count_down_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cdfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;

--function cdfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdfth("8 ms ","1 kHz") = 3)
report "count_down_for_time_high_test2 error # 1 " & LF &
to_string(3) & " : expected" & LF &
to_string(cdfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;





--function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer
ceil_test : process
begin

assert (ceil(-9.999999) = -9.0)
report "ceil_test error # 1 " & LF &
to_string(-9.0) & " : expected" & LF &
to_string(ceil(-9.999999)) & " : actual"
severity error;

assert (ceil(9.999999) = 10.0)
report "ceil_test error # 2 " & LF &
to_string(10.0) & " : expected" & LF &
to_string(ceil(9.999999)) & " : actual"
severity error;

wait;
end process;



--function cfi(intVal : integer) return natural;
cfi_test : process
begin

assert (cfi(-1000) = 5)
report "cfi_test error # 1 " & LF &
"5 : expected" & LF &
to_string(cfi(-1000)) & " : actual"
severity error;

assert (cfi(-10000) = 6)
report "cfi_test error # 2 " & LF &
"6 : expected" & LF &
to_string(cfi(-10000)) & " : actual"
severity error;


assert (cfi(1000) = 4)
report "cfi_test error # 3 " & LF &
"4 : expected" & LF &
to_string(cfi(1000)) & " : actual"
severity error;


assert (cfi(-100_000) = 7)
report "cfi_test error # 4 " & LF &
"7 : expected" & LF &
to_string(cfi(-100_000)) & " : actual"
severity error;


assert (cfi(100_000) = 6)
report "cfi_test error # 5 " & LF &
"6 : expected" & LF &
to_string(cfi(100_000)) & " : actual"
severity error;

assert (cfi(-9999999) = 8)
report "cfi_test error # 6 " & LF &
to_string(8) & " : expected" & LF &
to_string(cfi(-9999999)) & " : actual"
severity error;

assert (cfi(9999999) = 7)
report "cfi_test error # 7 " & LF &
to_string(7) & " : expected" & LF &
to_string(cfi(9999999)) & " : actual"
severity error;

wait;
end process;


--function cft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cft(CNTTIME,SYSCLKFREQ) = "100111010101101100110100000000")
report "count_for_time_test error # 1 " & LF &
to_string("100111010101101100110100000000") & " : expected" & LF &
to_string(cft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cft("1 min","66MHz") = "11101100000010001100111000000000")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100111000000000") & " : expected" & LF &
to_string(cft("1 min","66MHz")) & " : actual"
severity error;


assert (cft("1 hr","66MHz") = "11011101010010000100000100100000000000")
report "count_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100100000000000") & " : expected" & LF &
to_string(cft("1 hr","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz") = "01010010111110110001100001101100000000000000")
report "count_for_time_test error # 4 " & LF &
to_string("01010010111110110001100001101100000000000000") & " : expected" & LF &
to_string(cft("1 day","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 5 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz")) & " : actual"
severity error;


assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 6 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")+cft("1 as","66MHz")+cft("1 zs","66MHz")+cft("1 ys","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 7 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "011100011100110011110110101000101011010000000101001")
report "count_for_time_test error # 8 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-3 kHz") = "01")
report "count_for_time_test error # 9 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-18 eHz") = "01")
report "count_for_time_test error # 10 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cft("1 ns ","1E-15 yHz") = "01")
report "count_for_time_test error # 11 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cft("1 us ","1E-15 yHz") = "01111101000")
report "count_for_time_test error # 12 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(cft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cft("20 ms ","50 MHz"),21);

assert (ext(cft("20 ms ","50 MHz"),21) = "011110100001001000000")
report "count_for_time_test error # 13 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(ext(cft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test : process
begin

assert (cfth("1 us ","1E-15 yHz") = 10)
report "count_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cfth("8 ms ","1 kHz") = 4)
report "count_for_time_high_test2 error # 1 " & LF &
to_string(4) & " : expected" & LF &
to_string(cfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;



--function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
conv_to_hex_test1 : process
variable testVar : bv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test1 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
conv_to_hex_test2 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test2 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion
conv_to_hex_test3 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test3 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function cslv(int1Val : integer;
-- int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(sigVal : signed;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(usgVal : unsigned;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested


--function cuft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cuft(CNTTIME,SYSCLKFREQ) = "100111010101101100110011111111")
report "count_up_for_time_test error # 1 " & LF &
to_string("100111010101101100110011111111") & " : expected" & LF &
to_string(cuft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cuft("1 min","66MHz") = "11101100000010001100110111111111")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100110111111111") & " : expected" & LF &
to_string(cuft("1 min","66MHz")) & " : actual"
severity error;


assert (cuft("1 hr","66MHz") = "11011101010010000100000100011111111111")
report "count_up_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100011111111111") & " : expected" & LF &
to_string(cuft("1 hr","66MHz")) & " : actual"
severity error;


assert (cuft("1 day","66MHz") = "1010010111110110001100001101011111111111111")
report "count_up_for_time_test error # 4 " & LF &
to_string("1010010111110110001100001101011111111111111") & " : expected" & LF &
to_string(cuft("1 day","66MHz")) & " : actual"
severity error;




assert (cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "1010110011111110011100011111110110010010001")
report "count_up_for_time_test error # 6 " & LF &
to_string("1010110011111110011100011111110110010010001") & " : expected" & LF &
to_string(cuft("1 day","66MHz")+cuft("1 hr","66MHz")+cuft("1 min","66MHz")+cuft("1 sec","66MHz")+cuft("1 ms","66MHz")+cuft("1 us","66MHz")+cuft("1 ns","66MHz")+cuft("1 ps","66MHz")+cuft("1 fs","66MHz")+cuft("1 as","66MHz")+cuft("1 zs","66MHz")+cuft("1 ys","66MHz")) & " : actual" & LF &
to_string(cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;



assert (cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "11100011100110011110110101000101011010000000101000")
report "count_up_for_time_test error # 8 " & LF &
to_string("11100011100110011110110101000101011010000000101000") & " : expected" & LF &
to_string(cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-3 kHz") = "0")
report "count_up_for_time_test error # 9 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-18 eHz") = "0")
report "count_up_for_time_test error # 10 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cuft("1 ns ","1E-15 yHz") = "0")
report "count_up_for_time_test error # 11 " & LF &
to_string("0") & " : expected" & LF &
to_string(cuft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cuft("1 us ","1E-15 yHz") = "1111100111")
report "count_up_for_time_test error # 12 " & LF &
to_string("1111100111") & " : expected" & LF &
to_string(cuft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cuft("20 ms ","50 MHz"),21);

assert (ext(cuft("20 ms ","50 MHz"),25) = "0000011110100001000111111")
report "count_up_for_time_test error # 13 " & LF &
to_string("0000011110100001000111111") & " : expected" & LF &
to_string(ext(cuft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test : process
begin

assert (cufth("1 us ","1E-15 yHz") = 9)
report "count_up_for_time_high_test error # 1 " & LF &
to_string(9) & " : expected" & LF &
to_string(cufth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cufth("8 ms ","1 kHz") = 2)
report "count_up_for_time_high_test2 error # 1 " & LF &
to_string(2) & " : expected" & LF &
to_string(cufth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;

--function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value


--function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value



--function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed


--function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

--function ext(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector;
ext_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);

assert (ext2(slvVar,7) = "0000111") -- 7 bits
report "ext_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,7)) & " : actual"
severity error;

assert (ext2(slvVar,4) = "0111") -- 4 bits
report "ext_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,4)) & " : actual"
severity error;

assert (ext2(slvVar,4)'length = 4) -- 4 bits
report "ext_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(ext2(slvVar,4)'length) & " : actual"
severity error;

wait;
end process;



--function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order


--function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order



--function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order


--function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector



--function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed



--function mult_s(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply



--function mult_us(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply



--function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed



--function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value


--function now return string; -- returns a string representation of the current simulation time
now_test : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

wait for 3 sec;

assert FALSE
report "now_test error # 1 " & LF &
now & " : expected" & LF
severity error;

wait;
end process;


--function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function reduce_high(vectorVal : std_logic_vector) return integer; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function seq(str1Val : string;
-- str2Val : string) return boolean;



--function shl(vectorVal : std_logic_vector;
-- natVal : natural) return std_logic_vector;



--function slv_to_bcd(vectorVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified



--function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed



--function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
-- MSB_Val : std_logic;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value



--function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer



--function str_to_led(stringVal : string;
-- CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs



--function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
str_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (str_to_slv("1") = "01") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("0") = "0") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("00") & " : expected" & LF &
to_string(str_to_slv("0")) & " : actual"
severity error;

assert (str_to_slv("-1") = "11") -- -1
report "bcd_to_led_test error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(str_to_slv("-1")) & " : actual"
severity error;

assert (str_to_slv("10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 1 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv("10 us"))
severity error;

assert (str_to_slv(" 10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 2 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us"))
severity error;

assert (str_to_slv(" 10 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 3 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us "))
severity error;

assert (str_to_slv(" 10.0 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 4 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0 us "))
severity error;

assert (str_to_slv(" 0.0100 ms ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 5 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0100 ms "))
severity error;

assert (str_to_slv(" 0.0000100sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0000100sec "))
severity error;

assert (str_to_slv(" 10E-6 sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E-6 sec "))
severity error;


assert (str_to_slv(" 10,000,000,000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 7 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10,000,000,000 "))
severity error;

assert (str_to_slv(" 100,000Hz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 8 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100,000Hz "))
severity error;


assert (str_to_slv(" 100kHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100kHz "))
severity error;

assert (str_to_slv(" 0.1MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.1MHz "))
severity error;

assert (str_to_slv(" .1 MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" .1 MHz "))
severity error;

assert (str_to_slv(" 0.0001GHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 10 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0001GHz "))
severity error;


assert (str_to_slv(" 10E 9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 11 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E 9 "))
severity error;


assert (str_to_slv(" 10E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 12 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9.000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9.000 "))
severity error;

assert (str_to_slv(" 100E+3 HZ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 14 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;


assert (str_to_slv(" 1") = "01")
report "str_to_slv_test error # 15a " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(str_to_slv(" 1"))
severity error;

assert (str_to_slv(" -1") = "11")
report "str_to_slv_test error # 15b " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(str_to_slv(" -1"))
severity error;


assert (str_to_slv("1") = "01")
report "str_to_slv_test error # 16 " & LF &
to_string("01") & " : expected"
& LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("10") = "01010")
report "str_to_slv_test error # 17 " & LF &
to_string("01010") & " : expected"
& LF &
to_string(str_to_slv("10")) & " : actual"
severity error;

assert (str_to_slv(" 100E+3 HZ ps ns MHz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 18 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100E+3 HZ Hz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 19 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100,000 HZ 234sec") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 20 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ 234sec"))
severity error;

assert (str_to_slv("1 day") = "01001010111100001010011101100011101110110001110000000000000000000000") -- 0
report "bcd_to_led_test error # 21 " & LF &
to_string("01001010111100001010011101100011101110110001110000000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 day")) & " : actual"
severity error;

assert (str_to_slv("1 hr") = "011000111110101110001001110110100100111011010000000000000000000") -- 0
report "bcd_to_led_test error # 22 " & LF &
to_string("011000111110101110001001110110100100111011010000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 hr")) & " : actual"
severity error;

assert (str_to_slv("1 min") = "011010101001010011010111010011110100001100000000000000000") -- 0
report "bcd_to_led_test error # 23 " & LF &
to_string("011010101001010011010111010011110100001100000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 min")) & " : actual"
severity error;

assert (str_to_slv("1 sec") = "011100011010111111010100100110001101000000000000000") -- 0
report "bcd_to_led_test error # 24 " & LF &
to_string("011100011010111111010100100110001101000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 sec")) & " : actual"
severity error;

assert (str_to_slv("1 ms") = "01110100011010100101001010001000000000000") -- 0
report "bcd_to_led_test error # 25 " & LF &
to_string("01110100011010100101001010001000000000000") & " : expected" & LF &
to_string(str_to_slv("1 ms")) & " : actual"
severity error;

assert (str_to_slv("1 us") = "0111011100110101100101000000000") -- 0
report "bcd_to_led_test error # 26 " & LF &
to_string("0111011100110101100101000000000") & " : expected" & LF &
to_string(str_to_slv("1 us")) & " : actual"
severity error;

assert (str_to_slv("1 ns") = "011110100001001000000") -- 0
report "bcd_to_led_test error # 27 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 ns")) & " : actual"
severity error;

assert (str_to_slv("1 ps") = "01111101000") -- 0
report "bcd_to_led_test error # 28 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 ps")) & " : actual"
severity error;

assert (str_to_slv("1 fs") = "01") -- 0
report "bcd_to_led_test error # 29 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 fs")) & " : actual"
severity error;

assert (str_to_slv("1 as",24) = "011110100001001000000") -- 0
report "bcd_to_led_test error # 30 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 as",24)) & " : actual"
severity error;

assert (str_to_slv("1 zs",24) = "01111101000") -- 0
report "bcd_to_led_test error # 31 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 zs",24)) & " : actual"
severity error;

assert (str_to_slv("1 ys",24) = "01") -- 0
report "bcd_to_led_test error # 32 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 ys",24)) & " : actual"
severity error;


assert (str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs") = "01001110000111011000111100110011111100101100110000111010000000101001") -- 0
report "bcd_to_led_test error # 33 " & LF &
to_string("01001110000111011000111100110011111100101100110000111010000000101001") & " : expected" & LF &
to_string(str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs")) & " : actual"
severity error;


wait;
end process;


--function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed



--function str_to_slv_var_base(stringVal : string;
-- intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed



--function str_to_slv_var_base_high(stringVal : string;
-- intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value



--function strh(stringVal : string) return integer;

sxt_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := sxt2(int_to_slv(-1000),slv1Var'length);
slv2Var := sxt2(int_to_slv(-6),slv2Var'length);

assert (sxt2(slvVar,7) = "0000111") -- 7 bits
report "sxt2_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,7)) & " : actual"
severity error;

assert (sxt2(slvVar,4) = "0111") -- 4 bits
report "sxt2_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,4)) & " : actual"
severity error;

assert (sxt2("1001",7) = "1111001") -- 7 bits
report "sxt2_test error # 3 " & LF &
to_string("1111001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;

assert (sxt2("00",7) = "0000000") -- 4 bits
report "sxt2_test error # 4 " & LF &
to_string("0000000") & " : expected" & LF &
to_string(sxt2("00",7)) & " : actual"
severity error;

assert (sxt2("1001",4) = "1001") -- 7 bits
report "sxt2_test error # 5 " & LF &
to_string("1001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;


wait;
end process;

---- synopsys translate_off
--function time_to_slv(timeVal : time;
-- clkFreqVal : frequency) return std_logic_vector;
---- synopsys translate_on
--
--function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function
--
--function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency
--
---- synopsys translate_off
--function to_string(intVal : integer) return string; -- returns a string value for an integer value passed


--function to_string(realVal : real) return string; -- returns a string value for an real value passed
to_string_test2 : process
begin

assert (to_string(1.000000e+308) = "1.000000e+308")
report "to_string_test2 error # 1 " & LF &
"1.000000e+308" & " : expected" & LF &
to_string(1.000000e+308) & " : actual"
severity error;

assert (to_string(1.000000e-308) = "1.000000e-308")
report "to_string_test2 error # 2 " & LF &
"1.000000e-308" & " : expected" & LF &
to_string(1.000000e-308) & " : actual"
severity error;

assert (to_string(-1.000000e-308) = "-1.000000e-308")
report "to_string_test2 error # 2 " & LF &
"-1.000000e-308" & " : expected" & LF &
to_string(-1.000000e-308) & " : actual"
severity error;

wait;
end process;


--function to_string(timeVal : time) return string;
to_string_test3 : process
begin

assert (to_string(3 ns) = "3 ns")
report "to_string_test3 error # 1 " & LF &
"3 ns" & " : expected" & LF &
to_string(3 ns) & " : actual"
severity error;


assert (to_string(2040 ns) = "2040 ns")
report "to_string_test3 error # 1 " & LF &
"2040 ns" & " : expected" & LF &
to_string(2040 ns) & " : actual"
severity error;

wait;
end process;


--function to_string(vectorVal : std_logic_vector) return string;
---- synopsys translate_on
--
--function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--
--function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
--function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed
--
--function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed
--
--function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed
--
--------------------------------------------------------------------------------
---- Procedure Declarations
--------------------------------------------------------------------------------
---- synopsys translate_off
--procedure clkgen(
-- constant clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkPeriodSig : in time;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
---- synopsys translate_on
--
--procedure FF(
-- signal Clk : in std_logic;
-- signal Rst : in std_logic;
-- signal D : in std_logic_vector;
-- signal Q : out std_logic_vector);
--
--procedure slv_to_bcd(
-- signal BCD_RIn : in std_logic_vector;
-- signal BinIn : in std_logic_vector;
-- signal BinFBIn : in std_logic_vector;
-- signal ClkIn : in std_logic;
-- constant BCD_DigitsVal : in integer;
-- signal EnIn : in std_logic;
-- signal RstLowIn : in std_logic;
-- signal BCD_ROut : out std_logic_vector;
-- signal Bin_ROut : out std_logic_vector;
-- signal DoneOut : out std_logic);


divider_test : process
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);
begin
slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);
slv3Var := slv1Var/slv2Var;
-- assert FALSE
-- report "divider output :" & LF & to_string(to_int(slv1Var)) & " / " & to_string(to_int(slv2Var)) & " = " & to_string(to_int(slv3Var))
-- severity note;
wait;
end process;


bcd_to_led_test : process
variable slvVar : slv(27 downto 0);
begin
slvVar := bcd_to_led("0011001000010000",False); -- 3210
assert (slvVar = "1111001110110101100001111110")
report "bcd_to_led_test error # 1 "
severity error;
slvVar := bcd_to_led("0111011001010100",False); -- 7654
assert (slvVar = "1110010101111110110110110011")
report "bcd_to_led_test error # 2 "
severity error;
slvVar := bcd_to_led("0001000010011000",False); -- 1098
assert (slvVar = "0110000111111011100111111111")
report "bcd_to_led_test error # 3 "
severity error;
slvVar := bcd_to_led("0011001000010000",True); -- 3210
assert (slvVar = "0000110001001010011110000001")
report "bcd_to_led_test error # 4 "
severity error;
slvVar := bcd_to_led("0111011001010100",True); -- 7654
assert (slvVar = "0001101010000001001001001100")
report "bcd_to_led_test error # 5 "
severity error;
slvVar := bcd_to_led("0001000010011000",True); -- 1098
assert (slvVar = "1001111000000100011000000000")
report "bcd_to_led_test error # 6 "
severity error;
wait;
end process;


str_to_int_test : process
variable intVar : integer;
begin
intVar := str_to_int("10"); -- 3210
assert (intVar = 10)
report "str_to_int_test error # 1 " & LF &
"expected : 10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-10 sec"); -- 3210
assert (intVar = -10)
report "str_to_int_test error # 2 " & LF &
"expected : -10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-6 sec"); -- 3210
assert (intVar = -6)
report "str_to_int_test error # 3 " & LF &
"expected : -6" & LF &
"actual : " & to_string(intVar)
severity error;

wait;
end process;




reduce_test : process

begin

assert (reduce("00000") = "00") -- 0
report "reduce error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(reduce("00000")) & " : actual"
severity error;

assert (reduce("00001") = "01") -- 1
report "reduce error # 2 " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(reduce("00001"))
severity error;

assert (reduce("11111") = "11") -- -1
report "reduce error # 3 " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(reduce("11111"))
severity error;

assert (reduce("10000") = "10000") -- -16
report "reduce error # 4 " & LF &
"expected : " & to_string("10000") & LF &
"actual : " & to_string(reduce("10000"))
severity error;

wait;

end process;











--exp_test : process
--variable timeBaseVar : slv(500 downto 0);
--variable lineVar : line;
--begin
-- timeBaseVar := ext("01",timeBaseVar'length);
-- for loopVar in 1 to 50 loop
-- timeBaseVar := timeBaseVar(timeBaseVar'high-4 downto 0) * "1010";
--
---- write(lineVar,to_string(real(reduce_high(timeBaseVar))/real(loopVar)));
---- write(lineVar,LF);
-- assert FALSE
-- report
-- to_string(real(reduce_high(timeBaseVar))/real(loopVar)) & LF
-- severity note;
-- end loop;
--
-- wait;
--end process;



unsigned_mult_test : process

begin

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

assert (mult_us("000","011") = "000000") -- 0
report "mult error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","011")) & " : actual"
severity error;

assert (mult_us("011","000") = "000000") -- 0
report "mult error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("011","000")) & " : actual"
severity error;

assert (mult_us("000","101") = "000000") -- 0
report "mult error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","101")) & " : actual"
severity error;

assert (mult_us("101","000") = "000000") -- 0
report "mult error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("101","000")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 7 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

wait;

end process;








signed_mult_test : process

begin

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("000","011") = "000000") -- 0
report "mult_s error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","011")) & " : actual"
severity error;

assert (mult_s("011","000") = "000000") -- 0
report "mult_s error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("011","000")) & " : actual"
severity error;

assert (mult_s("000","101") = "000000") -- 0
report "mult_s error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","101")) & " : actual"
severity error;

assert (mult_s("101","000") = "000000") -- 0
report "mult_s error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("101","000")) & " : actual"
severity error;

assert (mult_s("011","101") = "110111") -- 3 * (-3) = -9
report "mult_s error # 7 " & LF &
to_string("110111") & " : expected" & LF &
to_string(mult_s("011","101")) & " : actual"
severity error;

assert (mult_s("011","100") = "110100") -- 3 * (-4) = -12
report "mult_s error # 8 " & LF &
to_string("110100") & " : expected" & LF &
to_string(mult_s("011","100")) & " : actual"
severity error;

assert (mult_s("101","101") = "001001") -- (-3) * (-3) = 9
report "mult_s error # 9 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("101","101")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 10 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 11 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;


assert (mult_s("100","100") = "010000") -- -4 * -4 = 16
report "mult_s error # 11 " & LF &
to_string("010000") & " : expected" & LF &
to_string(mult_s("100","100")) & " : actual"
severity error;



wait;

end process;








conv_to_hex_test : process
constant slvVar : slv(11 downto 0) := "101011110000";

begin

assert (conv_to_hex(slvVar) = "AF0") -- 0
report "mult_s error # 1 " & LF &
"AF0 : expected" & LF &
conv_to_hex(slvVar) & " : actual"
severity error;


wait;

end process;


--assert FALSE
--report "THIS IS THE END OF SIMULATION" & LF
--severity failure;

------------------------------------------------------------------------------
end behavioral;
-----------------------------------------------------------------------------




-- synopsys translate_on
 
M

My Name

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : natural := 30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := CFT_BASE_SIZE*4;


------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference

function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cdfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural; -- This function returns a natural representing the number of characters required to reprsent an integer value. It is essentially an integer'length function for the characters.

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference


function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector; -- create a 50% duty cycle count time using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference

function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cufth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfi_syn(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function itoa(intVal : integer) return string;

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

-- synopsys translate_off
impure function now return string; -- returns a string representation of the current simulation time
-- synopsys translate_on

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed
function reduce_length(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

-- synopsys translate_off
function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency
-- synopsys translate_on

function to_string(intVal : integer) return string; -- returns the string representation of an integer value passed
function to_string(realVal : real) return string; -- returns the string representation of a real value passed
function to_string(timeVal : time) return string; -- returns the string representation of a time value passed
function to_string(vectorVal : std_logic_vector) return string; -- returns the string representation of a std_logic_vector value passed

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
-- synthesis translate_off
--alias cft is count_for_time[string,string return std_logic_vector]; -- synplify doesn't like "[" or "]"
--alias cfth is count_for_time_high[string,string return integer];
-- synthesis translate_on
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce((timeVar/freqStrVar) - 2);
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cdfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length((timeVar/freqStrVar) - 2);
if (lengthVar >= natVal) then
return reduce((timeVar/freqStrVar) - 2);
else
return zeroVar & reduce((timeVar/freqStrVar) - 2);
end if;
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdfth (count down for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 2
-- for use in counting down to underflow) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cdfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high((timeVar/freqStrVar) - 2);
end cdfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length(timeVar/freqStrVar);
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : clkcnt (50% duty cycle clock count)
--
-- DESCRIPTION : This function takes a string based frequency value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector is
variable freq1StrVar : std_logic_vector(str_to_slv_var_base_high(freq1StrVal,CFT_BASE_SIZE) downto 0);
variable freq2StrVar : std_logic_vector(str_to_slv_var_base_high(freq2StrVal,CFT_BASE_SIZE) downto 0);
begin
freq1StrVar := str_to_slv(freq1StrVal,CFT_BASE_SIZE);
freq2StrVar := str_to_slv(freq2StrVal,CFT_BASE_SIZE);
return reduce((freq1StrVar/freq2StrVar)/2-2);
end clkcnt;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_unsigned((timeVar/freqStrVar) - 1);
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to:
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cufth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length_unsigned((timeVar/freqStrVar) - 1);
if (lengthVar >= natVal) then
return reduce_unsigned((timeVar/freqStrVar) - 1);
else
return zeroVar & reduce_unsigned((timeVar/freqStrVar) - 1);
end if;
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cufth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 1
-- for use in counting up from zero to the proper value) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cufth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high_unsigned((timeVar/freqStrVar) - 1);
end cufth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function (does not count
-- a '-' character).
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi_syn (decimal places for integer (synthesizeable))
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi_syn(intVal : integer) return natural is
variable resultVar : natural;
begin
if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
resultVar := 10;
elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
resultVar := 9;
elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
resultVar := 8;
elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
resultVar := 7;
elsif (intVal <= -100_000 or intVal >= 100_000) then
resultVar := 6;
elsif (intVal <= -10_000 or intVal >= 10_000) then
resultVar := 5;
elsif (intVal <= -1_000 or intVal >= 1_000) then
resultVar := 4;
elsif (intVal <= -100 or intVal >= 100) then
resultVar := 3;
elsif (intVal <= -10 or intVal >= 10) then
resultVar := 2;
else
resultVar := 1;
end if;
return resultVar;
end dpfi_syn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : itoa
--
-- DESCRIPTION : commonly used integer-to-string type converter
--
-- NOTES
--
------------------------------------------------------------------------------
--function itoa(intVal : integer) return string is
-- variable IntVar : integer := intVal;
--begin
-- if (IntVar < 0) then
-- return "-" & itoa(-IntVar);
-- elsif IntVar < 10 then
-- return IntString(IntVar);
-- else
-- return itoa(IntVar/10) & IntString(IntVar rem 10);
-- end if;
--end function itoa;


function itoa(intVal : integer) return string is
begin
return to_string(intVal);
end function itoa;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : now
--
-- DESCRIPTION : This function returns a string representation
-- of the current simulation time
--
-- NOTES :
--
------------------------------------------------------------------------------
-- synopsys translate_off
impure function now return string is
variable lineVar : line;
variable resultVar : string(1 to time'image(now)'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, time'image(now));
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end now;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- And add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_unsigned
--
-- DESCRIPTION : This function returns a vector with all sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length(vectorVal : std_logic_vector) return integer is
begin
return reduce_high(vectorVal) + 1;
end reduce_length;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer is
begin
return reduce_high_unsigned(vectorVal) + 1;
end reduce_length_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := intVal;
decPntFndVar := false;
decPlacesVar := 0;
expFndVar := false;
expVar := 0;
freqUnitFndVar := false;
negVar := false;
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false;
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar;
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),baseVar),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
------ synopsys translate_off
--function to_string(intVal : integer) return string is
-- variable lineVar : line;
-- variable resultVar : string(1 to cfi(intVal));
--begin
-- --Std.TextIO.Write(lineVar, intVal);
-- Write(lineVar, integer'Image(intVal));
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
------ synopsys translate_on


function to_string(intVal : integer) return string is
begin
return integer'Image(intVal);
end to_string;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
---- synopsys translate_off
--function to_string(realVal : real) return string is
-- variable lengthVar : natural;
-- variable lineVar : line;
-- variable resultVar : string(1 to real'Image(realVal)'length);
--begin
-- --Std.TextIO.Write(lineVar, intVal);
-- Write(lineVar, real'Image(realVal));
-- lengthVar := lineVar.all'length;
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
---- synopsys translate_on


function to_string(realVal : real) return string is
begin
return real'Image(realVal);
end to_string;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (time)
--
-- DESCRIPTION : This function returns a string value representing the
-- time value passed to it.
--
-- NOTES :
--
------------------------------------------------------------------------------
---- synopsys translate_off
--function to_string(timeVal : time) return string is
-- variable lineVar : line;
-- variable resultVar : string(1 to time'image(timeVal)'length);
--begin
-- --Std.TextIO.Write(lineVar, vectorVal);
-- Write(lineVar, time'image(timeVal));
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
---- synopsys translate_on

function to_string(timeVal : time) return string is
begin
return time'image(timeVal);
end to_string;



------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
-- 'U', -- Uninitialized
-- 'X', -- Forcing Unknown
-- '0', -- Forcing 0
-- '1', -- Forcing 1
-- 'Z', -- High Impedance
-- 'W', -- Weak Unknown
-- 'L', -- Weak 0
-- 'H', -- Weak 1
-- '-' -- Don't care
------------------------------------------------------------------------------
-- synthesis tool un-friendly version
---- synopsys translate_off
--function to_string(vectorVal : std_logic_vector) return string is
-- variable lineVar : line;
-- variable resultVar : string(1 to vectorVal'length);
--begin
-- --Std.TextIO.Write(lineVar, vectorVal);
-- Write(lineVar, vectorVal);
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
---- synopsys translate_on

-- synthesis tool friendly version
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
variable vectorVar : std_logic_vector(1 to vectorVal'length);
begin
vectorVar := vectorVal;
for loopVar in vectorVar'range loop
if (vectorVar(loopVar) = 'U') then -- 'U', -- Uninitialized
resultVar(loopVar) := 'U';
elsif (vectorVar(loopVar) = 'X') then -- 'X', -- Forcing Unknown
resultVar(loopVar) := 'X';
elsif (vectorVar(loopVar) = '0') then -- '0', -- Forcing 0
resultVar(loopVar) := '0';
elsif (vectorVar(loopVar) = '1') then -- '1', -- Forcing 1
resultVar(loopVar) := '1';
elsif (vectorVar(loopVar) = 'Z') then -- 'Z', -- High Impedance
resultVar(loopVar) := 'Z';
elsif (vectorVar(loopVar) = 'W') then -- 'W', -- Weak Unknown
resultVar(loopVar) := 'W';
elsif (vectorVar(loopVar) = 'L') then -- 'L', -- Weak 0
resultVar(loopVar) := 'L';
elsif (vectorVar(loopVar) = 'H') then -- 'H', -- Weak 1
resultVar(loopVar) := 'H';
elsif (vectorVar(loopVar) = '-') then -- '-' -- Don't care
resultVar(loopVar) := '-';
end if;
end loop;
return resultVar;
end to_string;


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------
















-- end of extension pack
-- start of test bench























































-- synopsys translate_off



------------------------------------------------------------------------------
-- Extension Pack test bench
------------------------------------------------------------------------------

library ieee, extension_lib;
use ieee.std_logic_1164.all;
use ieee.std_logic_unsigned.all;
use ieee.std_logic_arith.all;
use extension_lib.extension_pack.all;
use ieee.std_logic_textio.all;
use std.textio.all;

entity extension_pack_tb is
end extension_pack_tb;


------------------------------------------------------------------------------
architecture behavioral of extension_pack_tb is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Global Component/Function/Procedure Declarations
------------------------------------------------------------------------------
begin


star_operator_test : process
variable slvVar : slv(2 downto 0) := "111";
begin

assert (7*slvVar = "0110001") -- 7*7 = 49
report "* error # 1 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(7*slvVar) & " : actual"
severity error;

assert (slvVar*7 = "0110001") -- 7*7 = 49
report "* error # 2 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(slvVar*7) & " : actual"
severity error;

wait;
end process;




--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : std_logic_vector) return std_logic_vector;
slash1_operator_test : process
constant slvVar : slv := "0110001";
begin

assert ("0110001"/"111" = "0000111") -- 49/7 = 7
report "slash1_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string("0110001"/"111") & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : integer) return std_logic_vector;
slash2_operator_test : process
constant slvVar : slv := "0110001";
begin

assert (slvVar/7 = "0000111") -- 49/7 = 7
report "slash2_operator_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(slvVar/7) & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : string;
-- DivisorVal : integer) return std_logic_vector;
slash3_operator_test : process
constant var : string := "49";
begin

assert (var/7 = "0000111") -- 49/7 = 7
report "slash3_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(var/7) & " : actual"
severity error;

wait;
end process;



--function bcd_to_led(slvVal : std_logic_vector ;
-- CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion
bcd_to_led1_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_led(slvVar,true) = "0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") -- 123456789ABCDEF =
report "bcd_to_led_test error # 1 " & LF &
to_string("0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") & " : expected" & LF &
to_string(bcd_to_led(slvVar,true)) & " : actual"
severity error;

assert (bcd_to_led(slvVar,false) = "1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") -- 123456789ABCDEF =
report "bcd_to_led_test error # 2 " & LF &
to_string("1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") & " : expected" & LF &
to_string(bcd_to_led(slvVar,false)) & " : actual"
severity error;

wait;
end process;







--function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed
bcd_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_slv(slvVar) = "011100000100100010000110000111101101001110111111") -- 123456789ABCDEF = 123456790123455
report "bcd_to_slv_test error # 1 " & LF &
to_string("011100000100100010000110000111101101001110111111") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("00000001001000110100010101100111100010010000") = "01001001100101100000001011010010") -- 1234567890 =
report "bcd_to_slv_test error # 2 " & LF &
to_string("01001001100101100000001011010010") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("101010111100110111101111") = "100010010010001111111") -- ABCDEF (1123455)
report "bcd_to_slv_test error # 3 " & LF &
to_string("100010010010001111111") & " : expected" & LF &
to_string(bcd_to_slv("101010111100110111101111")) & " : actual"
severity error;


wait;
end process;


--function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value




--function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function
bv_to_slv_test : process
constant bvVar : bv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bv_to_slv(bvVar) = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 1 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(bvVar)) & " : actual"
severity error;

assert (bv_to_slv(X"123456789ABCDEF") = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 2 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(X"123456789ABCDEF")) & " : actual"
severity error;

wait;
end process;


--function cdft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdft("8 ms ","1 kHz") = slvVar)
report "count_down_for_time2_test error # 1 " & LF &
to_string("0111") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz")) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz")) = "0110")
report "count_down_for_time2_test error # 2 " & LF &
to_string("0110") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length = 4)
report "count_down_for_time2_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length) & " : actual"
severity error;

wait;
end process;




--function cdfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high_test : process
begin

assert (cdfth("1 us ","1E-15 yHz") = 10)
report "count_down_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cdfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;

--function cdfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdfth("8 ms ","1 kHz") = 3)
report "count_down_for_time_high_test2 error # 1 " & LF &
to_string(3) & " : expected" & LF &
to_string(cdfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;





--function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer
ceil_test : process
begin

assert (ceil(-9.999999) = -9.0)
report "ceil_test error # 1 " & LF &
to_string(-9.0) & " : expected" & LF &
to_string(ceil(-9.999999)) & " : actual"
severity error;

assert (ceil(9.999999) = 10.0)
report "ceil_test error # 2 " & LF &
to_string(10.0) & " : expected" & LF &
to_string(ceil(9.999999)) & " : actual"
severity error;

wait;
end process;



--function cfi(intVal : integer) return natural;
cfi_test : process
begin

assert (cfi(-1000) = 5)
report "cfi_test error # 1 " & LF &
"5 : expected" & LF &
to_string(cfi(-1000)) & " : actual"
severity error;

assert (cfi(-10000) = 6)
report "cfi_test error # 2 " & LF &
"6 : expected" & LF &
to_string(cfi(-10000)) & " : actual"
severity error;


assert (cfi(1000) = 4)
report "cfi_test error # 3 " & LF &
"4 : expected" & LF &
to_string(cfi(1000)) & " : actual"
severity error;


assert (cfi(-100_000) = 7)
report "cfi_test error # 4 " & LF &
"7 : expected" & LF &
to_string(cfi(-100_000)) & " : actual"
severity error;


assert (cfi(100_000) = 6)
report "cfi_test error # 5 " & LF &
"6 : expected" & LF &
to_string(cfi(100_000)) & " : actual"
severity error;

assert (cfi(-9999999) = 8)
report "cfi_test error # 6 " & LF &
to_string(8) & " : expected" & LF &
to_string(cfi(-9999999)) & " : actual"
severity error;

assert (cfi(9999999) = 7)
report "cfi_test error # 7 " & LF &
to_string(7) & " : expected" & LF &
to_string(cfi(9999999)) & " : actual"
severity error;

wait;
end process;


--function cft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cft(CNTTIME,SYSCLKFREQ) = "100111010101101100110100000000")
report "count_for_time_test error # 1 " & LF &
to_string("100111010101101100110100000000") & " : expected" & LF &
to_string(cft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cft("1 min","66MHz") = "11101100000010001100111000000000")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100111000000000") & " : expected" & LF &
to_string(cft("1 min","66MHz")) & " : actual"
severity error;


assert (cft("1 hr","66MHz") = "11011101010010000100000100100000000000")
report "count_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100100000000000") & " : expected" & LF &
to_string(cft("1 hr","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz") = "01010010111110110001100001101100000000000000")
report "count_for_time_test error # 4 " & LF &
to_string("01010010111110110001100001101100000000000000") & " : expected" & LF &
to_string(cft("1 day","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 5 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz")) & " : actual"
severity error;


assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 6 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")+cft("1 as","66MHz")+cft("1 zs","66MHz")+cft("1 ys","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 7 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "011100011100110011110110101000101011010000000101001")
report "count_for_time_test error # 8 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-3 kHz") = "01")
report "count_for_time_test error # 9 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-18 eHz") = "01")
report "count_for_time_test error # 10 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cft("1 ns ","1E-15 yHz") = "01")
report "count_for_time_test error # 11 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cft("1 us ","1E-15 yHz") = "01111101000")
report "count_for_time_test error # 12 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(cft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cft("20 ms ","50 MHz"),21);

assert (ext(cft("20 ms ","50 MHz"),21) = "011110100001001000000")
report "count_for_time_test error # 13 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(ext(cft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test : process
begin

assert (cfth("1 us ","1E-15 yHz") = 10)
report "count_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cfth("8 ms ","1 kHz") = 4)
report "count_for_time_high_test2 error # 1 " & LF &
to_string(4) & " : expected" & LF &
to_string(cfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;



--function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
conv_to_hex_test1 : process
variable testVar : bv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test1 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
conv_to_hex_test2 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test2 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion
conv_to_hex_test3 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test3 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function cslv(int1Val : integer;
-- int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(sigVal : signed;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(usgVal : unsigned;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested


--function cuft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cuft(CNTTIME,SYSCLKFREQ) = "100111010101101100110011111111")
report "count_up_for_time_test error # 1 " & LF &
to_string("100111010101101100110011111111") & " : expected" & LF &
to_string(cuft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cuft("1 min","66MHz") = "11101100000010001100110111111111")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100110111111111") & " : expected" & LF &
to_string(cuft("1 min","66MHz")) & " : actual"
severity error;


assert (cuft("1 hr","66MHz") = "11011101010010000100000100011111111111")
report "count_up_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100011111111111") & " : expected" & LF &
to_string(cuft("1 hr","66MHz")) & " : actual"
severity error;


assert (cuft("1 day","66MHz") = "1010010111110110001100001101011111111111111")
report "count_up_for_time_test error # 4 " & LF &
to_string("1010010111110110001100001101011111111111111") & " : expected" & LF &
to_string(cuft("1 day","66MHz")) & " : actual"
severity error;




assert (cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "1010110011111110011100011111110110010010001")
report "count_up_for_time_test error # 6 " & LF &
to_string("1010110011111110011100011111110110010010001") & " : expected" & LF &
to_string(cuft("1 day","66MHz")+cuft("1 hr","66MHz")+cuft("1 min","66MHz")+cuft("1 sec","66MHz")+cuft("1 ms","66MHz")+cuft("1 us","66MHz")+cuft("1 ns","66MHz")+cuft("1 ps","66MHz")+cuft("1 fs","66MHz")+cuft("1 as","66MHz")+cuft("1 zs","66MHz")+cuft("1 ys","66MHz")) & " : actual" & LF &
to_string(cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;



assert (cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "11100011100110011110110101000101011010000000101000")
report "count_up_for_time_test error # 8 " & LF &
to_string("11100011100110011110110101000101011010000000101000") & " : expected" & LF &
to_string(cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-3 kHz") = "0")
report "count_up_for_time_test error # 9 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-18 eHz") = "0")
report "count_up_for_time_test error # 10 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cuft("1 ns ","1E-15 yHz") = "0")
report "count_up_for_time_test error # 11 " & LF &
to_string("0") & " : expected" & LF &
to_string(cuft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cuft("1 us ","1E-15 yHz") = "1111100111")
report "count_up_for_time_test error # 12 " & LF &
to_string("1111100111") & " : expected" & LF &
to_string(cuft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cuft("20 ms ","50 MHz"),21);

assert (ext(cuft("20 ms ","50 MHz"),25) = "0000011110100001000111111")
report "count_up_for_time_test error # 13 " & LF &
to_string("0000011110100001000111111") & " : expected" & LF &
to_string(ext(cuft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test : process
begin

assert (cufth("1 us ","1E-15 yHz") = 9)
report "count_up_for_time_high_test error # 1 " & LF &
to_string(9) & " : expected" & LF &
to_string(cufth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cufth("8 ms ","1 kHz") = 2)
report "count_up_for_time_high_test2 error # 1 " & LF &
to_string(2) & " : expected" & LF &
to_string(cufth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;

--function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value


--function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value



--function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed


--function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

--function ext(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector;
ext_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);

assert (ext2(slvVar,7) = "0000111") -- 7 bits
report "ext_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,7)) & " : actual"
severity error;

assert (ext2(slvVar,4) = "0111") -- 4 bits
report "ext_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,4)) & " : actual"
severity error;

assert (ext2(slvVar,4)'length = 4) -- 4 bits
report "ext_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(ext2(slvVar,4)'length) & " : actual"
severity error;

wait;
end process;



--function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order


--function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order



--function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order


--function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector



--function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed



--function mult_s(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply



--function mult_us(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply



--function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed



--function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value


--function now return string; -- returns a string representation of the current simulation time
now_test : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

wait for 3 sec;

assert (now = time'image(now))
report "now_test error # 1 " & LF &
time'image(now) & " : expected" & LF &
now & " : actual"
severity error;

wait;
end process;


--function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function reduce_high(vectorVal : std_logic_vector) return integer; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function seq(str1Val : string;
-- str2Val : string) return boolean;



--function shl(vectorVal : std_logic_vector;
-- natVal : natural) return std_logic_vector;



--function slv_to_bcd(vectorVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified



--function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed



--function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
-- MSB_Val : std_logic;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value



--function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer



--function str_to_led(stringVal : string;
-- CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs



--function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
str_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (str_to_slv("1") = "01") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("0") = "0") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("00") & " : expected" & LF &
to_string(str_to_slv("0")) & " : actual"
severity error;

assert (str_to_slv("-1") = "11") -- -1
report "bcd_to_led_test error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(str_to_slv("-1")) & " : actual"
severity error;

assert (str_to_slv("10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 1 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv("10 us"))
severity error;

assert (str_to_slv(" 10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 2 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us"))
severity error;

assert (str_to_slv(" 10 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 3 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us "))
severity error;

assert (str_to_slv(" 10.0 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 4 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0 us "))
severity error;

assert (str_to_slv(" 0.0100 ms ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 5 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0100 ms "))
severity error;

assert (str_to_slv(" 0.0000100sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0000100sec "))
severity error;

assert (str_to_slv(" 10E-6 sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E-6 sec "))
severity error;


assert (str_to_slv(" 10,000,000,000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 7 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10,000,000,000 "))
severity error;

assert (str_to_slv(" 100,000Hz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 8 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100,000Hz "))
severity error;


assert (str_to_slv(" 100kHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100kHz "))
severity error;

assert (str_to_slv(" 0.1MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.1MHz "))
severity error;

assert (str_to_slv(" .1 MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" .1 MHz "))
severity error;

assert (str_to_slv(" 0.0001GHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 10 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0001GHz "))
severity error;


assert (str_to_slv(" 10E 9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 11 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E 9 "))
severity error;


assert (str_to_slv(" 10E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 12 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9.000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9.000 "))
severity error;

assert (str_to_slv(" 100E+3 HZ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 14 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;


assert (str_to_slv(" 1") = "01")
report "str_to_slv_test error # 15a " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(str_to_slv(" 1"))
severity error;

assert (str_to_slv(" -1") = "11")
report "str_to_slv_test error # 15b " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(str_to_slv(" -1"))
severity error;


assert (str_to_slv("1") = "01")
report "str_to_slv_test error # 16 " & LF &
to_string("01") & " : expected"
& LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("10") = "01010")
report "str_to_slv_test error # 17 " & LF &
to_string("01010") & " : expected"
& LF &
to_string(str_to_slv("10")) & " : actual"
severity error;

assert (str_to_slv(" 100E+3 HZ ps ns MHz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 18 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100E+3 HZ Hz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 19 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100,000 HZ 234sec") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 20 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ 234sec"))
severity error;

assert (str_to_slv("1 day") = "01001010111100001010011101100011101110110001110000000000000000000000") -- 0
report "bcd_to_led_test error # 21 " & LF &
to_string("01001010111100001010011101100011101110110001110000000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 day")) & " : actual"
severity error;

assert (str_to_slv("1 hr") = "011000111110101110001001110110100100111011010000000000000000000") -- 0
report "bcd_to_led_test error # 22 " & LF &
to_string("011000111110101110001001110110100100111011010000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 hr")) & " : actual"
severity error;

assert (str_to_slv("1 min") = "011010101001010011010111010011110100001100000000000000000") -- 0
report "bcd_to_led_test error # 23 " & LF &
to_string("011010101001010011010111010011110100001100000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 min")) & " : actual"
severity error;

assert (str_to_slv("1 sec") = "011100011010111111010100100110001101000000000000000") -- 0
report "bcd_to_led_test error # 24 " & LF &
to_string("011100011010111111010100100110001101000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 sec")) & " : actual"
severity error;

assert (str_to_slv("1 ms") = "01110100011010100101001010001000000000000") -- 0
report "bcd_to_led_test error # 25 " & LF &
to_string("01110100011010100101001010001000000000000") & " : expected" & LF &
to_string(str_to_slv("1 ms")) & " : actual"
severity error;

assert (str_to_slv("1 us") = "0111011100110101100101000000000") -- 0
report "bcd_to_led_test error # 26 " & LF &
to_string("0111011100110101100101000000000") & " : expected" & LF &
to_string(str_to_slv("1 us")) & " : actual"
severity error;

assert (str_to_slv("1 ns") = "011110100001001000000") -- 0
report "bcd_to_led_test error # 27 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 ns")) & " : actual"
severity error;

assert (str_to_slv("1 ps") = "01111101000") -- 0
report "bcd_to_led_test error # 28 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 ps")) & " : actual"
severity error;

assert (str_to_slv("1 fs") = "01") -- 0
report "bcd_to_led_test error # 29 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 fs")) & " : actual"
severity error;

assert (str_to_slv("1 as",24) = "011110100001001000000") -- 0
report "bcd_to_led_test error # 30 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 as",24)) & " : actual"
severity error;

assert (str_to_slv("1 zs",24) = "01111101000") -- 0
report "bcd_to_led_test error # 31 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 zs",24)) & " : actual"
severity error;

assert (str_to_slv("1 ys",24) = "01") -- 0
report "bcd_to_led_test error # 32 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 ys",24)) & " : actual"
severity error;


assert (str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs") = "01001110000111011000111100110011111100101100110000111010000000101001") -- 0
report "bcd_to_led_test error # 33 " & LF &
to_string("01001110000111011000111100110011111100101100110000111010000000101001") & " : expected" & LF &
to_string(str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs")) & " : actual"
severity error;


wait;
end process;


--function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed



--function str_to_slv_var_base(stringVal : string;
-- intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed



--function str_to_slv_var_base_high(stringVal : string;
-- intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value



--function strh(stringVal : string) return integer;

sxt_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := sxt2(int_to_slv(-1000),slv1Var'length);
slv2Var := sxt2(int_to_slv(-6),slv2Var'length);

assert (sxt2(slvVar,7) = "0000111") -- 7 bits
report "sxt2_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,7)) & " : actual"
severity error;

assert (sxt2(slvVar,4) = "0111") -- 4 bits
report "sxt2_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,4)) & " : actual"
severity error;

assert (sxt2("1001",7) = "1111001") -- 7 bits
report "sxt2_test error # 3 " & LF &
to_string("1111001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;

assert (sxt2("00",7) = "0000000") -- 4 bits
report "sxt2_test error # 4 " & LF &
to_string("0000000") & " : expected" & LF &
to_string(sxt2("00",7)) & " : actual"
severity error;

assert (sxt2("1001",4) = "1001") -- 7 bits
report "sxt2_test error # 5 " & LF &
to_string("1001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;


wait;
end process;

---- synopsys translate_off
--function time_to_slv(timeVal : time;
-- clkFreqVal : frequency) return std_logic_vector;
---- synopsys translate_on
--
--function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function
--
--function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency
--
---- synopsys translate_off
--function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
to_string_test1 : process
begin

assert (to_string(2147000000) = "2147000000")
report "to_string_test1 error # 1 " & LF &
"2147000000" & " : expected" & LF &
to_string(2147000000) & " : actual"
severity error;

assert (to_string(-2147000000) = "-2147000000")
report "to_string_test1 error # 2 " & LF &
"-2147000000" & " : expected" & LF &
to_string(-2147000000) & " : actual"
severity error;



wait;
end process;


--function to_string(realVal : real) return string; -- returns a string value for an real value passed
to_string_test2 : process
begin

assert (to_string(1.000000e+308) = "1.000000e+308")
report "to_string_test2 error # 1 " & LF &
"1.000000e+308" & " : expected" & LF &
to_string(1.000000e+308) & " : actual"
severity error;

assert (to_string(1.000000e-308) = "1.000000e-308")
report "to_string_test2 error # 2 " & LF &
"1.000000e-308" & " : expected" & LF &
to_string(1.000000e-308) & " : actual"
severity error;

assert (to_string(-1.000000e-308) = "-1.000000e-308")
report "to_string_test2 error # 2 " & LF &
"-1.000000e-308" & " : expected" & LF &
to_string(-1.000000e-308) & " : actual"
severity error;

wait;
end process;


--function to_string(timeVal : time) return string;
to_string_test3 : process
begin

assert (to_string(3 ns) = "3 ns")
report "to_string_test3 error # 1 " & LF &
"3 ns" & " : expected" & LF &
to_string(3 ns) & " : actual"
severity error;


assert (to_string(2040 ns) = "2040 ns")
report "to_string_test3 error # 1 " & LF &
"2040 ns" & " : expected" & LF &
to_string(2040 ns) & " : actual"
severity error;

wait;
end process;


--function to_string(vectorVal : std_logic_vector) return string;
---- synopsys translate_on
--
--function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--
--function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
--function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed
--
--function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed
--
--function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed
--
--------------------------------------------------------------------------------
---- Procedure Declarations
--------------------------------------------------------------------------------
---- synopsys translate_off
--procedure clkgen(
-- constant clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkPeriodSig : in time;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
---- synopsys translate_on
--
--procedure FF(
-- signal Clk : in std_logic;
-- signal Rst : in std_logic;
-- signal D : in std_logic_vector;
-- signal Q : out std_logic_vector);
--
--procedure slv_to_bcd(
-- signal BCD_RIn : in std_logic_vector;
-- signal BinIn : in std_logic_vector;
-- signal BinFBIn : in std_logic_vector;
-- signal ClkIn : in std_logic;
-- constant BCD_DigitsVal : in integer;
-- signal EnIn : in std_logic;
-- signal RstLowIn : in std_logic;
-- signal BCD_ROut : out std_logic_vector;
-- signal Bin_ROut : out std_logic_vector;
-- signal DoneOut : out std_logic);


divider_test : process
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);
begin
slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);
slv3Var := slv1Var/slv2Var;
-- assert FALSE
-- report "divider output :" & LF & to_string(to_int(slv1Var)) & " / " & to_string(to_int(slv2Var)) & " = " & to_string(to_int(slv3Var))
-- severity note;
wait;
end process;


bcd_to_led_test : process
variable slvVar : slv(27 downto 0);
begin
slvVar := bcd_to_led("0011001000010000",False); -- 3210
assert (slvVar = "1111001110110101100001111110")
report "bcd_to_led_test error # 1 "
severity error;
slvVar := bcd_to_led("0111011001010100",False); -- 7654
assert (slvVar = "1110010101111110110110110011")
report "bcd_to_led_test error # 2 "
severity error;
slvVar := bcd_to_led("0001000010011000",False); -- 1098
assert (slvVar = "0110000111111011100111111111")
report "bcd_to_led_test error # 3 "
severity error;
slvVar := bcd_to_led("0011001000010000",True); -- 3210
assert (slvVar = "0000110001001010011110000001")
report "bcd_to_led_test error # 4 "
severity error;
slvVar := bcd_to_led("0111011001010100",True); -- 7654
assert (slvVar = "0001101010000001001001001100")
report "bcd_to_led_test error # 5 "
severity error;
slvVar := bcd_to_led("0001000010011000",True); -- 1098
assert (slvVar = "1001111000000100011000000000")
report "bcd_to_led_test error # 6 "
severity error;
wait;
end process;


str_to_int_test : process
variable intVar : integer;
begin
intVar := str_to_int("10"); -- 3210
assert (intVar = 10)
report "str_to_int_test error # 1 " & LF &
"expected : 10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-10 sec"); -- 3210
assert (intVar = -10)
report "str_to_int_test error # 2 " & LF &
"expected : -10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-6 sec"); -- 3210
assert (intVar = -6)
report "str_to_int_test error # 3 " & LF &
"expected : -6" & LF &
"actual : " & to_string(intVar)
severity error;

wait;
end process;




reduce_test : process

begin

assert (reduce("00000") = "00") -- 0
report "reduce error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(reduce("00000")) & " : actual"
severity error;

assert (reduce("00001") = "01") -- 1
report "reduce error # 2 " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(reduce("00001"))
severity error;

assert (reduce("11111") = "11") -- -1
report "reduce error # 3 " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(reduce("11111"))
severity error;

assert (reduce("10000") = "10000") -- -16
report "reduce error # 4 " & LF &
"expected : " & to_string("10000") & LF &
"actual : " & to_string(reduce("10000"))
severity error;

wait;

end process;











--exp_test : process
--variable timeBaseVar : slv(500 downto 0);
--variable lineVar : line;
--begin
-- timeBaseVar := ext("01",timeBaseVar'length);
-- for loopVar in 1 to 50 loop
-- timeBaseVar := timeBaseVar(timeBaseVar'high-4 downto 0) * "1010";
--
---- write(lineVar,to_string(real(reduce_high(timeBaseVar))/real(loopVar)));
---- write(lineVar,LF);
-- assert FALSE
-- report
-- to_string(real(reduce_high(timeBaseVar))/real(loopVar)) & LF
-- severity note;
-- end loop;
--
-- wait;
--end process;



unsigned_mult_test : process

begin

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

assert (mult_us("000","011") = "000000") -- 0
report "mult error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","011")) & " : actual"
severity error;

assert (mult_us("011","000") = "000000") -- 0
report "mult error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("011","000")) & " : actual"
severity error;

assert (mult_us("000","101") = "000000") -- 0
report "mult error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","101")) & " : actual"
severity error;

assert (mult_us("101","000") = "000000") -- 0
report "mult error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("101","000")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 7 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

wait;

end process;








signed_mult_test : process

begin

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("000","011") = "000000") -- 0
report "mult_s error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","011")) & " : actual"
severity error;

assert (mult_s("011","000") = "000000") -- 0
report "mult_s error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("011","000")) & " : actual"
severity error;

assert (mult_s("000","101") = "000000") -- 0
report "mult_s error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","101")) & " : actual"
severity error;

assert (mult_s("101","000") = "000000") -- 0
report "mult_s error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("101","000")) & " : actual"
severity error;

assert (mult_s("011","101") = "110111") -- 3 * (-3) = -9
report "mult_s error # 7 " & LF &
to_string("110111") & " : expected" & LF &
to_string(mult_s("011","101")) & " : actual"
severity error;

assert (mult_s("011","100") = "110100") -- 3 * (-4) = -12
report "mult_s error # 8 " & LF &
to_string("110100") & " : expected" & LF &
to_string(mult_s("011","100")) & " : actual"
severity error;

assert (mult_s("101","101") = "001001") -- (-3) * (-3) = 9
report "mult_s error # 9 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("101","101")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 10 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 11 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;


assert (mult_s("100","100") = "010000") -- -4 * -4 = 16
report "mult_s error # 11 " & LF &
to_string("010000") & " : expected" & LF &
to_string(mult_s("100","100")) & " : actual"
severity error;



wait;

end process;








conv_to_hex_test : process
constant slvVar : slv(11 downto 0) := "101011110000";

begin

assert (conv_to_hex(slvVar) = "AF0") -- 0
report "mult_s error # 1 " & LF &
"AF0 : expected" & LF &
conv_to_hex(slvVar) & " : actual"
severity error;


wait;

end process;


--assert FALSE
--report "THIS IS THE END OF SIMULATION" & LF
--severity failure;

------------------------------------------------------------------------------
end behavioral;
-----------------------------------------------------------------------------

-- end of extension_pack testbench


-- synopsys translate_on
 
M

My Name

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (-60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : integer := -30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := (-CFT_BASE_SIZE)*4;


------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference

function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cdfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural; -- This function returns a natural representing the number of characters required to reprsent an integer value. It is essentially an integer'length function for the characters.

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference


function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector; -- create a 50% duty cycle count time using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference

function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cufth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfi_syn(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function itoa(intVal : integer) return string;

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

-- synopsys translate_off
impure function now return string; -- returns a string representation of the current simulation time
-- synopsys translate_on

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed
function reduce_length(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

-- synopsys translate_off
function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency
-- synopsys translate_on

function to_string(intVal : integer) return string; -- returns the string representation of an integer value passed
function to_string(realVal : real) return string; -- returns the string representation of a real value passed
function to_string(timeVal : time) return string; -- returns the string representation of a time value passed
function to_string(vectorVal : std_logic_vector) return string; -- returns the string representation of a std_logic_vector value passed

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce((timeVar/freqStrVar) - 2);
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cdfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length((timeVar/freqStrVar) - 2);
if (lengthVar >= natVal) then
return reduce((timeVar/freqStrVar) - 2);
else
return zeroVar & reduce((timeVar/freqStrVar) - 2);
end if;
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdfth (count down for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 2
-- for use in counting down to underflow) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cdfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high((timeVar/freqStrVar) - 2);
end cdfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length(timeVar/freqStrVar);
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : clkcnt (50% duty cycle clock count)
--
-- DESCRIPTION : This function takes a string based frequency value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
-- this function is for use with a process which counts
-- up to a static value. This method gives the smallest and
-- fastest circuit
--
--CounterProcess2:process(ClkRSig,Count2RSig)
-- variable CLKCNTVAL : slv := clkcnt("Freq1Val","Freq2Val")
--begin
-- if (Count2RSig = CLKCNTVAL) then
-- Count2Sig <= (others => '0');
-- ClkSig <= not ClkRSig;
-- else
-- Count2Sig <= Count2RSig + 1;
-- ClkSig <= ClkRSig;
-- end if;
--end process;
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector is
variable freq1StrVar : std_logic_vector(str_to_slv_var_base_high(freq1StrVal,CFT_BASE_SIZE) downto 0);
variable freq2StrVar : std_logic_vector(str_to_slv_var_base_high(freq2StrVal,CFT_BASE_SIZE) downto 0);
begin
freq1StrVar := str_to_slv(freq1StrVal,CFT_BASE_SIZE);
freq2StrVar := str_to_slv(freq2StrVal,CFT_BASE_SIZE);
return reduce_unsigned((freq1StrVar/freq2StrVar)/2-1);
end clkcnt;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_unsigned((timeVar/freqStrVar) - 1);
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to:
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cufth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length_unsigned((timeVar/freqStrVar) - 1);
if (lengthVar >= natVal) then
return reduce_unsigned((timeVar/freqStrVar) - 1);
else
return zeroVar & reduce_unsigned((timeVar/freqStrVar) - 1);
end if;
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cufth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 1
-- for use in counting up from zero to the proper value) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cufth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high_unsigned((timeVar/freqStrVar) - 1);
end cufth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function (does not count
-- a '-' character).
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi_syn (decimal places for integer (synthesizeable))
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi_syn(intVal : integer) return natural is
variable resultVar : natural;
begin
if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
resultVar := 10;
elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
resultVar := 9;
elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
resultVar := 8;
elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
resultVar := 7;
elsif (intVal <= -100_000 or intVal >= 100_000) then
resultVar := 6;
elsif (intVal <= -10_000 or intVal >= 10_000) then
resultVar := 5;
elsif (intVal <= -1_000 or intVal >= 1_000) then
resultVar := 4;
elsif (intVal <= -100 or intVal >= 100) then
resultVar := 3;
elsif (intVal <= -10 or intVal >= 10) then
resultVar := 2;
else
resultVar := 1;
end if;
return resultVar;
end dpfi_syn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : itoa
--
-- DESCRIPTION : commonly used integer-to-string type converter
--
-- NOTES
--
------------------------------------------------------------------------------
--function itoa(intVal : integer) return string is
-- variable IntVar : integer := intVal;
--begin
-- if (IntVar < 0) then
-- return "-" & itoa(-IntVar);
-- elsif IntVar < 10 then
-- return IntString(IntVar);
-- else
-- return itoa(IntVar/10) & IntString(IntVar rem 10);
-- end if;
--end function itoa;


function itoa(intVal : integer) return string is
begin
return to_string(intVal);
end function itoa;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : now
--
-- DESCRIPTION : This function returns a string representation
-- of the current simulation time
--
-- NOTES :
--
------------------------------------------------------------------------------
-- synopsys translate_off
impure function now return string is
variable lineVar : line;
variable resultVar : string(1 to time'image(now)'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, time'image(now));
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end now;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- And add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_unsigned
--
-- DESCRIPTION : This function returns a vector with all sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length(vectorVal : std_logic_vector) return integer is
begin
return reduce_high(vectorVal) + 1;
end reduce_length;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer is
begin
return reduce_high_unsigned(vectorVal) + 1;
end reduce_length_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,-15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := -intVal;
decPntFndVar := false; -- initialize to decimal point not found yet
decPlacesVar := 0;
expFndVar := false; -- initialize to exponent point not found yet
expVar := 0;
freqUnitFndVar := false; -- initialize to frequency units not found yet
negVar := false; -- initialize to negative sign not found yet
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false; -- initialize to secont time value not found yet
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\); -- this value will contain the time base (in binary) when this loop completes (10^30 for a baseVar of 30)
end loop;
for loopVar in stringVar'range loop -- this loop parses the string value passed to this function from left to right
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar; -- if a second value has been found then just wait here for the loop to complete
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
------ synopsys translate_off
--function to_string(intVal : integer) return string is
-- variable lineVar : line;
-- variable resultVar : string(1 to cfi(intVal));
--begin
-- --Std.TextIO.Write(lineVar, intVal);
-- Write(lineVar, integer'Image(intVal));
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
------ synopsys translate_on


function to_string(intVal : integer) return string is
begin
return integer'Image(intVal);
end to_string;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
---- synopsys translate_off
--function to_string(realVal : real) return string is
-- variable lengthVar : natural;
-- variable lineVar : line;
-- variable resultVar : string(1 to real'Image(realVal)'length);
--begin
-- --Std.TextIO.Write(lineVar, intVal);
-- Write(lineVar, real'Image(realVal));
-- lengthVar := lineVar.all'length;
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
---- synopsys translate_on


function to_string(realVal : real) return string is
begin
return real'Image(realVal);
end to_string;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (time)
--
-- DESCRIPTION : This function returns a string value representing the
-- time value passed to it.
--
-- NOTES :
--
------------------------------------------------------------------------------
---- synopsys translate_off
--function to_string(timeVal : time) return string is
-- variable lineVar : line;
-- variable resultVar : string(1 to time'image(timeVal)'length);
--begin
-- --Std.TextIO.Write(lineVar, vectorVal);
-- Write(lineVar, time'image(timeVal));
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
---- synopsys translate_on

function to_string(timeVal : time) return string is
begin
return time'image(timeVal);
end to_string;



------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
-- 'U', -- Uninitialized
-- 'X', -- Forcing Unknown
-- '0', -- Forcing 0
-- '1', -- Forcing 1
-- 'Z', -- High Impedance
-- 'W', -- Weak Unknown
-- 'L', -- Weak 0
-- 'H', -- Weak 1
-- '-' -- Don't care
------------------------------------------------------------------------------
-- synthesis tool un-friendly version
---- synopsys translate_off
--function to_string(vectorVal : std_logic_vector) return string is
-- variable lineVar : line;
-- variable resultVar : string(1 to vectorVal'length);
--begin
-- --Std.TextIO.Write(lineVar, vectorVal);
-- Write(lineVar, vectorVal);
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
---- synopsys translate_on

-- synthesis tool friendly version
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
variable vectorVar : std_logic_vector(1 to vectorVal'length);
begin
vectorVar := vectorVal;
for loopVar in vectorVar'range loop
if (vectorVar(loopVar) = 'U') then -- 'U', -- Uninitialized
resultVar(loopVar) := 'U';
elsif (vectorVar(loopVar) = 'X') then -- 'X', -- Forcing Unknown
resultVar(loopVar) := 'X';
elsif (vectorVar(loopVar) = '0') then -- '0', -- Forcing 0
resultVar(loopVar) := '0';
elsif (vectorVar(loopVar) = '1') then -- '1', -- Forcing 1
resultVar(loopVar) := '1';
elsif (vectorVar(loopVar) = 'Z') then -- 'Z', -- High Impedance
resultVar(loopVar) := 'Z';
elsif (vectorVar(loopVar) = 'W') then -- 'W', -- Weak Unknown
resultVar(loopVar) := 'W';
elsif (vectorVar(loopVar) = 'L') then -- 'L', -- Weak 0
resultVar(loopVar) := 'L';
elsif (vectorVar(loopVar) = 'H') then -- 'H', -- Weak 1
resultVar(loopVar) := 'H';
elsif (vectorVar(loopVar) = '-') then -- '-' -- Don't care
resultVar(loopVar) := '-';
end if;
end loop;
return resultVar;
end to_string;


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------
















-- end of extension pack
-- start of test bench























































-- synopsys translate_off



------------------------------------------------------------------------------
-- Extension Pack test bench
------------------------------------------------------------------------------

library ieee, extension_lib;
use ieee.std_logic_1164.all;
use ieee.std_logic_unsigned.all;
use ieee.std_logic_arith.all;
use extension_lib.extension_pack.all;
use ieee.std_logic_textio.all;
use std.textio.all;

entity extension_pack_tb is
end extension_pack_tb;


------------------------------------------------------------------------------
architecture behavioral of extension_pack_tb is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Global Component/Function/Procedure Declarations
------------------------------------------------------------------------------
begin


star_operator_test : process
variable slvVar : slv(2 downto 0) := "111";
begin

assert (7*slvVar = "0110001") -- 7*7 = 49
report "* error # 1 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(7*slvVar) & " : actual"
severity error;

assert (slvVar*7 = "0110001") -- 7*7 = 49
report "* error # 2 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(slvVar*7) & " : actual"
severity error;

wait;
end process;




--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : std_logic_vector) return std_logic_vector;
slash1_operator_test : process
constant slvVar : slv := "0110001";
begin

assert ("0110001"/"111" = "0000111") -- 49/7 = 7
report "slash1_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string("0110001"/"111") & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : integer) return std_logic_vector;
slash2_operator_test : process
constant slvVar : slv := "0110001";
begin

assert (slvVar/7 = "0000111") -- 49/7 = 7
report "slash2_operator_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(slvVar/7) & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : string;
-- DivisorVal : integer) return std_logic_vector;
slash3_operator_test : process
constant var : string := "49";
begin

assert (var/7 = "0000111") -- 49/7 = 7
report "slash3_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(var/7) & " : actual"
severity error;

wait;
end process;



--function bcd_to_led(slvVal : std_logic_vector ;
-- CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion
bcd_to_led1_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_led(slvVar,true) = "0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") -- 123456789ABCDEF =
report "bcd_to_led_test error # 1 " & LF &
to_string("0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") & " : expected" & LF &
to_string(bcd_to_led(slvVar,true)) & " : actual"
severity error;

assert (bcd_to_led(slvVar,false) = "1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") -- 123456789ABCDEF =
report "bcd_to_led_test error # 2 " & LF &
to_string("1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") & " : expected" & LF &
to_string(bcd_to_led(slvVar,false)) & " : actual"
severity error;

wait;
end process;







--function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed
bcd_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_slv(slvVar) = "011100000100100010000110000111101101001110111111") -- 123456789ABCDEF = 123456790123455
report "bcd_to_slv_test error # 1 " & LF &
to_string("011100000100100010000110000111101101001110111111") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("00000001001000110100010101100111100010010000") = "01001001100101100000001011010010") -- 1234567890 =
report "bcd_to_slv_test error # 2 " & LF &
to_string("01001001100101100000001011010010") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("101010111100110111101111") = "100010010010001111111") -- ABCDEF (1123455)
report "bcd_to_slv_test error # 3 " & LF &
to_string("100010010010001111111") & " : expected" & LF &
to_string(bcd_to_slv("101010111100110111101111")) & " : actual"
severity error;


wait;
end process;


--function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value




--function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function
bv_to_slv_test : process
constant bvVar : bv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bv_to_slv(bvVar) = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 1 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(bvVar)) & " : actual"
severity error;

assert (bv_to_slv(X"123456789ABCDEF") = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 2 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(X"123456789ABCDEF")) & " : actual"
severity error;

wait;
end process;


--function cdft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdft("8 ms ","1 kHz") = slvVar)
report "count_down_for_time2_test error # 1 " & LF &
to_string("0111") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz")) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz")) = "0110")
report "count_down_for_time2_test error # 2 " & LF &
to_string("0110") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length = 4)
report "count_down_for_time2_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length) & " : actual"
severity error;

wait;
end process;




--function cdfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high_test : process
begin

assert (cdfth("1 us ","1E-15 yHz") = 10)
report "count_down_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cdfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;

--function cdfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdfth("8 ms ","1 kHz") = 3)
report "count_down_for_time_high_test2 error # 1 " & LF &
to_string(3) & " : expected" & LF &
to_string(cdfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;





--function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer
ceil_test : process
begin

assert (ceil(-9.999999) = -9.0)
report "ceil_test error # 1 " & LF &
to_string(-9.0) & " : expected" & LF &
to_string(ceil(-9.999999)) & " : actual"
severity error;

assert (ceil(9.999999) = 10.0)
report "ceil_test error # 2 " & LF &
to_string(10.0) & " : expected" & LF &
to_string(ceil(9.999999)) & " : actual"
severity error;

wait;
end process;



--function cfi(intVal : integer) return natural;
cfi_test : process
begin

assert (cfi(-1000) = 5)
report "cfi_test error # 1 " & LF &
"5 : expected" & LF &
to_string(cfi(-1000)) & " : actual"
severity error;

assert (cfi(-10000) = 6)
report "cfi_test error # 2 " & LF &
"6 : expected" & LF &
to_string(cfi(-10000)) & " : actual"
severity error;


assert (cfi(1000) = 4)
report "cfi_test error # 3 " & LF &
"4 : expected" & LF &
to_string(cfi(1000)) & " : actual"
severity error;


assert (cfi(-100_000) = 7)
report "cfi_test error # 4 " & LF &
"7 : expected" & LF &
to_string(cfi(-100_000)) & " : actual"
severity error;


assert (cfi(100_000) = 6)
report "cfi_test error # 5 " & LF &
"6 : expected" & LF &
to_string(cfi(100_000)) & " : actual"
severity error;

assert (cfi(-9999999) = 8)
report "cfi_test error # 6 " & LF &
to_string(8) & " : expected" & LF &
to_string(cfi(-9999999)) & " : actual"
severity error;

assert (cfi(9999999) = 7)
report "cfi_test error # 7 " & LF &
to_string(7) & " : expected" & LF &
to_string(cfi(9999999)) & " : actual"
severity error;

wait;
end process;


--function cft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cft(CNTTIME,SYSCLKFREQ) = "100111010101101100110100000000")
report "count_for_time_test error # 1 " & LF &
to_string("100111010101101100110100000000") & " : expected" & LF &
to_string(cft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cft("1 min","66MHz") = "11101100000010001100111000000000")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100111000000000") & " : expected" & LF &
to_string(cft("1 min","66MHz")) & " : actual"
severity error;


assert (cft("1 hr","66MHz") = "11011101010010000100000100100000000000")
report "count_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100100000000000") & " : expected" & LF &
to_string(cft("1 hr","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz") = "01010010111110110001100001101100000000000000")
report "count_for_time_test error # 4 " & LF &
to_string("01010010111110110001100001101100000000000000") & " : expected" & LF &
to_string(cft("1 day","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 5 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz")) & " : actual"
severity error;


assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 6 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")+cft("1 as","66MHz")+cft("1 zs","66MHz")+cft("1 ys","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 7 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "011100011100110011110110101000101011010000000101001")
report "count_for_time_test error # 8 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-3 kHz") = "01")
report "count_for_time_test error # 9 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-18 eHz") = "01")
report "count_for_time_test error # 10 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cft("1 ns ","1E-15 yHz") = "01")
report "count_for_time_test error # 11 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cft("1 us ","1E-15 yHz") = "01111101000")
report "count_for_time_test error # 12 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(cft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cft("20 ms ","50 MHz"),21);

assert (ext(cft("20 ms ","50 MHz"),21) = "011110100001001000000")
report "count_for_time_test error # 13 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(ext(cft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test : process
begin

assert (cfth("1 us ","1E-15 yHz") = 10)
report "count_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cfth("8 ms ","1 kHz") = 4)
report "count_for_time_high_test2 error # 1 " & LF &
to_string(4) & " : expected" & LF &
to_string(cfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;



--function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
conv_to_hex_test1 : process
variable testVar : bv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test1 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
conv_to_hex_test2 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test2 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion
conv_to_hex_test3 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test3 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function cslv(int1Val : integer;
-- int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(sigVal : signed;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(usgVal : unsigned;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested


--function cuft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cuft(CNTTIME,SYSCLKFREQ) = "100111010101101100110011111111")
report "count_up_for_time_test error # 1 " & LF &
to_string("100111010101101100110011111111") & " : expected" & LF &
to_string(cuft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cuft("1 min","66MHz") = "11101100000010001100110111111111")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100110111111111") & " : expected" & LF &
to_string(cuft("1 min","66MHz")) & " : actual"
severity error;


assert (cuft("1 hr","66MHz") = "11011101010010000100000100011111111111")
report "count_up_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100011111111111") & " : expected" & LF &
to_string(cuft("1 hr","66MHz")) & " : actual"
severity error;


assert (cuft("1 day","66MHz") = "1010010111110110001100001101011111111111111")
report "count_up_for_time_test error # 4 " & LF &
to_string("1010010111110110001100001101011111111111111") & " : expected" & LF &
to_string(cuft("1 day","66MHz")) & " : actual"
severity error;




assert (cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "1010110011111110011100011111110110010010001")
report "count_up_for_time_test error # 6 " & LF &
to_string("1010110011111110011100011111110110010010001") & " : expected" & LF &
to_string(cuft("1 day","66MHz")+cuft("1 hr","66MHz")+cuft("1 min","66MHz")+cuft("1 sec","66MHz")+cuft("1 ms","66MHz")+cuft("1 us","66MHz")+cuft("1 ns","66MHz")+cuft("1 ps","66MHz")+cuft("1 fs","66MHz")+cuft("1 as","66MHz")+cuft("1 zs","66MHz")+cuft("1 ys","66MHz")) & " : actual" & LF &
to_string(cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;



assert (cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "11100011100110011110110101000101011010000000101000")
report "count_up_for_time_test error # 8 " & LF &
to_string("11100011100110011110110101000101011010000000101000") & " : expected" & LF &
to_string(cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-3 kHz") = "0")
report "count_up_for_time_test error # 9 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-18 eHz") = "0")
report "count_up_for_time_test error # 10 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cuft("1 ns ","1E-15 yHz") = "0")
report "count_up_for_time_test error # 11 " & LF &
to_string("0") & " : expected" & LF &
to_string(cuft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cuft("1 us ","1E-15 yHz") = "1111100111")
report "count_up_for_time_test error # 12 " & LF &
to_string("1111100111") & " : expected" & LF &
to_string(cuft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cuft("20 ms ","50 MHz"),21);

assert (ext(cuft("20 ms ","50 MHz"),25) = "0000011110100001000111111")
report "count_up_for_time_test error # 13 " & LF &
to_string("0000011110100001000111111") & " : expected" & LF &
to_string(ext(cuft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test : process
begin

assert (cufth("1 us ","1E-15 yHz") = 9)
report "count_up_for_time_high_test error # 1 " & LF &
to_string(9) & " : expected" & LF &
to_string(cufth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cufth("8 ms ","1 kHz") = 2)
report "count_up_for_time_high_test2 error # 1 " & LF &
to_string(2) & " : expected" & LF &
to_string(cufth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;

--function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value


--function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value



--function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed


--function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

--function ext(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector;
ext_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);

assert (ext2(slvVar,7) = "0000111") -- 7 bits
report "ext_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,7)) & " : actual"
severity error;

assert (ext2(slvVar,4) = "0111") -- 4 bits
report "ext_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,4)) & " : actual"
severity error;

assert (ext2(slvVar,4)'length = 4) -- 4 bits
report "ext_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(ext2(slvVar,4)'length) & " : actual"
severity error;

wait;
end process;



--function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order


--function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order



--function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order


--function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector



--function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed



--function mult_s(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply



--function mult_us(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply



--function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed



--function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value


--function now return string; -- returns a string representation of the current simulation time
now_test : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

wait for 3 sec;

assert (now = time'image(now))
report "now_test error # 1 " & LF &
time'image(now) & " : expected" & LF &
now & " : actual"
severity error;

wait;
end process;


--function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function reduce_high(vectorVal : std_logic_vector) return integer; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function seq(str1Val : string;
-- str2Val : string) return boolean;



--function shl(vectorVal : std_logic_vector;
-- natVal : natural) return std_logic_vector;



--function slv_to_bcd(vectorVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified



--function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed



--function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
-- MSB_Val : std_logic;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value



--function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer



--function str_to_led(stringVal : string;
-- CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs



--function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
str_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (str_to_slv("1") = "01") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("0") = "0") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("00") & " : expected" & LF &
to_string(str_to_slv("0")) & " : actual"
severity error;

assert (str_to_slv("-1") = "11") -- -1
report "bcd_to_led_test error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(str_to_slv("-1")) & " : actual"
severity error;

assert (str_to_slv("10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 1 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv("10 us"))
severity error;

assert (str_to_slv(" 10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 2 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us"))
severity error;

assert (str_to_slv(" 10 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 3 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us "))
severity error;

assert (str_to_slv(" 10.0 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 4 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0 us "))
severity error;

assert (str_to_slv(" 0.0100 ms ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 5 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0100 ms "))
severity error;

assert (str_to_slv(" 0.0000100sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0000100sec "))
severity error;

assert (str_to_slv(" 10E-6 sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E-6 sec "))
severity error;


assert (str_to_slv(" 10,000,000,000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 7 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10,000,000,000 "))
severity error;

assert (str_to_slv(" 100,000Hz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 8 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100,000Hz "))
severity error;


assert (str_to_slv(" 100kHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100kHz "))
severity error;

assert (str_to_slv(" 0.1MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.1MHz "))
severity error;

assert (str_to_slv(" .1 MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" .1 MHz "))
severity error;

assert (str_to_slv(" 0.0001GHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 10 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0001GHz "))
severity error;


assert (str_to_slv(" 10E 9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 11 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E 9 "))
severity error;


assert (str_to_slv(" 10E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 12 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9.000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9.000 "))
severity error;

assert (str_to_slv(" 100E+3 HZ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 14 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;


assert (str_to_slv(" 1") = "01")
report "str_to_slv_test error # 15a " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(str_to_slv(" 1"))
severity error;

assert (str_to_slv(" -1") = "11")
report "str_to_slv_test error # 15b " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(str_to_slv(" -1"))
severity error;


assert (str_to_slv("1") = "01")
report "str_to_slv_test error # 16 " & LF &
to_string("01") & " : expected"
& LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("10") = "01010")
report "str_to_slv_test error # 17 " & LF &
to_string("01010") & " : expected"
& LF &
to_string(str_to_slv("10")) & " : actual"
severity error;

assert (str_to_slv(" 100E+3 HZ ps ns MHz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 18 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100E+3 HZ Hz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 19 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100,000 HZ 234sec") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 20 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ 234sec"))
severity error;

assert (str_to_slv("1 day") = "01001010111100001010011101100011101110110001110000000000000000000000") -- 0
report "str_to_slv_test error # 21 " & LF &
to_string("01001010111100001010011101100011101110110001110000000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 day")) & " : actual"
severity error;

assert (str_to_slv("1 hr") = "011000111110101110001001110110100100111011010000000000000000000") -- 0
report "str_to_slv_test error # 22 " & LF &
to_string("011000111110101110001001110110100100111011010000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 hr")) & " : actual"
severity error;

assert (str_to_slv("1 min") = "011010101001010011010111010011110100001100000000000000000") -- 0
report "str_to_slv_test error # 23 " & LF &
to_string("011010101001010011010111010011110100001100000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 min")) & " : actual"
severity error;

assert (str_to_slv("1 sec") = "011100011010111111010100100110001101000000000000000") -- 0
report "str_to_slv_test error # 24 " & LF &
to_string("011100011010111111010100100110001101000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 sec")) & " : actual"
severity error;

assert (str_to_slv("1 ms") = "01110100011010100101001010001000000000000") -- 0
report "str_to_slv_test error # 25 " & LF &
to_string("01110100011010100101001010001000000000000") & " : expected" & LF &
to_string(str_to_slv("1 ms")) & " : actual"
severity error;

assert (str_to_slv("1 us") = "0111011100110101100101000000000") -- 0
report "str_to_slv_test error # 26 " & LF &
to_string("0111011100110101100101000000000") & " : expected" & LF &
to_string(str_to_slv("1 us")) & " : actual"
severity error;

assert (str_to_slv("1 ns") = "011110100001001000000") -- 0
report "str_to_slv_test error # 27 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 ns")) & " : actual"
severity error;

assert (str_to_slv("1 ps") = "01111101000") -- 0
report "str_to_slv_test error # 28 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 ps")) & " : actual"
severity error;

assert (str_to_slv("1 fs") = "01") -- 0
report "str_to_slv_test error # 29 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 fs")) & " : actual"
severity error;

assert (str_to_slv("1 as",-24) = "011110100001001000000") -- 0
report "str_to_slv_test error # 30 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 as",-24)) & " : actual"
severity error;

assert (str_to_slv("1 zs",-24) = "01111101000") -- 0
report "str_to_slv_test error # 31 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 zs",-24)) & " : actual"
severity error;

assert (str_to_slv("1 ys",-24) = "01") -- 0
report "str_to_slv_test error # 32 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 ys",-24)) & " : actual"
severity error;


assert (str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs") = "01001110000111011000111100110011111100101100110000111010000000101001") -- 0
report "str_to_slv_test error # 33 " & LF &
to_string("01001110000111011000111100110011111100101100110000111010000000101001") & " : expected" & LF &
to_string(str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs")) & " : actual"
severity error;


wait;
end process;


--function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed



--function str_to_slv_var_base(stringVal : string;
-- intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed



--function str_to_slv_var_base_high(stringVal : string;
-- intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value



--function strh(stringVal : string) return integer;

sxt_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := sxt2(int_to_slv(-1000),slv1Var'length);
slv2Var := sxt2(int_to_slv(-6),slv2Var'length);

assert (sxt2(slvVar,7) = "0000111") -- 7 bits
report "sxt2_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,7)) & " : actual"
severity error;

assert (sxt2(slvVar,4) = "0111") -- 4 bits
report "sxt2_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,4)) & " : actual"
severity error;

assert (sxt2("1001",7) = "1111001") -- 7 bits
report "sxt2_test error # 3 " & LF &
to_string("1111001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;

assert (sxt2("00",7) = "0000000") -- 4 bits
report "sxt2_test error # 4 " & LF &
to_string("0000000") & " : expected" & LF &
to_string(sxt2("00",7)) & " : actual"
severity error;

assert (sxt2("1001",4) = "1001") -- 7 bits
report "sxt2_test error # 5 " & LF &
to_string("1001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;


wait;
end process;

---- synopsys translate_off
--function time_to_slv(timeVal : time;
-- clkFreqVal : frequency) return std_logic_vector;
---- synopsys translate_on
--
--function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function
--
--function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency
--
---- synopsys translate_off
--function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
to_string_test1 : process
begin

assert (to_string(2147000000) = "2147000000")
report "to_string_test1 error # 1 " & LF &
"2147000000" & " : expected" & LF &
to_string(2147000000) & " : actual"
severity error;

assert (to_string(-2147000000) = "-2147000000")
report "to_string_test1 error # 2 " & LF &
"-2147000000" & " : expected" & LF &
to_string(-2147000000) & " : actual"
severity error;



wait;
end process;


--function to_string(realVal : real) return string; -- returns a string value for an real value passed
to_string_test2 : process
begin

assert (to_string(1.000000e+308) = "1.000000e+308")
report "to_string_test2 error # 1 " & LF &
"1.000000e+308" & " : expected" & LF &
to_string(1.000000e+308) & " : actual"
severity error;

assert (to_string(1.000000e-308) = "1.000000e-308")
report "to_string_test2 error # 2 " & LF &
"1.000000e-308" & " : expected" & LF &
to_string(1.000000e-308) & " : actual"
severity error;

assert (to_string(-1.000000e-308) = "-1.000000e-308")
report "to_string_test2 error # 2 " & LF &
"-1.000000e-308" & " : expected" & LF &
to_string(-1.000000e-308) & " : actual"
severity error;

wait;
end process;


--function to_string(timeVal : time) return string;
to_string_test3 : process
begin

assert (to_string(3 ns) = "3 ns")
report "to_string_test3 error # 1 " & LF &
"3 ns" & " : expected" & LF &
to_string(3 ns) & " : actual"
severity error;


assert (to_string(2040 ns) = "2040 ns")
report "to_string_test3 error # 1 " & LF &
"2040 ns" & " : expected" & LF &
to_string(2040 ns) & " : actual"
severity error;

wait;
end process;


--function to_string(vectorVal : std_logic_vector) return string;
---- synopsys translate_on
--
--function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--
--function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
--function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed
--
--function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed
--
--function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed
--
--------------------------------------------------------------------------------
---- Procedure Declarations
--------------------------------------------------------------------------------
---- synopsys translate_off
--procedure clkgen(
-- constant clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkPeriodSig : in time;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
---- synopsys translate_on
--
--procedure FF(
-- signal Clk : in std_logic;
-- signal Rst : in std_logic;
-- signal D : in std_logic_vector;
-- signal Q : out std_logic_vector);
--
--procedure slv_to_bcd(
-- signal BCD_RIn : in std_logic_vector;
-- signal BinIn : in std_logic_vector;
-- signal BinFBIn : in std_logic_vector;
-- signal ClkIn : in std_logic;
-- constant BCD_DigitsVal : in integer;
-- signal EnIn : in std_logic;
-- signal RstLowIn : in std_logic;
-- signal BCD_ROut : out std_logic_vector;
-- signal Bin_ROut : out std_logic_vector;
-- signal DoneOut : out std_logic);


divider_test : process
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);
begin
slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);
slv3Var := slv1Var/slv2Var;
-- assert FALSE
-- report "divider output :" & LF & to_string(to_int(slv1Var)) & " / " & to_string(to_int(slv2Var)) & " = " & to_string(to_int(slv3Var))
-- severity note;
wait;
end process;


bcd_to_led_test : process
variable slvVar : slv(27 downto 0);
begin
slvVar := bcd_to_led("0011001000010000",False); -- 3210
assert (slvVar = "1111001110110101100001111110")
report "bcd_to_led_test error # 1 "
severity error;
slvVar := bcd_to_led("0111011001010100",False); -- 7654
assert (slvVar = "1110010101111110110110110011")
report "bcd_to_led_test error # 2 "
severity error;
slvVar := bcd_to_led("0001000010011000",False); -- 1098
assert (slvVar = "0110000111111011100111111111")
report "bcd_to_led_test error # 3 "
severity error;
slvVar := bcd_to_led("0011001000010000",True); -- 3210
assert (slvVar = "0000110001001010011110000001")
report "bcd_to_led_test error # 4 "
severity error;
slvVar := bcd_to_led("0111011001010100",True); -- 7654
assert (slvVar = "0001101010000001001001001100")
report "bcd_to_led_test error # 5 "
severity error;
slvVar := bcd_to_led("0001000010011000",True); -- 1098
assert (slvVar = "1001111000000100011000000000")
report "bcd_to_led_test error # 6 "
severity error;
wait;
end process;


str_to_int_test : process
variable intVar : integer;
begin
intVar := str_to_int("10"); -- 3210
assert (intVar = 10)
report "str_to_int_test error # 1 " & LF &
"expected : 10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-10 sec"); -- 3210
assert (intVar = -10)
report "str_to_int_test error # 2 " & LF &
"expected : -10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-6 sec"); -- 3210
assert (intVar = -6)
report "str_to_int_test error # 3 " & LF &
"expected : -6" & LF &
"actual : " & to_string(intVar)
severity error;

wait;
end process;




reduce_test : process

begin

assert (reduce("00000") = "00") -- 0
report "reduce error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(reduce("00000")) & " : actual"
severity error;

assert (reduce("00001") = "01") -- 1
report "reduce error # 2 " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(reduce("00001"))
severity error;

assert (reduce("11111") = "11") -- -1
report "reduce error # 3 " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(reduce("11111"))
severity error;

assert (reduce("10000") = "10000") -- -16
report "reduce error # 4 " & LF &
"expected : " & to_string("10000") & LF &
"actual : " & to_string(reduce("10000"))
severity error;

wait;

end process;











--exp_test : process
--variable timeBaseVar : slv(500 downto 0);
--variable lineVar : line;
--begin
-- timeBaseVar := ext("01",timeBaseVar'length);
-- for loopVar in 1 to 50 loop
-- timeBaseVar := timeBaseVar(timeBaseVar'high-4 downto 0) * "1010";
--
---- write(lineVar,to_string(real(reduce_high(timeBaseVar))/real(loopVar)));
---- write(lineVar,LF);
-- assert FALSE
-- report
-- to_string(real(reduce_high(timeBaseVar))/real(loopVar)) & LF
-- severity note;
-- end loop;
--
-- wait;
--end process;



unsigned_mult_test : process

begin

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

assert (mult_us("000","011") = "000000") -- 0
report "mult error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","011")) & " : actual"
severity error;

assert (mult_us("011","000") = "000000") -- 0
report "mult error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("011","000")) & " : actual"
severity error;

assert (mult_us("000","101") = "000000") -- 0
report "mult error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","101")) & " : actual"
severity error;

assert (mult_us("101","000") = "000000") -- 0
report "mult error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("101","000")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 7 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

wait;

end process;








signed_mult_test : process

begin

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("000","011") = "000000") -- 0
report "mult_s error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","011")) & " : actual"
severity error;

assert (mult_s("011","000") = "000000") -- 0
report "mult_s error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("011","000")) & " : actual"
severity error;

assert (mult_s("000","101") = "000000") -- 0
report "mult_s error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","101")) & " : actual"
severity error;

assert (mult_s("101","000") = "000000") -- 0
report "mult_s error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("101","000")) & " : actual"
severity error;

assert (mult_s("011","101") = "110111") -- 3 * (-3) = -9
report "mult_s error # 7 " & LF &
to_string("110111") & " : expected" & LF &
to_string(mult_s("011","101")) & " : actual"
severity error;

assert (mult_s("011","100") = "110100") -- 3 * (-4) = -12
report "mult_s error # 8 " & LF &
to_string("110100") & " : expected" & LF &
to_string(mult_s("011","100")) & " : actual"
severity error;

assert (mult_s("101","101") = "001001") -- (-3) * (-3) = 9
report "mult_s error # 9 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("101","101")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 10 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 11 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;


assert (mult_s("100","100") = "010000") -- -4 * -4 = 16
report "mult_s error # 11 " & LF &
to_string("010000") & " : expected" & LF &
to_string(mult_s("100","100")) & " : actual"
severity error;



wait;

end process;








conv_to_hex_test : process
constant slvVar : slv(11 downto 0) := "101011110000";

begin

assert (conv_to_hex(slvVar) = "AF0") -- 0
report "mult_s error # 1 " & LF &
"AF0 : expected" & LF &
conv_to_hex(slvVar) & " : actual"
severity error;


wait;

end process;


--assert FALSE
--report "THIS IS THE END OF SIMULATION" & LF
--severity failure;

------------------------------------------------------------------------------
end behavioral;
-----------------------------------------------------------------------------

-- end of extension_pack testbench


-- synopsys translate_on
 
M

My Name

------------------------------------------------------------------------------
--
-- author : Michael Bills ([email protected])
--
-- description : This package has functions and procedures
-- for testbenching and assisting in RTL design
-- creation. It consists mostly of conversion functions.
--
--
-- Copyright (c) 2005 by Michael Bills
--
-- Permission to use, copy, modify, distribute, and sell this source code
-- for any purpose is hereby granted without fee, provided that
-- the above copyright notices and this permission notice appear
-- in all copies of this source code.
--
-- THIS SOURCE CODE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND,
-- EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION,
-- ANY WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.
--
-- THE USER OF THIS SOURCE CODE ASSUMES ALL LIABILITY FOR THEIR USE
-- OF THIS SOURCE CODE.
--
-- IN NO EVENT SHALL MICHAEL BILLS BE LIABLE FOR ANY SPECIAL, INCIDENTAL,
-- INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, OR ANY DAMAGES WHATSOEVER
-- RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER OR NOT ADVISED OF
-- THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF LIABILITY, ARISING
-- OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOURCE CODE.
--
------------------------------------------------------------------------------


-- LIBRARY STATEMENT
library ieee, extension_lib;

-- PACKAGE STATEMENT
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_signed."abs";
use ieee.std_logic_unsigned.all;
use ieee.std_logic_textio.all;
use std.textio.all;


------------------------------------------------------------------------------
package extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Type Declarations
------------------------------------------------------------------------------
type hexchar is ('0', '1', '2', '3', '4', '5', '6', '7',
'8', '9', 'A', 'B', 'C', 'D', 'E', 'F');

type hex is array (positive range <>) of hexchar;

type LED_Char is (' ', '"', ''', '-', '.', '/', '0', '1',
'2', '3', '4', '5', '6', '7', '8', '9',
'=', '?', 'A', 'B', 'C', 'D', 'E', 'F',
'G', 'H', 'I', 'J', 'K', 'L', 'O', 'P',
'S', 'T', 'U', 'Y', 'Z', '\', ']', '^',
'_', 'b', 'c', 'd', 'h', 'g', 'j', 'l',
'n', 'o', 'r', 'u', '¬', '­', '¯', '°',
'·');

type SevenSegLED is array (positive range <>) of LED_Char;


type frequency is range -1 to 2_147_483_647
units
Hz;
daHz = 10 Hz; -- dekahertz 10E+1
hHz = 10 daHz; -- hectohertz 10E+2
kHz = 10 hHz; -- kilohertz 10E+3
MHz = 1000 kHz; -- megahertz 10E+6
GHz = 1000 MHz; -- gigahertz 10E+9
end units;


------------------------------------------------------------------------------
-- Subtype Declarations
------------------------------------------------------------------------------
--subtype bv is bit_vector;
--subtype char is character;
---- synopsys translate_off
--subtype fok is file_open_kind;
--subtype fos is file_open_status;
--subtype freq is frequency;
---- synopsys translate_on
--subtype int is integer;
--subtype nat is natural;
--subtype pos is positive;
--subtype sl is std_logic;
--subtype slv is std_logic_vector;
--subtype str is string;
--subtype sul is std_ulogic;
--subtype sulv is std_ulogic_vector;
--subtype uns is unsigned;


------------------------------------------------------------------------------
-- Constant Declarations
------------------------------------------------------------------------------
-- count_for_time base size (-60 means the timebase = 10E-60 seconds)
-- this value should be increased if round off error occurs
-- in a value computed by the function "count_for_time" or if
-- array length errors similar to this occur:
-- # ** Fatal: (vsim-3420) Array lengths do not match. Left is (96 downto 0). Right is (97 downto 0).
--
-- This value must be smaller than MAX_VECT_SIZE by a factor of 4 for
-- logic vectors 2 bits long and it must be smaller by a factor of 3.5 for
-- logic vectors longer than 2 bits

constant CFT_BASE_SIZE : integer := -30;


-- this value represents the largest size a logic vector may be for certain
-- functions and procedures in this package. It is used to set upper loop
-- limits for non-deterministic values thus avoiding the use of access
-- types and enabling the functions to be used for synthesizeable code.
--
-- This value may be increased (as high as natural'high will allow)
-- if a larger value needs to be represented, or it may be decreased
-- if compile time is excessive by modifying the CFT_BASE_SIZE constant

constant MAX_VECT_SIZE : natural := (-CFT_BASE_SIZE)*4;


------------------------------------------------------------------------------
-- Function Declarations
------------------------------------------------------------------------------

function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector;

function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector;

--function "/"(Dividend : std_logic_vector;
-- Divisor : std_logic_vector) return std_logic_vector; -- synthesizeable version

function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector;

function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector;

function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector;

function bcd_to_led(slvVal : std_logic_vector ;
CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion

function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function

function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference

function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 2 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cdfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified (minus a count of 2) using the frequency (or period) value passed as a reference

function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer

function cfi(intVal : integer) return natural; -- This function returns a natural representing the number of characters required to reprsent an integer value. It is essentially an integer'length function for the characters.

function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference

function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cfth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference


function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector; -- create a 50% duty cycle count time using the frequency (or period) value passed as a reference

function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion

function cslv(int1Val : integer;
int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(sigVal : signed;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
function cslv(usgVal : unsigned;
intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"

function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference

function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector; -- count for the time specified (minus a count of 1 for latency) using the frequency (or period) value passed as a reference and the integer value passed as a length for the vector (if it will fit in a vector that size)

function cufth(timeStrVal : string;
freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference

function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfi_syn(intVal : integer) return natural; -- returns the number of decimal places for an integer value

function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value

function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed
function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with zeros, to the length specified by intVal unless the vector is already longer than that

function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order
function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order

function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector

function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed

function itoa(intVal : integer) return string;

function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply

function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed

-- synopsys translate_off
impure function now return string; -- returns a string representation of the current simulation time
-- synopsys translate_on

function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value

function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed
function reduce_high(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'high value of a vector just large enough to represent the standard logic vector value passed
function reduce_length(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed (including a sign bit)
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer; -- returns an integer value that represents the vector'length value of a vector just large enough to represent the standard logic vector value passed

function seq(str1Val : string;
str2Val : string) return boolean;

function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector;

function slv_to_bcd(vectorVal : std_logic_vector;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed

function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
MSB_Val : std_logic;
BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value

function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer

function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs

function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed
function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed

function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value

function strh(stringVal : string) return integer;

function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector; -- returns a standard logic vector, padded with sign bits, to the length specified by intVal unless the vector is already longer than that

function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function

-- synopsys translate_off
function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency
-- synopsys translate_on

function to_string(intVal : integer) return string; -- returns the string representation of an integer value passed
function to_string(realVal : real) return string; -- returns the string representation of a real value passed
function to_string(timeVal : time) return string; -- returns the string representation of a time value passed
function to_string(vectorVal : std_logic_vector) return string; -- returns the string representation of a std_logic_vector value passed

function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"

function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed

function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed

function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed

------------------------------------------------------------------------------
-- Procedure Declarations
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);

procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic);
-- synopsys translate_on

procedure FF(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector);

procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector;
signal DoneOut : out std_logic);


------------------------------------------------------------------------------
-- Aliases
------------------------------------------------------------------------------
alias bool is boolean;
alias bv is bit_vector;
alias char is character;
-- synopsys translate_off
alias fok is file_open_kind;
alias fos is file_open_status;
alias freq is frequency;
-- synopsys translate_on
alias int is integer;
alias nat is natural;
alias pos is positive;
alias sl is std_logic;
alias slv is std_logic_vector;
alias str is string;
alias sul is std_ulogic;
alias sulv is std_ulogic_vector;
alias uns is unsigned;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------


------------------------------------------------------------------------------
package body extension_pack is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- Functions
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies an integer by a std_logic_vector
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : integer;
MultiplierVal : std_logic_vector) return std_logic_vector is
begin
return int_to_slv(MultiplicandVal)*MultiplierVal;
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "*"
--
-- DESCRIPTION : This function multiplies a std_logic_vector by an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function "*"(MultiplicandVal : std_logic_vector;
MultiplierVal : integer) return std_logic_vector is
begin
return MultiplicandVal*int_to_slv(MultiplierVal);
end "*";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an unsigned std_logic vector value
-- by another unsigned std_logic_vector value
--
-- NOTES : the algorithm used in this function
-- is the standard long division algorithm.
-- it rounds to the nearest value
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : std_logic_vector) return std_logic_vector is
variable DividendVar : std_logic_vector(DividendVal'length+DivisorVal'length downto 0);
variable DivisorVar : std_logic_vector(DivisorVal'length downto 0);
variable InterimVar : std_logic_vector(DivisorVal'length downto 0);
variable ResultVar : std_logic_vector(DividendVal'length downto 0);
begin
DividendVar := ext(DividendVal & '0',DividendVar'length);
DivisorVar := '0' & DivisorVal;
InterimVar := '0' & DividendVar(DividendVar'high downto DividendVar'high-(DivisorVar'length-2));
ResultVar := (others => '0');
for loopVar in ResultVar'range loop
if (InterimVar >= DivisorVar) then
InterimVar := InterimVar - DivisorVar;
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '1';
else
InterimVar := InterimVar(InterimVar'high-1 downto 0) & DividendVar(loopVar);
ResultVar(loopVar) := '0';
end if;
end loop;
-- round to the nearest digit
if (InterimVar >= DivisorVal) then -- it the remainder is at least 1/2 of the Divisor (it was effectively multiplied by two during the final pass through the loop)
ResultVar := ResultVar + '1'; -- then round up to the next value
end if;
return ResultVar(ResultVar'length-2 downto 0);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides a std_logic vector value by
-- another std_logic_vector value
--
--
-- NOTES : this function is synthesizable
--
------------------------------------------------------------------------------
--function "/"(DividendVal : STD_LOGIC_VECTOR;
-- DivisorVal : STD_LOGIC_VECTOR) return STD_LOGIC_VECTOR is
--
--variable B : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable A : STD_LOGIC_VECTOR(DividendVal'length - 1 downto 0);
--variable QUOTIENT, REMAINDER : STD_LOGIC_VECTOR(DivisorVal'length - 1 downto 0);
--variable VECT : STD_LOGIC_VECTOR(DividendVal'length downto 0);
--variable QI : STD_LOGIC_VECTOR(0 downto 0);
--variable OVFL : STD_LOGIC;
--
--function div(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--
--variable R : STD_LOGIC_VECTOR(A'length - 2 downto 0);
--variable RESIDUAL : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--variable S : STD_LOGIC_VECTOR(B'length + Q'length downto 0);
--
--function div1(A: STD_LOGIC_VECTOR;
-- B: STD_LOGIC_VECTOR;
-- Q: STD_LOGIC_VECTOR;
-- EXT: STD_LOGIC) return STD_LOGIC_VECTOR is
--variable S : STD_LOGIC_VECTOR(A'length downto 0);
--variable REST : STD_LOGIC_VECTOR(A'length - 1 downto 0);
--variable QN : STD_LOGIC_VECTOR(Q'length downto 0);
--
--begin
-- S := EXT & A - B;
--
-- QN := Q & (not S(S'high));
-- if S(S'high) = '1' then
-- REST := A;
-- else
-- REST := S(S'high - 1 downto 0);
-- end if;
-- return QN & REST;
--end div1;
--
--begin
-- S := div1(A(A'high downto A'high - B'high), B, Q, EXT);
-- QN := S(S'high downto B'high + 1);
--
-- if A'length > B'length then
-- R := S(B'high - 1 downto 0) & A(A'high - B'high - 1 downto 0);
-- return DIV(R, B, QN, S(B'high)); -- save MSB '1' in the rest for future sum
-- else
-- RESIDUAL := S(B'high downto 0);
-- return QN(QN'high - 1 downto 0) & RESIDUAL; -- delete initial '0'
-- end if;
--end div;
--
--begin
-- A := DividendVal; -- it is necessary to avoid errors during synthesis!!!!
-- B := DivisorVal;
-- QI := (others =>'0');
--
-- VECT := div(A, B, QI, '0');
--
-- QUOTIENT := VECT(VECT'high - 1 downto B'high + 1);
-- REMAINDER := VECT(B'high downto 0);
-- OVFL := VECT(VECT'high );
-- return OVFL & QUOTIENT & REMAINDER;
---- return VECT;
--
--end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : std_logic_vector;
DivisorVal : integer) return std_logic_vector is
begin
return DividendVal/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : "/"
--
-- DESCRIPTION : This function divides an string value
-- by integer value
--
-- NOTES :
--
------------------------------------------------------------------------------
function "/"(DividendVal : string;
DivisorVal : integer) return std_logic_vector is
begin
return str_to_slv(DividendVal)/int_to_slv(DivisorVal);
end "/";


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_led
--
-- DESCRIPTION : This function converts a packed BCD vector or a hex value
-- into a seven segment LED output
--
-- NOTES if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function bcd_to_led(slvVal : std_logic_vector ; CAVal : boolean) return std_logic_vector is
variable resultVar : std_logic_vector(7*slvVal'length/4-1 downto 0);
variable vectorParseVar : std_logic_vector(3 downto 0);
variable vectorVar : std_logic_vector(slvVal'length-1 downto 0);
begin
vectorVar := slvVal; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
for loopVar in 0 to slvVal'length/4-1 loop
vectorParseVar := vectorVar(4*loopVar+3 downto 4*loopVar);
case vectorParseVar is
-- Illuminated
-- vector Segment
-- value abcdefg
when "0000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111110"; -- 0
when "0001" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- 1
when "0010" => resultVar(7*loopVar+6 downto 7*loopvar) := "1101101"; -- 2
when "0011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111001"; -- 3
when "0100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110011"; -- 4
when "0101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011011"; -- 5
when "0110" => resultVar(7*loopVar+6 downto 7*loopvar) := "1011111"; -- 6
when "0111" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110010"; -- 7
when "1000" => resultVar(7*loopVar+6 downto 7*loopvar) := "1111111"; -- 8
when "1001" => resultVar(7*loopVar+6 downto 7*loopvar) := "1110011"; -- 9
when "1010" => resultVar(7*loopVar+6 downto 7*loopvar) := "0001000"; -- A
when "1011" => resultVar(7*loopVar+6 downto 7*loopvar) := "1100000"; -- b
when "1100" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110001"; -- C
when "1101" => resultVar(7*loopVar+6 downto 7*loopvar) := "1000010"; -- d
when "1110" => resultVar(7*loopVar+6 downto 7*loopvar) := "0110000"; -- E
when "1111" => resultVar(7*loopVar+6 downto 7*loopvar) := "0111000"; -- F
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end bcd_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- in standard logic vector for and returns an unsigned,
-- decending range, binary value
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector is
type BCDArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(vectorVal'length-1 downto 0); --
variable CarryVar : std_logic_vector(vectorVal'length/4 downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable BCDVar : BCDArrayType; -- BCD value array
variable ResultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
BCDVar(0) := vectorVal; -- set the initial entry in the array to the input vector
for OutrLoopVar in 1 to vectorVal'length loop --
CarryVar(CarryVar'high) := '0';
for InnrLoopVar in CarryVar'high-1 downto 0 loop -- start at the MSB of the BCD vector
BCD_WoCarVar := '0' & BCDVar(OutrLoopVar-1) -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
(4*InnrLoopVar+3 downto 4*InnrLoopVar+1); -- read the results of the previous calculation
BCD_WiCarVar := BCD_WoCarVar + "0101"; -- compute the result for the current BCD digit if carry is needed
CarryVar(InnrLoopVar) := BCDVar(OutrLoopVar-1)(4*InnrLoopVar); -- read in the next bit of the LSB of the previous BCD digit input into the lowest carry bit
if (CarryVar(InnrLoopVar+1) = '1') then -- if the the previous digit has a carry bit then then the result of the binary shift right is greater by 5
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WiCarVar;
else -- otherwise
BCDVar(OutrLoopVar)(4*InnrLoopVar+3 downto 4*InnrLoopVar) := BCD_WoCarVar; -- we shift the bits right by 1 space
end if;
end loop;
ResultVar(OutrLoopVar-1) := BCDVar(OutrLoopVar-1)(0);
end loop;
return ResultVar;
end bcd_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bcd_to_slv_pipe
--
-- DESCRIPTION : This function converts a packed binary coded decimal (BCD)
-- into an unsigned, decending range,
-- binary value into a standard logic vector
-- and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
function bcd_to_slv_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift right
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0) := (others => '0'); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
CarryVar(CarryVar'high) := '0';
for loopVar in BCD_DigitsVal-1 downto 0 loop
BCD_WoCarVar := '0' & BCDVar(4*loopVar+3 downto 4*loopVar+1);
BCD_WiCarVar := BCD_WoCarVar + "0101";
CarryVar(loopVar) := BCDVar(4*loopVar);
if (CarryVar(loopVar+1) = '1') then
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WiCarVar;
else
ResultVar(4*loopVar+3 downto 4*loopVar) := BCD_WoCarVar;
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end bcd_to_slv_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : bv_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an bit vector
-- to a std logic vector.
--
-- NOTES
--
------------------------------------------------------------------------------
function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector is
begin
return To_StdLogicVector(bitVectVal);
end bv_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce((timeVar/freqStrVar) - 2);
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdft (count down for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value (minus 2 for
-- latency for counting down to an underflow for) using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a variable
-- value (CountValIn) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig(CountRSig'high) = '1') then
-- CountSig <= CountValIn;
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig - 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cdft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cdfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length((timeVar/freqStrVar) - 2);
if (lengthVar >= natVal) then
return reduce((timeVar/freqStrVar) - 2);
else
return zeroVar & reduce((timeVar/freqStrVar) - 2);
end if;
end cdft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cdfth (count down for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 2
-- for use in counting down to underflow) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cdfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high((timeVar/freqStrVar) - 2);
end cdfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ceil (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function rounds a real value up to the next
-- real integer
--
-- NOTES
--
------------------------------------------------------------------------------
function ceil (RealVal : in real) return real is
constant integerMaxVal : real := real(2_147_483_647);
variable RoundVar : real;
variable ResultVar : real;
begin
RoundVar := real(integer(RealVal));
if (abs(RealVal) >= integerMaxVal) then
ResultVar := RealVal;
elsif (RoundVar = RealVal) then
ResultVar := RoundVar;
elsif (RealVal > 0.0) then
if (RoundVar >= RealVal) then
ResultVar := RoundVar;
else
ResultVar := RoundVar + 1.0;
end if;
elsif (RealVal = 0.0) then
ResultVar := 0.0;
else
if (RoundVar <= RealVal) then
ResultVar := RoundVar + 1.0;
else
ResultVar := RoundVar;
end if;
end if;
return ResultVar;
end ceil;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfi (characters for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of characters required to reprsent an
-- integer value. It is essentially
-- an integer'length function for the characters.
--
-- NOTES :
--
------------------------------------------------------------------------------
function cfi(intVal : integer) return natural is
variable intVar : integer;
variable negVar : boolean;
begin
if (intVal < 0) then
intVar := -intVal;
negVar := true;
else
intVar := intVal;
negVar := false;
end if;
for LoopVar in 1 to MAX_VECT_SIZE loop
if (intVar = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
if (negVar) then
return loopVar + 1; -- allow for the '-' character
else
return loopVar;
end if;
else
intVar := intVar/10;
end if;
end loop;
end cfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce(timeVar/freqStrVar);
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cft (count for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function cft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cfth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length(timeVar/freqStrVar);
if (lengthVar >= natVal) then
return reduce(timeVar/freqStrVar);
else
return zeroVar & reduce(timeVar/freqStrVar);
end if;
end cft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cfth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cfth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high(timeVar/freqStrVar);
end cfth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : clkcnt (50% duty cycle clock count)
--
-- DESCRIPTION : This function takes a string based frequency value and
-- converts it to a std_logic_vector value using
-- a string based frequency value, as a reference
-- NOTES
-- this function is for use with a process which counts
-- up to a static value. This method gives the smallest and
-- fastest circuit
--
--CounterProcess2:process(ClkRSig,Count2RSig)
-- variable CLKCNTVAL : slv := clkcnt("Freq1StrVal","Freq2StrVal")
--begin
-- if (Count2RSig = CLKCNTVAL) then
-- Count2Sig <= (others => '0');
-- ClkSig <= not ClkRSig;
-- else
-- Count2Sig <= Count2RSig + 1;
-- ClkSig <= ClkRSig;
-- end if;
--end process;
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
------------------------------------------------------------------------------
function clkcnt(freq1StrVal : string;
freq2StrVal : string) return std_logic_vector is
variable freq1StrVar : std_logic_vector(str_to_slv_var_base_high(freq1StrVal,CFT_BASE_SIZE) downto 0);
variable freq2StrVar : std_logic_vector(str_to_slv_var_base_high(freq2StrVal,CFT_BASE_SIZE) downto 0);
begin
freq1StrVar := str_to_slv(freq1StrVal,CFT_BASE_SIZE);
freq2StrVar := str_to_slv(freq2StrVal,CFT_BASE_SIZE);
return reduce_unsigned((freq1StrVar/freq2StrVar)/2-1);
end clkcnt;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a bit vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : bit_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : bit_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a logic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_logic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(VectorVar,vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : conv_to_hex
--
-- DESCRIPTION : This function converts a ulogic vector of any length to a
-- string representing the Hexadecimal value of that vector
-- NOTES
--
------------------------------------------------------------------------------
function conv_to_hex(vectorVal : std_ulogic_vector) return string is
variable resultVar : string(integer(ceil(real(vectorVal'length)/4.0)) downto 1);
variable vectorParseVar : std_logic_vector(4 downto 1);
variable vectorStretchVar : std_logic_vector((integer(ceil(real(vectorVal'length)/4.0)))*4 downto 1);
variable VectorVar : std_ulogic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
vectorStretchVar := ext(to_stdlogicvector(VectorVar),vectorStretchVar'length);
for loopVar in resultVar'range loop
vectorParseVar := vectorStretchVar(loopVar*4 downto loopVar*4-3);
case vectorParseVar(4 downto 1) is
when "0000" => resultVar(loopVar) := '0';
when "0001" => resultVar(loopVar) := '1';
when "0010" => resultVar(loopVar) := '2';
when "0011" => resultVar(loopVar) := '3';
when "0100" => resultVar(loopVar) := '4';
when "0101" => resultVar(loopVar) := '5';
when "0110" => resultVar(loopVar) := '6';
when "0111" => resultVar(loopVar) := '7';
when "1000" => resultVar(loopVar) := '8';
when "1001" => resultVar(loopVar) := '9';
when "1010" => resultVar(loopVar) := 'A';
when "1011" => resultVar(loopVar) := 'B';
when "1100" => resultVar(loopVar) := 'C';
when "1101" => resultVar(loopVar) := 'D';
when "1110" => resultVar(loopVar) := 'E';
when "1111" => resultVar(loopVar) := 'F';
when others =>
end case;
end loop;
return resultVar;
end conv_to_hex;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer (int1Val)
-- to a std logic vector of length int2Val.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(int1Val : integer; int2Val : integer) return std_logic_vector is
begin
return conv_std_logic_vector(int1Val,int2Val);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert signed to std_logic_vector)
--
-- DESCRIPTION : This function converts an signed value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(sigVal : signed; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(sigVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cslv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an unsigned value
-- to a std logic vector of length intVal.
--
-- NOTES
--
------------------------------------------------------------------------------
function cslv(usgVal : unsigned; intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(usgVal,intVal);
end cslv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to.
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_unsigned((timeVar/freqStrVar) - 1);
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cuft (count up for time)
--
-- DESCRIPTION : This function takes a string based time value and
-- converts it to a std_logic_vector (minus one for latency)
-- value using a string based frequency value,
-- as a reference
-- NOTES
--
-- if the following error occurs it is due to an improperly sized vector
-- that the result of this function is assigned to:
--
--# ** Fatal: (vsim-3420) Array lengths do not match.
--
-- This function is best used to determine a constant
-- value (COUNTVALUE) for use with a counter styled similarly
-- to this:
--
-- CounterProcess:process(CountRSig,CountValIn)
-- begin
-- if (CountRSig = COUNTVALUE) then
-- CountSig <= (others => '0');
-- PulseSig <= '1';
-- else
-- CountSig <= CountRSig + 1;
-- PulseSig <= '0';
-- end if;
-- end process;
--
------------------------------------------------------------------------------
function cuft(timeStrVal : string;
freqStrVal : string;
natVal : natural) return std_logic_vector is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable lengthVar : natural;
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
variable zeroVar : std_logic_vector(natVal - cufth(timeStrVal,freqStrVal) - 2 downto 0) := (others => '0');
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
lengthVar := reduce_length_unsigned((timeVar/freqStrVar) - 1);
if (lengthVar >= natVal) then
return reduce_unsigned((timeVar/freqStrVar) - 1);
else
return zeroVar & reduce_unsigned((timeVar/freqStrVar) - 1);
end if;
end cuft;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : cufth (count up for time high)
--
-- DESCRIPTION : This function computes the vector'high value
-- from a string based time value (minus a count of 1
-- for use in counting up from zero to the proper value) and
-- converts it to a std_logic_vector value using
-- the a string based period value, as a reference
-- NOTES
--
------------------------------------------------------------------------------
function cufth(timeStrVal : string;
freqStrVal : string) return integer is
variable freqStrVar : std_logic_vector(str_to_slv_var_base_high(freqStrVal,CFT_BASE_SIZE) downto 0);
variable timeVar : std_logic_vector(str_to_slv_var_base_high(timeStrVal,CFT_BASE_SIZE) downto 0);
begin
freqStrVar := str_to_slv(freqStrVal,CFT_BASE_SIZE);
timeVar := str_to_slv(timeStrVal,CFT_BASE_SIZE);
return reduce_high_unsigned((timeVar/freqStrVar) - 1);
end cufth;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi (decimal places for integer)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function (does not count
-- a '-' character).
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi(intVal : integer) return natural is
variable intVar : integer;
variable CountVar : natural := 1;
variable ResultVar : natural;
begin
if (intVal < 0) then
intVar := -intVal;
else
intVar := intVal;
end if;
for CountVar in 1 to MAX_VECT_SIZE loop
if (intVal = 0) then
return 1;
elsif (intVar < 10 and intVar >= 1) then
return CountVar;
else
intVar := intVar/10;
end if;
end loop;
end dpfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfi_syn (decimal places for integer (synthesizeable))
--
-- DESCRIPTION : This function returns a natural representing the
-- number of digits in an integer value. It is essentially
-- an integer'length function.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfi_syn(intVal : integer) return natural is
variable resultVar : natural;
begin
if (intVal <= -1_000_000_000 or intVal >= 1_000_000_000) then
resultVar := 10;
elsif (intVal <= -100_000_000 or intVal >= 100_000_000) then
resultVar := 9;
elsif (intVal <= -10_000_000 or intVal >= 10_000_000) then
resultVar := 8;
elsif (intVal <= -1_000_000 or intVal >= 1_000_000) then
resultVar := 7;
elsif (intVal <= -100_000 or intVal >= 100_000) then
resultVar := 6;
elsif (intVal <= -10_000 or intVal >= 10_000) then
resultVar := 5;
elsif (intVal <= -1_000 or intVal >= 1_000) then
resultVar := 4;
elsif (intVal <= -100 or intVal >= 100) then
resultVar := 3;
elsif (intVal <= -10 or intVal >= 10) then
resultVar := 2;
else
resultVar := 1;
end if;
return resultVar;
end dpfi_syn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfr (decimal places for real)
--
-- DESCRIPTION : This function returns an natural representing the
-- number of digits to the left of the decimal
-- in a real value.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfr(realVal : real) return natural is
variable realVar : real;
variable ResultVar : natural;
begin
if (realVal < 0.0) then
realVar := -realVal;
else
realVar := realVal;
end if;
for loopVar in 1 to MAX_VECT_SIZE loop
if (realVal = 0.0) then
return 1;
elsif (realVar < 10.0 and realVar >= 1.0) then
return loopVar;
else
realVar := realVar/10.0;
end if;
end loop;
end dpfr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvr (decimal places for slv range)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the largest integer value that
-- can be represented by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvr(vectorVal : std_logic_vector) return natural is
variable returnVar : std_logic_vector(vectorVal'length-1 downto 0) := (others => '1');
begin
return dpfi(conv_integer(returnVar));
end dpfslvr;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : dpfslvv (decimal places for slv value)
--
-- DESCRIPTION : This function returns a natural representing the
-- number of decimal places the integer value represented
-- by a vector will occupy.
--
-- NOTES :
--
------------------------------------------------------------------------------
function dpfslvv(vectorVal : std_logic_vector) return natural is
begin
return dpfi(conv_integer(vectorVal));
end dpfslvv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : ext2 (zero extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by natVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function ext2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable vectorVar : slv (vectorVal'length - 1 downto 0);
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
begin
vectorVar := vectorVal;
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end ext2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : bit_vector) return bit_vector is
variable resultVar : bit_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_logic_vector) return std_logic_vector is
variable resultVar : std_logic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : flip
--
-- DESCRIPTION : This function returns a vector with all the bits
-- in the vector flipped.
-- i.e. if vectorval = 00011001
-- flip(vectorval) returns 10011000
-- NOTES
--
------------------------------------------------------------------------------
function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector is
variable resultVar : std_ulogic_vector(vectorVal'range);
begin
for loopVar in vectorVal'range loop
resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end flip;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : hex_to_slv
--
-- DESCRIPTION : This function converts a Hexadecimal value string
-- of any length to a std_logic_vector
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function hex_to_slv(stringVal : string) return std_logic_vector is
variable stringVar : string(1 to stringVal'length);
variable resultVar : std_logic_vector(4*stringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '0' => resultVar(4*loopVar downto 4*loopvar-3) := "0000";
when '1' => resultVar(4*loopVar downto 4*loopvar-3) := "0001";
when '2' => resultVar(4*loopVar downto 4*loopvar-3) := "0010";
when '3' => resultVar(4*loopVar downto 4*loopvar-3) := "0011";
when '4' => resultVar(4*loopVar downto 4*loopvar-3) := "0100";
when '5' => resultVar(4*loopVar downto 4*loopvar-3) := "0101";
when '6' => resultVar(4*loopVar downto 4*loopvar-3) := "0110";
when '7' => resultVar(4*loopVar downto 4*loopvar-3) := "0111";
when '8' => resultVar(4*loopVar downto 4*loopvar-3) := "1000";
when '9' => resultVar(4*loopVar downto 4*loopvar-3) := "1001";
when 'a' | 'A' => resultVar(4*loopVar downto 4*loopvar-3) := "1010";
when 'b' | 'B' => resultVar(4*loopVar downto 4*loopvar-3) := "1011";
when 'c' | 'C' => resultVar(4*loopVar downto 4*loopvar-3) := "1100";
when 'd' | 'D' => resultVar(4*loopVar downto 4*loopvar-3) := "1101";
when 'e' | 'E' => resultVar(4*loopVar downto 4*loopvar-3) := "1110";
when 'f' | 'F' => resultVar(4*loopVar downto 4*loopvar-3) := "1111";
when others =>
end case;
end loop;
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end hex_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : int_to_slv (convert integer to std_logic_vector)
--
-- DESCRIPTION : This function converts an integer value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function int_to_slv(intVal : integer) return std_logic_vector is
begin
return conv_std_logic_vector(intVal,vlfi(intVal)); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end int_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : itoa
--
-- DESCRIPTION : commonly used integer-to-string type converter
--
-- NOTES
--
------------------------------------------------------------------------------
--function itoa(intVal : integer) return string is
-- variable IntVar : integer := intVal;
--begin
-- if (IntVar < 0) then
-- return "-" & itoa(-IntVar);
-- elsif IntVar < 10 then
-- return IntString(IntVar);
-- else
-- return itoa(IntVar/10) & IntString(IntVar rem 10);
-- end if;
--end function itoa;


function itoa(intVal : integer) return string is
begin
return to_string(intVal);
end function itoa;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_s
--
-- DESCRIPTION : This function multiplies an signed std_logic vector
-- value by another signed std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_s(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable negVar : std_logic;
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := abs(multiplicand);
multiplierVar := ext(abs(Multiplier),multiplierVar'length);
negVar := multiplier(multiplier'left) xor multiplicand(multiplicand'left);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
if (negVar = '1') then
return neg(resultVar);
else
return resultVar;
end if;
end mult_s;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : mult_us
--
-- DESCRIPTION : This function multiplies an unsigned std_logic vector
-- value by another unsigned std_logic_vector value
--
-- NOTES : This function is provided for in std_logic_arith
------------------------------------------------------------------------------
function mult_us(Multiplier : std_logic_vector;
Multiplicand : std_logic_vector) return std_logic_vector is
variable multiplicandVar : std_logic_vector(Multiplicand'length-1 downto 0);
variable multiplierVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
variable resultVar : std_logic_vector(Multiplier'length+Multiplicand'length-1 downto 0);
begin
multiplicandVar := multiplicand;
multiplierVar := ext(Multiplier,multiplierVar'length);
resultVar := (others => '0');
for loopVar in multiplicandVar'reverse_range loop
if (multiplicandVar(loopVar) = '1') then
resultVar := resultVar + multiplierVar;
end if;
multiplierVar := multiplierVar(multiplierVar'high-1 downto 0) & '0';
end loop;
return resultVar;
end mult_us;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : nat_to_slv (convert natural to std_logic_vector)
--
-- DESCRIPTION : This function converts a natural value to a
-- std_logic_vector with a range just large enough
-- to represent it
--
-- NOTES
--
------------------------------------------------------------------------------
function nat_to_slv(natVal : natural) return std_logic_vector is
begin
return conv_std_logic_vector(natVal,vlfn(natVal));
end nat_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : neg
--
-- DESCRIPTION : This function toggles the sign of the value passed
--
-- NOTES :
--
------------------------------------------------------------------------------
function neg(VectorVal : std_logic_vector) return std_logic_vector is
variable oneFndVar : boolean;
variable resultVar : std_logic_vector(VectorVal'length-1 downto 0);
begin
oneFndVar := false;
resultVar := VectorVal;
resultVar := not resultVar; -- invert all bits
resultVar := resultVar + '1'; -- then add one
return ResultVar;
end neg;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : now
--
-- DESCRIPTION : This function returns a string representation
-- of the current simulation time
--
-- NOTES :
--
------------------------------------------------------------------------------
-- synopsys translate_off
impure function now return string is
variable lineVar : line;
variable resultVar : string(1 to time'image(now)'length);
begin
--Std.TextIO.Write(lineVar, vectorVal);
Write(lineVar, time'image(now));
resultVar(lineVar.all'range) := lineVar.all;
deallocate(lineVar);
return resultVar;
end now;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce
--
-- DESCRIPTION : This function returns a vector with the extra sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
lengthVar := lengthVar + 1; -- And add one for the sign bit
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_unsigned
--
-- DESCRIPTION : This function returns a vector with all sign
-- bits removed
--
-- NOTES :
--
------------------------------------------------------------------------------
function reduce_unsigned(vectorVal : std_logic_vector) return std_logic_vector is
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
resultVar := vectorVal;
lengthVar := 0;
MSBFound := False;
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return resultVar(lengthVar downto 0); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end reduce_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_high_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the vector'high value of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
--
------------------------------------------------------------------------------
function reduce_high_unsigned(vectorVal : std_logic_vector) return integer is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable lengthVar : integer;
variable MSBFound : boolean;
variable resultVar : std_logic_vector(MAX_VECT_SIZE downto 0);
begin
interimVar := vectorVal;
lengthVar := 0;
MSBFound := False;
resultVar := sxt(interimVar,resultVar'length); -- sign extend the value passed to the size of the slv variable
for loopVar in resultVar'range loop -- start at the MSB of the vector and index down
if (((resultVar(resultVar'high) = '0' and resultVar(loopVar) = '1') or -- if it's a positive value then look for a bit to be '1'
(resultVar(resultVar'high) = '1' and resultVar(loopVar) = '0')) and -- or if it's a negative value look for a bit to be '0'
(MSBFound = False)) -- and the MSB hasn't been found yet
then -- and if a bit is asserted then
lengthVar := loopVar; -- this is the minimum number of bits needed to represent the absolute value.
MSBFound := True;
end if;
end loop;
return lengthVar;
end reduce_high_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length(vectorVal : std_logic_vector) return integer is
begin
return reduce_high(vectorVal) + 1;
end reduce_length;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : reduce_length_unsigned
--
-- DESCRIPTION : This function returns an integer value representing
-- the length of a sign bit reduced vector
--
-- NOTES : This function assumes that vectorVal'low = '0'
--
------------------------------------------------------------------------------
function reduce_length_unsigned(vectorVal : std_logic_vector) return integer is
begin
return reduce_high_unsigned(vectorVal) + 1;
end reduce_length_unsigned;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : seq (string equality function)
--
-- DESCRIPTION : This function returns true if both string values passed
-- are identical
--
-- NOTES : This function was added because the the synthesis tool
-- didn't support a boolean string equality operation test.
-- Also, adding a new overloaded operator "=" caused problems
-- with the simulator
--
------------------------------------------------------------------------------
function seq(str1Val : string;
str2Val : string) return boolean is
variable char1Var : character;
variable char2Var : character;
variable resultVar : boolean;
variable str1Var : string(1 to str1Val'length);
variable str2Var : string(1 to str2Val'length);
begin
resultVar := true;
str1Var := str1Val;
str2Var := str2Val;
for loopVar in str1Var'range loop
if (str1Var(loopVar) /= str2Var(loopVar)) then
resultVar := false;
end if;
end loop;
return resultVar;
end seq;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : shift
----
---- DESCRIPTION : This function returns a std_logic_vector shifted
---- by the number of integer places specified. This provides
---- an easy way to multiply or divide by 2^(natVal)
----
----
---- NOTES
----
--------------------------------------------------------------------------------
--function shift(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector is
-- variable resultVar : std_logic_vector(vectorVal'length-1 downto 0);
--begin
-- resultVar := vectorVal;
-- resultVar := (others => '0');
-- resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := resultVar;
-- return resultVar;
--end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : shl (shift left)
--
-- DESCRIPTION : This function returns a std_logic_vector shifted left
-- by the number of binary places specified. This provides
-- an easy way to multiply by 2^(natVal)
--
--
-- NOTES
--
------------------------------------------------------------------------------
function shl(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable interimVar : std_logic_vector(vectorVal'length-1 downto 0);
variable resultVar : std_logic_vector(vectorVal'length+natVal-1 downto 0);
begin
interimVar := vectorVal;
resultVar := (others => '0');
resultVar(resultVar'high downto resultVar'high-vectorVal'length+1) := interimVar;
return resultVar;
end shl;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- std logic vector value into a
-- packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number of BCD digits passed to the function.
--
-- NOTES
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
--
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector; BCD_DigitsVal : integer)
return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*BCD_DigitsVal-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed without carry from the current BCD value
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if the next BCD Digit is computed with carry from the current BCD value
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to BCD_DigitsVal-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector is
type resultArrayType is array(vectorVal'length downto 0) -- array depth is 1 level more than the input vector
of std_logic_vector(4*dpfslvr(vectorVal)-1 downto 0); -- array width is determined by the number of BCD digits to output
variable CarryVar : std_logic_vector
(dpfslvr(vectorVal) downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if no carry to the next BCD Digit is needed
variable BCD_WiCarVar : std_logic_vector(3 downto 0); -- BCD digit variable used by the inner loop if carry to the next BCD Digit is needed
variable InnrLoopVar : integer := 0; -- inner loop index variable
variable OutrLoopVar : integer := 0; -- outer loop index variable
variable ResultVar : resultArrayType; -- BCD value result variable
variable VectorVar : std_logic_vector(vectorVal'length-1 downto 0);
begin
VectorVar := vectorVal;
ResultVar(0) := (others => '0'); -- set the initial entry in the results array to zero
for OutrLoopVar in VectorVar'high downto 0 loop -- start at the MSB of the std logic vector input and work down
CarryVar(0) := VectorVar(OutrLoopVar); -- read in the next bit of the slv input into the lowest carry bit
for InnrLoopVar in 0 to CarryVar'high-1 loop -- start at the LSB of the BCD output
BCD_WoCarVar := ResultVar(VectorVar'length - OutrLoopVar -1) -- read the results of the previous calculation
(4*InnrLoopVar+3 downto 4*InnrLoopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101"; -- compute the result for the current BCD digit if a carry to the next digit will be needed
if (BCD_WoCarVar > "0100") then -- if the digit is 5 or greater ("0101") then the result of the binary shift left "10100" = decimal 16, which is to great to represent in one BCD digit so then
CarryVar(InnrLoopVar+1) := '1'; -- we carry a digit to the next BCD digit
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- and we use the lesser value for the current digit along with the carry value from the previous BCD digit
else -- otherwise the digit is small enough to be represented in one BCD digit when a binary shift in is performed
CarryVar(InnrLoopVar+1) := '0';
ResultVar(VectorVar'length - OutrLoopVar)
(4*InnrLoopVar+3 downto 4*InnrLoopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(InnrLoopVar); -- so we write the value to the result variable along with any carry value from a previous BCD digit
end if;
end loop;
end loop;
return ResultVar(VectorVar'high+1); -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd_pipe
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function slv_to_bcd_pipe(
BCD_RVal : std_logic_vector; -- registered output of this function fed back in
MSB_Val : std_logic; -- msb of binary value being shifted in
BCD_DigitsVal : integer) return std_logic_vector is -- binary coded decimal arithmetic shift left
variable BCDVar : std_logic_vector(BCD_RVal'length-1 downto 0);
variable CarryVar : std_logic_vector(BCD_DigitsVal downto 0); -- the # of carry bits is determined by the number of BCD digits
variable BCD_WoCarVar : std_logic_vector(3 downto 0);
variable BCD_WiCarVar : std_logic_vector(3 downto 0);
variable ResultVar : std_logic_vector(4*BCD_DigitsVal-1 downto 0);
begin
BCDVar := BCD_RVal;
for loopVar in 0 to BCD_DigitsVal-1 loop
CarryVar(0) := MSB_Val;
BCD_WoCarVar := BCDVar(4*loopVar+3 downto 4*loopVar);
BCD_WiCarVar := BCD_WoCarVar - "0101";
if (BCD_WoCarVar > "0100") then
CarryVar(loopVar+1) := '1';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WiCarVar(2 downto 0) & CarryVar(loopVar);
else
CarryVar(loopVar+1) := '0';
ResultVar(4*loopVar+3 downto 4*loopVar)
:= BCD_WoCarVar(2 downto 0) & CarryVar(loopVar);
end if;
end loop;
return ResultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end slv_to_bcd_pipe;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_int
--
-- DESCRIPTION : This function converts a string to an integer
--
-- NOTES :
--
------------------------------------------------------------------------------
function str_to_int(stringVal : string) return integer is
variable decPlace : integer := 1;
variable stringVar : string(1 to stringVal'length);
variable negVar : boolean; -- used to indicate whether or not the string represents a negative number
variable resultVar : integer;
variable vectorParseVar : character;
begin
negVar := false;
resultVar := 0;
stringVar := stringVal;
for loopVar in stringVar'range loop
vectorParseVar := stringVar(loopVar);
case vectorParseVar is
when '-' => negVar := true;
when '0' => resultVar := (resultVar * 10) + 0;
when '1' => resultVar := (resultVar * 10) + 1;
when '2' => resultVar := (resultVar * 10) + 2;
when '3' => resultVar := (resultVar * 10) + 3;
when '4' => resultVar := (resultVar * 10) + 4;
when '5' => resultVar := (resultVar * 10) + 5;
when '6' => resultVar := (resultVar * 10) + 6;
when '7' => resultVar := (resultVar * 10) + 7;
when '8' => resultVar := (resultVar * 10) + 8;
when '9' => resultVar := (resultVar * 10) + 9;
when '.' =>
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
when others => resultVar := resultVar;
end case;
end loop;
if (negVar) then -- ignore everything after a decimal point
return -resultVar;
else
return resultVar;
end if;
end str_to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_led
--
-- DESCRIPTION : This function converts a Seven Segment LED
-- string of any length to a std_logic_vector
--
-- NOTES : if the CAVal boolean input is true the output will
-- be for a Common Anode (1=off) display, otherwise it will
-- be for a Common Cathode (1=on)display.
--
-- _____
-- | a |
-- f| |b
-- |_____|
-- | g |
-- e| |c
-- |_____|
-- d
--
-- "width mismatch" errors here are due to improper sizing of the vector
-- that this function is assigned to
------------------------------------------------------------------------------
function str_to_led(stringVal : string;
CAVal : boolean) return std_logic_vector is
variable stringVar : string(stringVal'length downto 1);
variable resultVar : std_logic_vector(7*StringVal'length downto 1);
variable vectorParseVar : character;
begin
stringVar := stringVal;
for loopVar in StringVar'range loop
vectorParseVar := StringVar(loopVar);
case vectorParseVar is
-- Illuminated
-- character Segment
-- shown abcdefg
when ' ' => resultVar(7*loopVar downto 7*loopVar-6) := "0000000";
when '"' => resultVar(7*loopVar downto 7*loopVar-6) := "0100010";
when ''' => resultVar(7*loopVar downto 7*loopVar-6) := "0100000";
when '-' => resultVar(7*loopVar downto 7*loopVar-6) := "0000001";
when '/' => resultVar(7*loopVar downto 7*loopVar-6) := "0100101";
when '0' | 'D' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when '1' => resultVar(7*loopVar downto 7*loopVar-6) := "0110000";
when '2' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '3' => resultVar(7*loopVar downto 7*loopVar-6) := "1111001";
when '4' => resultVar(7*loopVar downto 7*loopVar-6) := "0110011";
when '5' | 'S' => resultVar(7*loopVar downto 7*loopVar-6) := "1011011";
when '6' => resultVar(7*loopVar downto 7*loopVar-6) := "1011111";
when '7' => resultVar(7*loopVar downto 7*loopVar-6) := "1110010";
when '8' | 'B' => resultVar(7*loopVar downto 7*loopVar-6) := "1111111";
when '9' => resultVar(7*loopVar downto 7*loopVar-6) := "1110011";
when '=' => resultVar(7*loopVar downto 7*loopVar-6) := "0001001";
when '?' => resultVar(7*loopVar downto 7*loopVar-6) := "1100101";
when 'A' => resultVar(7*loopVar downto 7*loopVar-6) := "1110111";
when 'C' => resultVar(7*loopVar downto 7*loopVar-6) := "1001110";
when 'E' => resultVar(7*loopVar downto 7*loopVar-6) := "1001111";
when 'F' => resultVar(7*loopVar downto 7*loopVar-6) := "1000111";
when 'G' => resultVar(7*loopVar downto 7*loopVar-6) := "1011110";
when 'H' => resultVar(7*loopVar downto 7*loopVar-6) := "0110111";
when 'I' => resultVar(7*loopVar downto 7*loopVar-6) := "0000110";
when 'J' => resultVar(7*loopVar downto 7*loopVar-6) := "1111100";
when 'L' => resultVar(7*loopVar downto 7*loopVar-6) := "0001110";
when 'O' => resultVar(7*loopVar downto 7*loopVar-6) := "1111110";
when 'P' => resultVar(7*loopVar downto 7*loopVar-6) := "1100111";
when 'T' => resultVar(7*loopVar downto 7*loopVar-6) := "1000110";
when 'U' => resultVar(7*loopVar downto 7*loopVar-6) := "0111110";
when 'Y' => resultVar(7*loopVar downto 7*loopVar-6) := "0100111";
when 'Z' => resultVar(7*loopVar downto 7*loopVar-6) := "1101101";
when '\' => resultVar(7*loopVar downto 7*loopVar-6) := "0010011";
when ']' => resultVar(7*loopVar downto 7*loopVar-6) := "1111000";
when '^' => resultVar(7*loopVar downto 7*loopVar-6) := "1100010";
when '_' => resultVar(7*loopVar downto 7*loopVar-6) := "0001000";
when 'b' => resultVar(7*loopVar downto 7*loopVar-6) := "0011111";
when 'c' => resultVar(7*loopVar downto 7*loopVar-6) := "0001101";
when 'd' => resultVar(7*loopVar downto 7*loopVar-6) := "0111101";
when 'g' => resultVar(7*loopVar downto 7*loopVar-6) := "1111011";
when 'h' => resultVar(7*loopVar downto 7*loopVar-6) := "0010111";
when 'j' => resultVar(7*loopVar downto 7*loopVar-6) := "0111100";
when 'l' => resultVar(7*loopVar downto 7*loopVar-6) := "0111000";
when 'n' => resultVar(7*loopVar downto 7*loopVar-6) := "0010101";
when 'o' => resultVar(7*loopVar downto 7*loopVar-6) := "0011101";
when 'r' => resultVar(7*loopVar downto 7*loopVar-6) := "0000101";
when 'u' => resultVar(7*loopVar downto 7*loopVar-6) := "0011100";
when '¬' => resultVar(7*loopVar downto 7*loopVar-6) := "0010001";
when '¯' => resultVar(7*loopVar downto 7*loopVar-6) := "1000000";
when '°' => resultVar(7*loopVar downto 7*loopVar-6) := "1100011";
when others =>
end case;
end loop;
if (CAVal) then
return not resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
else
return resultVar; -- "width mismatch" errors here are due to improper sizing of the vector that this function is assigned to
end if;
end str_to_led;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES :
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string) return std_logic_vector is
begin
return str_to_slv(stringVal,-15); -- default to 1fs time base
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_high(stringVal : string) return integer is
begin
return reduce_high(str_to_slv(stringVal));
end str_to_slv_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES : This function supports both positive and negative numbers
-- as well as positive and negative exponents. It supports
-- multiple time unit per string as long as there are no
-- exponents used.
--
-- Time units supported
--
-- 0.000 000 000 000 000 000 000 001 yoctosecond [ ys ] 10^(-24)
-- 0.000 000 000 000 000 000 001 zeptosecond [ zs ] 10^(-21)
-- 0.000 000 000 000 000 001 attosecond [ as ] 10^(-18)
-- 0.000 000 000 000 001 femtosecond [ fs ] 10^(-15)
-- 0.000 000 000 001 [ trillionth ] picosecond [ ps ] 10^(-12)
-- 0.000 000 001 [ billionth ] nanosecond [ ns ] 10^(-9)
-- 0.000 001 [ millionth ] microsecond [ µs ] 10^(-6)
-- 0.001 [ thousandth ] millisecond [ ms ] 10^(-3)
-- 0.01 [ hundredth ] centisecond [ cs ] 10^(-2)
-- 1.0 second [ s ] 10^(0)
-- 60.0 minute [ min ] 10^(0)
-- 3600.0 hour [ hr ] 10^(0)
-- 86,400.0 day [ day ] 10^(0)
--
--
-- Frequency units supported
--
-- 1 hertz [ hz ] 10^(0)
-- 1,000 kilohertz [ khz ] 10^(3)
-- 1,000,000 megahertz [ mhz ] 10^(6)
-- 1,000,000,000 gigahertz [ ghz ] 10^(9)
-- 1,000,000,000,000 terahertz [ thz ] 10^(12)
-- 1,000,000,000,000,000 petahertz [ phz ] 10^(15)
-- 1,000,000,000,000,000,000 exahertz [ ehz ] 10^(18)
-- 1,000,000,000,000,000,000,000 zetahertz [ zhz ] 10^(21)
-- 1,000,000,000,000,000,000,000,000 yottahertz [ yhz ] 10^(24)
--
-- EXAMPLE "1 day, 3 hrs, 15.298 seconds"
-- "66,000,000 Hz" "66,000,000.000 Hz" "66 MHz" "66E6 Hz" "66E+6 Hz" "66.000E+6 Hz"
-- "66,000,000 us" "66,000,000.000 us" "66 us" "66E6 us" "66E+6 us" "66.000E+6 us"
--
--
------------------------------------------------------------------------------
function str_to_slv(stringVal : string;
intVal : integer) return std_logic_vector is
constant \10\ : std_logic_vector(3 downto 0) := "1010"; -- 10
constant \60\ : std_logic_vector(5 downto 0) := "111100"; -- 60
constant \3600\ : std_logic_vector(11 downto 0) := "111000010000"; -- 3600
constant \86400\ : std_logic_vector(16 downto 0) := "10101000110000000"; -- 86,400 (solar day)
variable baseVar : integer; -- exponent of the timebase i.e. 1fs = 1E-15 seconds so the timebase = 15
variable decPlacesVar : integer; -- used to count how many numbers are after the decimal point
variable decPntFndVar : boolean; -- used to flag whether or not a decimal point was found in the string
variable expFndVar : boolean; -- used to flag that the exponent has been reached so that the rest of the string value will not be interpreted as part of the base value
variable expVar : integer; -- used to indicated the exponent value
variable freqUnitFndVar : boolean; -- used to flag whether or not the string represents a frequency
variable negVar : boolean; -- used to flag whether or not the string represents a negative number
variable resultVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable result2Var : std_logic_vector(MAX_VECT_SIZE+16 downto 0); -- used to store a result from a secondary value such as would be encounter when a value such as "1 hr 10 mins" is passed to the function
variable scndTimeFndVar : boolean; -- used to indicate a second time value was found
variable stringVar : string(1 to stringVal'length+4); -- slightly larger because string is addessed beyond the current loop to test for units
variable timeBaseVar : std_logic_vector(MAX_VECT_SIZE+16 downto 0);
variable timeUnitFndVar : boolean; -- used to flag that a time unit was found (days, hrs, mins, secs)
variable vectorParseVar : character; -- character currently under test
begin
baseVar := -intVal;
decPntFndVar := false; -- initialize to decimal point not found yet
decPlacesVar := 0;
expFndVar := false; -- initialize to exponent point not found yet
expVar := 0;
freqUnitFndVar := false; -- initialize to frequency units not found yet
negVar := false; -- initialize to negative sign not found yet
resultVar := (others => '0');
result2Var := (others => '0');
scndTimeFndVar := false; -- initialize to secont time value not found yet
stringVar := stringVal & " "; -- tack on few extra spaces for padding so that it is possible to address beyond the current loop variable
timeUnitFndVar := false;
timeBaseVar := ext("01",timeBaseVar'length);
for loopVar in 1 to baseVar loop
timeBaseVar := mult_us(timeBaseVar(MAX_VECT_SIZE+12 downto 0), \10\); -- this value will contain the time base (in binary) when this loop completes (10^30 for a baseVar of 30)
end loop;
for loopVar in stringVar'range loop -- this loop parses the string value passed to this function from left to right
vectorParseVar := stringVar(loopVar);
if (scndTimeFndVar) then
resultVar := resultVar; -- if a second value has been found then just wait here for the loop to complete
else
case vectorParseVar is
when '-' =>
if (not decPntFndvar and not expFndVar and not freqUnitFndVar and not timeUnitFndVar) then -- expect the sign to be near the front of the string
negVar := true;
end if;
when '0' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then -- if the decimal point was found and we're not reading an exponent then
decPlacesVar := decPlacesVar + 1; -- consider this to be a number after the decimal point
end if;
if (not expFndVar) then -- if we are not reading the exponent then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 0; -- factor in the next digit
end if;
end if;
when '1' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 1;
end if;
end if;
when '2' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 2;
end if;
end if;
when '3' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 3;
end if;
end if;
when '4' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 4;
end if;
end if;
when '5' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 5;
end if;
end if;
when '6' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 6;
end if;
end if;
when '7' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 7;
end if;
end if;
when '8' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 8;
end if;
end if;
when '9' =>
if (freqUnitFndVar) then
resultVar := resultVar; -- do nothing
elsif (timeUnitFndVar) then -- if we've already found a time unit then this must be a second time value
result2Var := ext(str_to_slv(stringVar(loopVar to stringVar'length),intVal),result2Var'length); -- pass the rest of the string to the next instance of the function
scndTimeFndVar := true;
else
if (decPntFndVar and not expFndVar) then
decPlacesVar := decPlacesVar + 1;
end if;
if (not expFndVar) then
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\) + 9;
end if;
end if;
when 'e' | 'E' => -- exponent
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- exahertz unit found
for loopVar in 1 to 18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not expFndVar and not freqUnitFndVar and not timeUnitFndVar) -- if we haven't already found an exponent, frequency unit, or time unit
then
expFndVar := true; -- mark that we've found it
expVar := str_to_int(stringVar(loopVar to stringVal'length)); -- and capture its value
end if;
when '.' => decPntFndVar := true; -- mark the position of the decimal point
when 'y' | 'Y' => -- yoctosecond 10^-24
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- yoctosecond unit found
for loopVar in 1 to baseVar-24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- yottahertz unit found
for loopVar in 1 to 24 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'z' | 'Z' => -- zeptosecond 10^-21
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- zeptosecond unit found
for loopVar in 1 to baseVar-21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- zettahertz unit found
for loopVar in 1 to 21 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'a' | 'A' => -- attosecond 10^-18
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- attosecond unit found
for loopVar in 1 to baseVar-18 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'f' | 'F' => -- femtosecond 10^-15
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- femtosecond unit found
for loopVar in 1 to baseVar-15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'p' | 'P' => -- picosecond 10^-12
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- picosecond unit found
for loopVar in 1 to baseVar-12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- petahertz unit found
for loopVar in 1 to 15 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'n' | 'N' => -- nanosecond 10^-9
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- nanosecond unit found
for loopVar in 1 to baseVar-9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'u' | 'U' => -- microsecond 10^-6
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- microsecond unit found
for loopVar in 1 to baseVar-6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'm' | 'M' => -- millisecond 10^-3
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 's') or
(stringVar(loopVar+1) = 'S')))
then
timeUnitFndVar := true; -- millisecond unit found
for loopVar in 1 to baseVar-3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "in")) or
(seq(stringVar(loopVar+1 to loopVar+2), "iN")) or
(seq(stringVar(loopVar+1 to loopVar+2), "In")) or
(seq(stringVar(loopVar+1 to loopVar+2), "IN"))))
then
timeUnitFndVar := true; -- minute unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+10 downto 0), \60\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- megahertz unit found
for loopVar in 1 to 6 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 's' | 'S' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "eC")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ec")) or
(seq(stringVar(loopVar+1 to loopVar+2), "EC"))))
then
timeUnitFndVar := true; -- second unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'h' | 'H' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'r') or
(stringVar(loopVar+1) = 'R')))
then
timeUnitFndVar := true; -- hour unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE+4 downto 0), \3600\);
elsif (not freqUnitFndVar and not timeUnitFndVar and
((stringVar(loopVar+1) = 'z') or
(stringVar(loopVar+1) = 'Z')))
then
freqUnitFndVar := true;
end if;
when 'd' | 'D' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "aY")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Ay")) or
(seq(stringVar(loopVar+1 to loopVar+2), "AY"))))
then
timeUnitFndVar := true; -- day unit found
for loopVar in 1 to baseVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
resultVar := mult_us(resultVar(MAX_VECT_SIZE-1 downto 0), \86400\);
end if;
when 'g' | 'G' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- gigahertz unit found
for loopVar in 1 to 9 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 'k' | 'K' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- kilohertz unit found
for loopVar in 1 to 3 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when 't' | 'T' =>
if (not freqUnitFndVar and not timeUnitFndVar and
((seq(stringVar(loopVar+1 to loopVar+2), "hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "hZ")) or
(seq(stringVar(loopVar+1 to loopVar+2), "Hz")) or
(seq(stringVar(loopVar+1 to loopVar+2), "HZ"))))
then
freqUnitFndVar := true; -- terahertz unit found
for loopVar in 1 to 12 loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
end if;
when others =>
end case;
end if;
end loop;
if (expVar >= 0) then -- if it's a positive exponent then perform a multiplication loop
for loopVar in 1 to expVar loop
resultVar := mult_us(resultVar(MAX_VECT_SIZE+12 downto 0), \10\);
end loop;
else -- if it's a negative exponent then perform a division loop
for loopVar in 1 to (-expVar) loop
resultVar := resultVar / \10\;
end loop;
end if;
if (decPntFndVar) then -- if a decimal point was present in the value then
for loopVar in 1 to decPlacesVar loop -- scale the output accordingly
resultVar := resultVar / \10\;
end loop;
end if;
resultVar := resultVar + result2Var; -- add on any secondary value
if (freqUnitFndVar) then -- the the string is a frequency value then
resultVar := timeBaseVar / resultVar; -- invert it to convert it to a period value before returning
end if;
if (negVar and not timeUnitFndVar) then -- the the string is a negative value and its not a time value then
resultVar := neg(resultVar); -- negate the result
end if;
return reduce(resultVar);
end str_to_slv;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : str_to_slv_var_base_high
--
-- DESCRIPTION : This function converts an integer value string
-- of any length to a std_logic_vector
--
-- NOTES
--
--
------------------------------------------------------------------------------
function str_to_slv_var_base_high(stringVal : string;
intVal : integer) return integer is
begin
return reduce_high(str_to_slv(stringVal,intVal));
end str_to_slv_var_base_high;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : strh
--
-- DESCRIPTION : This function returns the high value of a sring vector
--
--
-- NOTES
--
--
------------------------------------------------------------------------------
function strh(stringVal : string) return integer is
begin
return stringVal'high;
end strh;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : sxt2 (sign extend)
--
-- DESCRIPTION : This function returns a standard logic vector,
-- padded with zeros, to the length specified by intVal
--
-- NOTES :
--
------------------------------------------------------------------------------
function sxt2(vectorVal : std_logic_vector;
natVal : natural) return std_logic_vector is
variable zeroVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '0');
variable oneVar : slv (natVal - vectorVal'length - 1 downto 0) := (others => '1');
variable vectorVar : slv (vectorVal'length - 1 downto 0);
begin
vectorVar := vectorVal;
if (vectorVar(vectorVar'high) = '1') then
if (vectorVar'length >= natVal) then
return vectorVar;
else
return oneVar & vectorVar;
end if;
else
if (vectorVar'length >= natVal) then
return vectorVar;
else
return zeroVar & vectorVar;
end if;
end if;

end sxt2;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_int
--
-- DESCRIPTION : conv_integer function repackaged
--
-- NOTES
--
------------------------------------------------------------------------------
function to_int(vectorVal : std_logic_vector) return integer is
begin
return conv_integer(vectorVal);
end to_int;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_period
--
-- DESCRIPTION : This function returns a one cycle period value for
-- a given frequency
--
-- NOTES timeVar must be larger than the simulator resolution
-- and is limited by the integer that can be created from
-- time'pos of it's value
--
-- the funtion does not work with Synplify 7.7
------------------------------------------------------------------------------
--function to_period(freqVal : frequency) return time is
-- variable resultVar : time;
--begin
-- resultVar := 1E9/frequency'pos(freqVal) * 1 ns; -- max of 2147.483647 ns for Precision Synthesis
-- return resultVar;
--end to_period;


--synopsys translate_on
function to_period(freqVal : frequency) return time is
variable resultVar : time;
variable timeVar : time := 1 ms;
variable divVar : real := real(1 sec/timeVar);
begin
if (frequency'pos(freqVal) > 2_147_483_647) then
assert FALSE
report "Frequency value passed to function is greater than 2,147,483,647 when converted to base units."
severity warning;
end if;
resultVar := divVar/real(frequency'pos(freqVal)) * timeVar; -- see "NOTES"
return resultVar;
end to_period;
--synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (integer)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
------ synopsys translate_off
--function to_string(intVal : integer) return string is
-- variable lineVar : line;
-- variable resultVar : string(1 to cfi(intVal));
--begin
-- --Std.TextIO.Write(lineVar, intVal);
-- Write(lineVar, integer'Image(intVal));
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
------ synopsys translate_on


function to_string(intVal : integer) return string is
begin
return integer'Image(intVal);
end to_string;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (real)
--
-- DESCRIPTION : This function returns a string value representing the
-- integer value passed to it.
-- NOTES
--
------------------------------------------------------------------------------
---- synopsys translate_off
--function to_string(realVal : real) return string is
-- variable lengthVar : natural;
-- variable lineVar : line;
-- variable resultVar : string(1 to real'Image(realVal)'length);
--begin
-- --Std.TextIO.Write(lineVar, intVal);
-- Write(lineVar, real'Image(realVal));
-- lengthVar := lineVar.all'length;
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
---- synopsys translate_on


function to_string(realVal : real) return string is
begin
return real'Image(realVal);
end to_string;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (time)
--
-- DESCRIPTION : This function returns a string value representing the
-- time value passed to it.
--
-- NOTES :
--
------------------------------------------------------------------------------
---- synopsys translate_off
--function to_string(timeVal : time) return string is
-- variable lineVar : line;
-- variable resultVar : string(1 to time'image(timeVal)'length);
--begin
-- --Std.TextIO.Write(lineVar, vectorVal);
-- Write(lineVar, time'image(timeVal));
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
---- synopsys translate_on

function to_string(timeVal : time) return string is
begin
return time'image(timeVal);
end to_string;



------------------------------------------------------------------------------
--
-- FUNCTION NAME : to_string (vector)
--
-- DESCRIPTION : This function returns a string value representing the
-- vector value passed to it.
-- NOTES
--
-- 'U', -- Uninitialized
-- 'X', -- Forcing Unknown
-- '0', -- Forcing 0
-- '1', -- Forcing 1
-- 'Z', -- High Impedance
-- 'W', -- Weak Unknown
-- 'L', -- Weak 0
-- 'H', -- Weak 1
-- '-' -- Don't care
------------------------------------------------------------------------------
-- synthesis tool un-friendly version
---- synopsys translate_off
--function to_string(vectorVal : std_logic_vector) return string is
-- variable lineVar : line;
-- variable resultVar : string(1 to vectorVal'length);
--begin
-- --Std.TextIO.Write(lineVar, vectorVal);
-- Write(lineVar, vectorVal);
-- resultVar(lineVar.all'range) := lineVar.all;
-- deallocate(lineVar);
-- return resultVar;
--end to_string;
---- synopsys translate_on

-- synthesis tool friendly version
function to_string(vectorVal : std_logic_vector) return string is
variable lineVar : line;
variable resultVar : string(1 to vectorVal'length);
variable vectorVar : std_logic_vector(1 to vectorVal'length);
begin
vectorVar := vectorVal;
for loopVar in vectorVar'range loop
if (vectorVar(loopVar) = 'U') then -- 'U', -- Uninitialized
resultVar(loopVar) := 'U';
elsif (vectorVar(loopVar) = 'X') then -- 'X', -- Forcing Unknown
resultVar(loopVar) := 'X';
elsif (vectorVar(loopVar) = '0') then -- '0', -- Forcing 0
resultVar(loopVar) := '0';
elsif (vectorVar(loopVar) = '1') then -- '1', -- Forcing 1
resultVar(loopVar) := '1';
elsif (vectorVar(loopVar) = 'Z') then -- 'Z', -- High Impedance
resultVar(loopVar) := 'Z';
elsif (vectorVar(loopVar) = 'W') then -- 'W', -- Weak Unknown
resultVar(loopVar) := 'W';
elsif (vectorVar(loopVar) = 'L') then -- 'L', -- Weak 0
resultVar(loopVar) := 'L';
elsif (vectorVar(loopVar) = 'H') then -- 'H', -- Weak 1
resultVar(loopVar) := 'H';
elsif (vectorVar(loopVar) = '-') then -- '-' -- Don't care
resultVar(loopVar) := '-';
end if;
end loop;
return resultVar;
end to_string;


--------------------------------------------------------------------------------
----
---- PROCEDURE NAME : transpose
----
---- DESCRIPTION : This procedure returns the transpose of an array
----
---- NOTES : column 1 -> row 1
---- column 2 -> row 2
----
--------------------------------------------------------------------------------
--procedure( transpose(arrayVal : array_type) return array_type is
-- variable resultVar : std_ulogic_vector(vectorVal'range);
--begin
-- for loopVar in vectorVal'low to vectorVal'high loop
-- resultVar(resultVar'high-loopVar) := vectorVal(loopVar);
-- end loop;
-- return resultVar;
--end transpose;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfi (vector high for integer)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the integer value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfi for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfi(intVal : integer) return natural is
begin
return vlfi(intVal) - 1;
end vhfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vhfn (vector high for natural)
--
-- DESCRIPTION : This function returns the 'high value to be used
-- in the range declaration of a vector used to
-- represent the natural value passed to it.
--
-- WARNING: This function assumes the rest of the
-- range declaration of the vector
-- will be "downto 0"
--
-- NOTES : see vlfn for more information
--
-- EXAMPLE :
------------------------------------------------------------------------------
function vhfn(natVal : natural) return natural is
begin
return vlfn(natVal) - 1;
end vhfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfi (vector length for integer)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the integer value passed to it. This includes
-- the sign bit; hence the "resultVar := loopVar + 1;"
--
-- NOTES : type integer is range -2147483648 to 2147483647;
-- This function can be used in code intended for synthesis
-- Using a 31 bit variable strips off the sign bit that
-- the conversion function generates. This allows us
-- to place the sign bit in the new location at the top
-- of the vector.
--
-- EXAMPLE : -2147483648 passed, convertion to logic vector gives
-- 0000000000000000000000000000000. Bit 31 is '0' and
-- a sign bit is needed so 31 + 1 = 32 bits are needed to
-- represent this value
--
-- given intVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 7 (6 bits to represent 32, plus the sign bit)
------------------------------------------------------------------------------
function vlfi(intVal : integer) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1); -- range of 31 downto 1 used because the numbering is correct for the positional location of the bits
begin
slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
if (intVal > 0) then -- if the integer is positive then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
return 1;
elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
return 2;
elsif (intVal < -1) then -- if the integer is negative then
for loopVar in slvVar'range loop -- start at the top of the vector and index down
if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
return loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
end if;
end loop;
end if;
return resultVar;
end vlfi;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vlfn (vector length for natural)
--
-- DESCRIPTION : This function returns an integer representing the
-- length of the vector required to represent
-- the natural value passed to it. There is no
-- sign bit needed so "resultVar := loopVar;"
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
-- EXAMPLE : given natVal = 32
-- slvVar is assigned 0000000000000000000000000100000
-- "if" condition becomes true for loopVar = 6
-- result is 6 (6 bits to represent 32, no sign bit needed)
------------------------------------------------------------------------------
function vlfn(natVal : natural) return natural is
variable resultVar : natural;
variable slvVar : std_logic_vector(31 downto 1);
begin
slvVar := conv_std_logic_vector(natVal,slvVar'length);
if (natVal > 2_147_483_647) then
assert false
report "value exceeds 2,147,483,647"
severity warning;
return 0;
elsif (natVal > 0) then
for loopVar in slvVar'range loop
if (slvVar(loopVar) = '1') then
return loopVar;
end if;
end loop;
else
return 1;
end if;
end vlfn;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfi (vector range for integer)
--
-- DESCRIPTION : This function returns a std_logic_vector of the same range
-- required to represent the integer value passed to it.
-- This includes the sign bit;
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfi(intVal : integer) return std_logic_vector is
variable slvVar : std_logic_vector(vhfi(intVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfi;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfi (vector range for integer)
----
---- DESCRIPTION : This function returns a std_logic_vector of the same range
---- required to represent the integer value passed to it.
---- This includes the sign bit;
---- hence the "resultVar := loopVar + 1;"
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfi(intVal : integer) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(intVal,slvVar'length); -- convert the integer passed to the function to a 31 bit logic vector
-- if (intVal > 0) then -- if the integer is positive then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '1') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- elsif (intVal = 0) then -- '0' has no value and, therefore, needs no sign bit
-- resultVar := 1;
-- elsif (intVal = -1) then -- '-1' is a special case which contains no zeros so the following algorithm would fail.
-- resultVar := 2;
-- elsif (intVal < -1) then -- if the integer is negative then
-- for loopVar in slvVar'range loop -- start at the top of the vector and index down
-- if (slvVar(loopVar) = '0') then -- and if a bit is asserted then
-- resultVar := loopVar + 1; -- this is the minimum number of bits needed to represent the absolute value. And then add one for the sign bit
-- exit;
-- end if;
-- end loop;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
---- return size.all'range;
-- return size.all;
-- deallocate(size);
--end vrfi;
---- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : vrfn (vector range for natural)
--
-- DESCRIPTION : This function returns an std_logic_vector representing the
-- length of the vector required to represent
-- the natural value passed to it.
--
-- NOTES : subtype natural is integer range 0 to 2_147_483_647;
-- This function can be used in code intended for synthesis
--
------------------------------------------------------------------------------
function vrfn(natVal : natural) return std_logic_vector is
variable slvVar : std_logic_vector(vhfn(natVal) downto 0);
attribute slv_high : natural;
attribute slv_low : natural;
attribute slv_range : natural;
attribute slv_high of slvVar : variable is slvVar'high;
attribute slv_low of slvVar : variable is slvVar'low;
--attribute slv_range of slvVar : variable is slvVar'range;
begin
return slvVar;
end vrfn;


--------------------------------------------------------------------------------
----
---- FUNCTION NAME : vrfn (vector range for natural)
----
---- DESCRIPTION : This function returns an std_logic_vector representing the
---- length of the vector required to represent
---- the natural value passed to it.
----
---- NOTES : subtype natural is integer range 0 to 2_147_483_647;
---- This function cannot be used in code intended for synthesis
----
--------------------------------------------------------------------------------
---- synopsys translate_off
--function vrfn(natVal : natural) return std_logic_vector is
-- type slv_ptr is access std_logic_vector;
-- variable size : slv_ptr;
-- variable resultVar : natural;
-- variable slvVar : std_logic_vector(31 downto 1);
--begin
-- slvVar := conv_std_logic_vector(natVal,slvVar'length);
-- if (natVal > 0) then
-- for loopVar in slvVar'range loop
-- if (slvVar(loopVar) = '1') then
-- resultVar := loopVar;
-- exit;
-- end if;
-- end loop;
-- else
-- resultVar := 1;
-- end if;
-- size := new std_logic_vector(resultVar-1 downto 0);
-- return size.all;
-- deallocate(size);
--end vrfn;
---- synopsys translate_on










------------------------------------------------------------------------------
--
-- Procedures
--
------------------------------------------------------------------------------


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
constant clkFreqSig : in frequency;
signal clkSig : out std_logic) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while true loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a 50% duty cycle clock with the specified
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
signal clkSig : out std_logic) is
variable posPeriodVar : time := (to_period(clkFreqSig) * 50.0) / 100;
variable negPeriodVar : time := to_period(clkFreqSig) - posPeriodVar;
begin
while clkEnSig loop
clkSig <= '1';
wait for posPeriodVar;
clkSig <= '0';
wait for negPeriodVar;
end loop;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkPeriodSig : in time;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (clkPeriodSig * clkDutySig) / 100;
negPeriodVar := clkPeriodSig - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- PROCEDURE NAME : clock_gen
--
-- DESCRIPTION : generate a clock
--
-- NOTES
--
------------------------------------------------------------------------------
-- synopsys translate_off
procedure clkgen(
signal clkEnSig : in boolean;
signal clkFreqSig : in frequency;
constant clkDutySig : in real;
signal clkResetSig : in boolean;
signal clkSig : inout std_logic) is
variable posPeriodVar : time;
variable negPeriodVar : time;
begin
posPeriodVar := (to_period(clkFreqSig) * clkDutySig) / 100;
negPeriodVar := to_period(clkFreqSig) - posPeriodVar;
if (clkResetSig)
then
clkSig <= '1';
elsif (clkEnSig)
then
if (clkSig = '1')
then
clkSig <= '0' after posPeriodVar;
else
clkSig <= '1' after negPeriodVar;
end if;
end if;
end clkgen;
-- synopsys translate_on


------------------------------------------------------------------------------
--
-- FUNCTION NAME : FF
--
-- DESCRIPTION : simple flip flop procedure
--
-- NOTES : synthesizeable
--
------------------------------------------------------------------------------
procedure FF
(
signal Clk : in std_logic;
signal Rst : in std_logic;
signal D : in std_logic_vector;
signal Q : out std_logic_vector) is
variable zeros : std_logic_vector(Q'range) := (others => '0');
begin
if (Rst = '1') then
Q <= zeros;
elsif Rising_Edge(Clk) then
Q <= D;
end if;
end FF;


------------------------------------------------------------------------------
--
-- FUNCTION NAME : slv_to_bcd
--
-- DESCRIPTION : This function converts an unsigned, decending range,
-- binary value into a packed binary coded decimal (BCD)
-- standard logic vector and returns the result in
-- the number BCD digits required to represent the maximum
-- unsigned value possible in the vector passed to it.
-- it is for use in pipelined implementations where
-- the binary coded decimal output is registered
-- and passed back to the function along with the binary
-- vector input to be shifted out of its MSB
-- register and into the function as a new bit.
--
--
-- NOTES
-- BCD_DigitsVal -> dpfslvr(vectorVal)
------------------------------------------------------------------------------
procedure slv_to_bcd(
signal BCD_RIn : in std_logic_vector;
signal BinIn : in std_logic_vector;
signal BinFBIn : in std_logic_vector;
signal ClkIn : in std_logic;
constant BCD_DigitsVal : in integer;
signal EnIn : in std_logic;
signal RstLowIn : in std_logic;
signal BCD_ROut : out std_logic_vector;
signal Bin_ROut : out std_logic_vector; -- registed, shifted version of BinIn
signal DoneOut : out std_logic) is
constant BCD_ZEROS : std_logic_vector(BCD_ROut'range) := (others => '0');
constant BIN_ZEROS : std_logic_vector(BinIn'range) := (others => '0');
variable BCD_Var : std_logic_vector(BCD_ROut'range);
variable BCD_RVar : std_logic_vector(BCD_ROut'range);
begin
if (RstLowIn = '0' or EnIn = '0') then
BCD_ROut <= BCD_ZEROS;
BCD_RVar := BIN_ZEROS;
Bin_ROut <= BinIn;
DoneOut <= '0';
elsif rising_edge(ClkIn) then
Bin_ROut <= BinFBIn(BinFBIn'high-1 downto BinFBIn'low) & '0';
if (BinFBIn = BIN_ZEROS) then
BCD_ROut <= BCD_RIn;
DoneOut <= '1';
else
BCD_ROut <= slv_to_bcd_pipe(BCD_RIn,BinFBIn(BinFBIn'high),BCD_DigitsVal);
DoneOut <= '0';
end if;
end if;
end slv_to_bcd;


------------------------------------------------------------------------------
end extension_pack;
------------------------------------------------------------------------------
















-- end of extension pack
-- start of test bench























































-- synopsys translate_off



------------------------------------------------------------------------------
-- Extension Pack test bench
------------------------------------------------------------------------------

library ieee, extension_lib;
use ieee.std_logic_1164.all;
use ieee.std_logic_unsigned.all;
use ieee.std_logic_arith.all;
use extension_lib.extension_pack.all;
use ieee.std_logic_textio.all;
use std.textio.all;

entity extension_pack_tb is
end extension_pack_tb;


------------------------------------------------------------------------------
architecture behavioral of extension_pack_tb is
------------------------------------------------------------------------------


------------------------------------------------------------------------------
-- Global Component/Function/Procedure Declarations
------------------------------------------------------------------------------
begin


star_operator_test : process
variable slvVar : slv(2 downto 0) := "111";
begin

assert (7*slvVar = "0110001") -- 7*7 = 49
report "* error # 1 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(7*slvVar) & " : actual"
severity error;

assert (slvVar*7 = "0110001") -- 7*7 = 49
report "* error # 2 " & LF &
to_string("0110001") & " : expected" & LF &
to_string(slvVar*7) & " : actual"
severity error;

wait;
end process;




--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : std_logic_vector) return std_logic_vector;
slash1_operator_test : process
constant slvVar : slv := "0110001";
begin

assert ("0110001"/"111" = "0000111") -- 49/7 = 7
report "slash1_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string("0110001"/"111") & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : std_logic_vector;
-- DivisorVal : integer) return std_logic_vector;
slash2_operator_test : process
constant slvVar : slv := "0110001";
begin

assert (slvVar/7 = "0000111") -- 49/7 = 7
report "slash2_operator_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(slvVar/7) & " : actual"
severity error;

wait;
end process;



--function "/"(DividendVal : string;
-- DivisorVal : integer) return std_logic_vector;
slash3_operator_test : process
constant var : string := "49";
begin

assert (var/7 = "0000111") -- 49/7 = 7
report "slash3_operator_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(var/7) & " : actual"
severity error;

wait;
end process;



--function bcd_to_led(slvVal : std_logic_vector ;
-- CAVal : boolean) return std_logic_vector; -- binary coded decimal to seven segment LED conversion
bcd_to_led1_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_led(slvVar,true) = "0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") -- 123456789ABCDEF =
report "bcd_to_led_test error # 1 " & LF &
to_string("0000001100111100100100000110100110001001000100000000110100000000001100111011100111111001110011110110011111000111") & " : expected" & LF &
to_string(bcd_to_led(slvVar,true)) & " : actual"
severity error;

assert (bcd_to_led(slvVar,false) = "1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") -- 123456789ABCDEF =
report "bcd_to_led_test error # 2 " & LF &
to_string("1111110011000011011011111001011001110110111011111111001011111111110011000100011000000110001100001001100000111000") & " : expected" & LF &
to_string(bcd_to_led(slvVar,false)) & " : actual"
severity error;

wait;
end process;







--function bcd_to_slv(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed
bcd_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bcd_to_slv(slvVar) = "011100000100100010000110000111101101001110111111") -- 123456789ABCDEF = 123456790123455
report "bcd_to_slv_test error # 1 " & LF &
to_string("011100000100100010000110000111101101001110111111") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("00000001001000110100010101100111100010010000") = "01001001100101100000001011010010") -- 1234567890 =
report "bcd_to_slv_test error # 2 " & LF &
to_string("01001001100101100000001011010010") & " : expected" & LF &
to_string(bcd_to_slv(slvVar)) & " : actual"
severity error;

assert (bcd_to_slv("101010111100110111101111") = "100010010010001111111") -- ABCDEF (1123455)
report "bcd_to_slv_test error # 3 " & LF &
to_string("100010010010001111111") & " : expected" & LF &
to_string(bcd_to_slv("101010111100110111101111")) & " : actual"
severity error;


wait;
end process;


--function bcd_to_slv_pipe(BCD_RVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value




--function bv_to_slv(bitVectVal : bit_vector) return std_logic_vector; -- repackaging of "To_StdLogicVector" function
bv_to_slv_test : process
constant bvVar : bv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (bv_to_slv(bvVar) = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 1 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(bvVar)) & " : actual"
severity error;

assert (bv_to_slv(X"123456789ABCDEF") = "0000000100100011010001010110011110001001101010111100110111101111") -- 123456789ABCDEF = 123456790123455
report "bv_to_slv_test error # 2 " & LF &
to_string("0000000100100011010001010110011110001001101010111100110111101111") & " : expected" & LF &
to_string(bv_to_slv(X"123456789ABCDEF")) & " : actual"
severity error;

wait;
end process;


--function cdft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdft("8 ms ","1 kHz") = slvVar)
report "count_down_for_time2_test error # 1 " & LF &
to_string("0111") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz")) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz")) = "0110")
report "count_down_for_time2_test error # 2 " & LF &
to_string("0110") & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))) & " : actual"
severity error;

assert (cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length = 4)
report "count_down_for_time2_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(cdft("8 ms ","1 kHz",cdfth("8 ms ","1 kHz"))'length) & " : actual"
severity error;

wait;
end process;




--function cdfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high_test : process
begin

assert (cdfth("1 us ","1E-15 yHz") = 10)
report "count_down_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cdfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;

--function cdfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_down_for_time_high2_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cdfth("8 ms ","1 kHz") = 3)
report "count_down_for_time_high_test2 error # 1 " & LF &
to_string(3) & " : expected" & LF &
to_string(cdfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;





--function ceil(RealVal : in real ) return real; -- rounds a real value up the the next highest real integer
ceil_test : process
begin

assert (ceil(-9.999999) = -9.0)
report "ceil_test error # 1 " & LF &
to_string(-9.0) & " : expected" & LF &
to_string(ceil(-9.999999)) & " : actual"
severity error;

assert (ceil(9.999999) = 10.0)
report "ceil_test error # 2 " & LF &
to_string(10.0) & " : expected" & LF &
to_string(ceil(9.999999)) & " : actual"
severity error;

wait;
end process;



--function cfi(intVal : integer) return natural;
cfi_test : process
begin

assert (cfi(-1000) = 5)
report "cfi_test error # 1 " & LF &
"5 : expected" & LF &
to_string(cfi(-1000)) & " : actual"
severity error;

assert (cfi(-10000) = 6)
report "cfi_test error # 2 " & LF &
"6 : expected" & LF &
to_string(cfi(-10000)) & " : actual"
severity error;


assert (cfi(1000) = 4)
report "cfi_test error # 3 " & LF &
"4 : expected" & LF &
to_string(cfi(1000)) & " : actual"
severity error;


assert (cfi(-100_000) = 7)
report "cfi_test error # 4 " & LF &
"7 : expected" & LF &
to_string(cfi(-100_000)) & " : actual"
severity error;


assert (cfi(100_000) = 6)
report "cfi_test error # 5 " & LF &
"6 : expected" & LF &
to_string(cfi(100_000)) & " : actual"
severity error;

assert (cfi(-9999999) = 8)
report "cfi_test error # 6 " & LF &
to_string(8) & " : expected" & LF &
to_string(cfi(-9999999)) & " : actual"
severity error;

assert (cfi(9999999) = 7)
report "cfi_test error # 7 " & LF &
to_string(7) & " : expected" & LF &
to_string(cfi(9999999)) & " : actual"
severity error;

wait;
end process;


--function cft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cft(CNTTIME,SYSCLKFREQ) = "100111010101101100110100000000")
report "count_for_time_test error # 1 " & LF &
to_string("100111010101101100110100000000") & " : expected" & LF &
to_string(cft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cft("1 min","66MHz") = "11101100000010001100111000000000")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100111000000000") & " : expected" & LF &
to_string(cft("1 min","66MHz")) & " : actual"
severity error;


assert (cft("1 hr","66MHz") = "11011101010010000100000100100000000000")
report "count_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100100000000000") & " : expected" & LF &
to_string(cft("1 hr","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz") = "01010010111110110001100001101100000000000000")
report "count_for_time_test error # 4 " & LF &
to_string("01010010111110110001100001101100000000000000") & " : expected" & LF &
to_string(cft("1 day","66MHz")) & " : actual"
severity error;


assert (cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 5 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz")) & " : actual"
severity error;


assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 6 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day","66MHz")+cft("1 hr","66MHz")+cft("1 min","66MHz")+cft("1 sec","66MHz")+cft("1 ms","66MHz")+cft("1 us","66MHz")+cft("1 ns","66MHz")+cft("1 ps","66MHz")+cft("1 fs","66MHz")+cft("1 as","66MHz")+cft("1 zs","66MHz")+cft("1 ys","66MHz")) & " : actual" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz") = "01010110011111110011100011111110110010010010")
report "count_for_time_test error # 7 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;

assert (cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "011100011100110011110110101000101011010000000101001")
report "count_for_time_test error # 8 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-3 kHz") = "01")
report "count_for_time_test error # 9 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cft("1 sec","1E-18 eHz") = "01")
report "count_for_time_test error # 10 " & LF &
to_string("01") & " : expected" & LF &
to_string(cft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cft("1 ns ","1E-15 yHz") = "01")
report "count_for_time_test error # 11 " & LF &
to_string("01010110011111110011100011111110110010010010") & " : expected" & LF &
to_string(cft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cft("1 us ","1E-15 yHz") = "01111101000")
report "count_for_time_test error # 12 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(cft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cft("20 ms ","50 MHz"),21);

assert (ext(cft("20 ms ","50 MHz"),21) = "011110100001001000000")
report "count_for_time_test error # 13 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(ext(cft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test : process
begin

assert (cfth("1 us ","1E-15 yHz") = 10)
report "count_for_time_high_test error # 1 " & LF &
to_string(10) & " : expected" & LF &
to_string(cfth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cfth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cfth("8 ms ","1 kHz") = 4)
report "count_for_time_high_test2 error # 1 " & LF &
to_string(4) & " : expected" & LF &
to_string(cfth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;


--function clkcnt(freq1StrVal : string;
-- freq2StrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
clock_count_test : process
begin

assert (clkcnt("1 kHz","50 MHz") = "110000110100111")
report "clock_count_test error # 1 " & LF &
to_string("110000110100111") & " : expected" & LF &
to_string(clkcnt("1 kHz","50 MHz")) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : bit_vector) return string; -- bit_vector to hexadecimal conversion
conv_to_hex_test1 : process
variable testVar : bv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test1 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_logic_vector) return string; -- std_logic_vector to hexadecimal conversion
conv_to_hex_test2 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test2 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function conv_to_hex(vectorVal : std_ulogic_vector) return string; -- std_ulogic_vector to hexadecimal conversion
conv_to_hex_test3 : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (conv_to_hex(testVar) = "0123456789ABCDEF")
report "conv_to_hex_test3 error # 1 " & LF &
"0123456789ABCDEF" & " : expected" & LF &
conv_to_hex(testVar) & " : actual"
severity error;

wait;
end process;


--function cslv(int1Val : integer;
-- int2Val : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(sigVal : signed;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested

--function cslv(usgVal : unsigned;
-- intVal : integer) return std_logic_vector; -- repackaging of "conv_std_logic_vector"
-- repackaged functions not tested


--function cuft(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_test : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(20 downto 0);
begin


assert (cuft(CNTTIME,SYSCLKFREQ) = "100111010101101100110011111111")
report "count_up_for_time_test error # 1 " & LF &
to_string("100111010101101100110011111111") & " : expected" & LF &
to_string(cuft(CNTTIME,SYSCLKFREQ)) & " : actual"
severity error;


assert (cuft("1 min","66MHz") = "11101100000010001100110111111111")
report "count_for_time_test error # 2 " & LF &
to_string("11101100000010001100110111111111") & " : expected" & LF &
to_string(cuft("1 min","66MHz")) & " : actual"
severity error;


assert (cuft("1 hr","66MHz") = "11011101010010000100000100011111111111")
report "count_up_for_time_test error # 3 " & LF &
to_string("11011101010010000100000100011111111111") & " : expected" & LF &
to_string(cuft("1 hr","66MHz")) & " : actual"
severity error;


assert (cuft("1 day","66MHz") = "1010010111110110001100001101011111111111111")
report "count_up_for_time_test error # 4 " & LF &
to_string("1010010111110110001100001101011111111111111") & " : expected" & LF &
to_string(cuft("1 day","66MHz")) & " : actual"
severity error;




assert (cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs","66MHz") = "1010110011111110011100011111110110010010001")
report "count_up_for_time_test error # 6 " & LF &
to_string("1010110011111110011100011111110110010010001") & " : expected" & LF &
to_string(cuft("1 day","66MHz")+cuft("1 hr","66MHz")+cuft("1 min","66MHz")+cuft("1 sec","66MHz")+cuft("1 ms","66MHz")+cuft("1 us","66MHz")+cuft("1 ns","66MHz")+cuft("1 ps","66MHz")+cuft("1 fs","66MHz")+cuft("1 as","66MHz")+cuft("1 zs","66MHz")+cuft("1 ys","66MHz")) & " : actual" & LF &
to_string(cuft("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs 1as 1zs 1ys","66MHz")) & " : actual"
severity error;



assert (cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz") = "11100011100110011110110101000101011010000000101000")
report "count_up_for_time_test error # 8 " & LF &
to_string("11100011100110011110110101000101011010000000101000") & " : expected" & LF &
to_string(cuft("1 ns 1 ps 1 fs 1as 1zs 1ys","1YHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-3 kHz") = "0")
report "count_up_for_time_test error # 9 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-3 kHz")) & " : actual"
severity error;

assert (cuft("1 sec","1E-18 eHz") = "0")
report "count_up_for_time_test error # 10 " & LF &
to_string("00") & " : expected" & LF &
to_string(cuft("1 sec","1E-18 eHz")) & " : actual"
severity error;

assert (cuft("1 ns ","1E-15 yHz") = "0")
report "count_up_for_time_test error # 11 " & LF &
to_string("0") & " : expected" & LF &
to_string(cuft("1 ns ","1E-15 yHz")) & " : actual"
severity error;

assert (cuft("1 us ","1E-15 yHz") = "1111100111")
report "count_up_for_time_test error # 12 " & LF &
to_string("1111100111") & " : expected" & LF &
to_string(cuft("1 us ","1E-15 yHz")) & " : actual"
severity error;

slvVar := ext(cuft("20 ms ","50 MHz"),21);

assert (ext(cuft("20 ms ","50 MHz"),25) = "0000011110100001000111111")
report "count_up_for_time_test error # 13 " & LF &
to_string("0000011110100001000111111") & " : expected" & LF &
to_string(ext(cuft("20 ms ","50 MHz"),25)) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return integer; -- returns the high value to be used in the range declaration of a vector used to represent the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test : process
begin

assert (cufth("1 us ","1E-15 yHz") = 9)
report "count_up_for_time_high_test error # 1 " & LF &
to_string(9) & " : expected" & LF &
to_string(cufth("1 us ","1E-15 yHz")) & " : actual"
severity error;

wait;
end process;


--function cufth(timeStrVal : string;
-- freqStrVal : string) return std_logic_vector; -- count for the time specified using the frequency (or period) value passed as a reference
count_up_for_time_high_test2 : process
variable CNTTIME : string(1 to 6) := "10 sec";
variable SYSCLKFREQ : string(1 to 5) := "66MHz";
variable slvVar : slv(3 downto 0) := "0110"; -- 8 - 2 = 6
begin

assert (cufth("8 ms ","1 kHz") = 2)
report "count_up_for_time_high_test2 error # 1 " & LF &
to_string(2) & " : expected" & LF &
to_string(cufth("8 ms ","1 kHz")) & " : actual"
severity error;

wait;
end process;

--function dpfi(intVal : integer) return natural; -- returns the number of decimal places for an integer value


--function dpfr(realVal : real) return natural; -- returns the number of decimal places to the left of the decimal point for a real value



--function dpfslvr(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the full range of the std_logic_vector passed


--function dpfslvv(vectorVal : std_logic_vector) return natural; -- returns the number of decimal places needed to represent the value of the std_logic_vector passed

--function ext(vectorVal : std_logic_vector;
-- intVal : integer) return std_logic_vector;
ext_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);

assert (ext2(slvVar,7) = "0000111") -- 7 bits
report "ext_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,7)) & " : actual"
severity error;

assert (ext2(slvVar,4) = "0111") -- 4 bits
report "ext_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(ext2(slvVar,4)) & " : actual"
severity error;

assert (ext2(slvVar,4)'length = 4) -- 4 bits
report "ext_test error # 3 " & LF &
to_string(4) & " : expected" & LF &
to_string(ext2(slvVar,4)'length) & " : actual"
severity error;

wait;
end process;



--function flip(vectorVal : bit_vector) return bit_vector; -- returns a bit_vector with all the bits in the reverse order


--function flip(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector with all the bits in the reverse order



--function flip(vectorVal : std_ulogic_vector) return std_ulogic_vector; -- returns a std_ulogic_vector with all the bits in the reverse order


--function hex_to_slv(stringVal : string) return std_logic_vector; -- converts a Hexadeximal string to a standard logic vector



--function int_to_slv(intVal : integer) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the integer value passed



--function mult_s(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- signed multiply



--function mult_us(Multiplier : std_logic_vector;
-- Multiplicand : std_logic_vector) return std_logic_vector; -- unsigned multiply



--function nat_to_slv(natVal : natural) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the natural value passed



--function neg(VectorVal : std_logic_vector) return std_logic_vector; -- returns the negated value


--function now return string; -- returns a string representation of the current simulation time
now_test : process
variable testVar : slv(63 downto 0) := "0000000100100011010001010110011110001001101010111100110111101111";
begin

wait for 3 sec;

assert (now = time'image(now))
report "now_test error # 1 " & LF &
time'image(now) & " : expected" & LF &
now & " : actual"
severity error;

wait;
end process;


--function reduce(vectorVal : std_logic_vector) return std_logic_vector; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function reduce_high(vectorVal : std_logic_vector) return integer; -- returns a std_logic_vector value just large enough to represent the standard logic vector value passed



--function seq(str1Val : string;
-- str2Val : string) return boolean;



--function shl(vectorVal : std_logic_vector;
-- natVal : natural) return std_logic_vector;



--function slv_to_bcd(vectorVal : std_logic_vector;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified



--function slv_to_bcd(vectorVal : std_logic_vector) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using enough BCD digits to represent the largest value possible in the range of the vector passed



--function slv_to_bcd_pipe(BCD_RVal : std_logic_vector;
-- MSB_Val : std_logic;
-- BCD_DigitsVal : integer) return std_logic_vector; -- returns a packed BCD number in std_logic_vector form from the std_logic_vector passed to it using the number of BCD digits specified. For pipelined operation. function must be called N times where N is the number of bits in the passed value



--function str_to_int(stringVal : string) return integer; -- converts an Integer string to an integer



--function str_to_led(stringVal : string;
-- CAVal : boolean) return std_logic_vector; -- converts a Hexadecimal string of any length to a std_logic_vector for seven segment LEDs



--function str_to_slv(stringVal : string) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector
str_to_slv_test : process
constant slvVar : slv := "0000000100100011010001010110011110001001101010111100110111101111";
begin

assert (str_to_slv("1") = "01") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("0") = "0") -- 0
report "bcd_to_led_test error # 1 " & LF &
to_string("00") & " : expected" & LF &
to_string(str_to_slv("0")) & " : actual"
severity error;

assert (str_to_slv("-1") = "11") -- -1
report "bcd_to_led_test error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(str_to_slv("-1")) & " : actual"
severity error;

assert (str_to_slv("10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 1 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv("10 us"))
severity error;

assert (str_to_slv(" 10 us") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 2 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us"))
severity error;

assert (str_to_slv(" 10 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 3 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10 us "))
severity error;

assert (str_to_slv(" 10.0 us ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 4 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0 us "))
severity error;

assert (str_to_slv(" 0.0100 ms ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 5 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0100 ms "))
severity error;

assert (str_to_slv(" 0.0000100sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0000100sec "))
severity error;

assert (str_to_slv(" 10E-6 sec ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 6a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E-6 sec "))
severity error;


assert (str_to_slv(" 10,000,000,000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 7 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10,000,000,000 "))
severity error;

assert (str_to_slv(" 100,000Hz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 8 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100,000Hz "))
severity error;


assert (str_to_slv(" 100kHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100kHz "))
severity error;

assert (str_to_slv(" 0.1MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9a " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.1MHz "))
severity error;

assert (str_to_slv(" .1 MHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 9b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" .1 MHz "))
severity error;

assert (str_to_slv(" 0.0001GHz ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 10 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 0.0001GHz "))
severity error;


assert (str_to_slv(" 10E 9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 11 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E 9 "))
severity error;


assert (str_to_slv(" 10E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 12 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9 "))
severity error;


assert (str_to_slv(" 10.0000000E+9.000 ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 13b " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 10.0000000E+9.000 "))
severity error;

assert (str_to_slv(" 100E+3 HZ") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 14 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;


assert (str_to_slv(" 1") = "01")
report "str_to_slv_test error # 15a " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(str_to_slv(" 1"))
severity error;

assert (str_to_slv(" -1") = "11")
report "str_to_slv_test error # 15b " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(str_to_slv(" -1"))
severity error;


assert (str_to_slv("1") = "01")
report "str_to_slv_test error # 16 " & LF &
to_string("01") & " : expected"
& LF &
to_string(str_to_slv("1")) & " : actual"
severity error;

assert (str_to_slv("10") = "01010")
report "str_to_slv_test error # 17 " & LF &
to_string("01010") & " : expected"
& LF &
to_string(str_to_slv("10")) & " : actual"
severity error;

assert (str_to_slv(" 100E+3 HZ ps ns MHz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 18 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100E+3 HZ Hz") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 19 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ"))
severity error;

assert (str_to_slv(" 100,000 HZ 234sec") = "01001010100000010111110010000000000")
report "str_to_slv_test error # 20 " & LF &
"expected : " & to_string("01001010100000010111110010000000000") & LF &
"actual : " & to_string(str_to_slv(" 100E+3 HZ 234sec"))
severity error;

assert (str_to_slv("1 day") = "01001010111100001010011101100011101110110001110000000000000000000000") -- 0
report "str_to_slv_test error # 21 " & LF &
to_string("01001010111100001010011101100011101110110001110000000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 day")) & " : actual"
severity error;

assert (str_to_slv("1 hr") = "011000111110101110001001110110100100111011010000000000000000000") -- 0
report "str_to_slv_test error # 22 " & LF &
to_string("011000111110101110001001110110100100111011010000000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 hr")) & " : actual"
severity error;

assert (str_to_slv("1 min") = "011010101001010011010111010011110100001100000000000000000") -- 0
report "str_to_slv_test error # 23 " & LF &
to_string("011010101001010011010111010011110100001100000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 min")) & " : actual"
severity error;

assert (str_to_slv("1 sec") = "011100011010111111010100100110001101000000000000000") -- 0
report "str_to_slv_test error # 24 " & LF &
to_string("011100011010111111010100100110001101000000000000000") & " : expected" & LF &
to_string(str_to_slv("1 sec")) & " : actual"
severity error;

assert (str_to_slv("1 ms") = "01110100011010100101001010001000000000000") -- 0
report "str_to_slv_test error # 25 " & LF &
to_string("01110100011010100101001010001000000000000") & " : expected" & LF &
to_string(str_to_slv("1 ms")) & " : actual"
severity error;

assert (str_to_slv("1 us") = "0111011100110101100101000000000") -- 0
report "str_to_slv_test error # 26 " & LF &
to_string("0111011100110101100101000000000") & " : expected" & LF &
to_string(str_to_slv("1 us")) & " : actual"
severity error;

assert (str_to_slv("1 ns") = "011110100001001000000") -- 0
report "str_to_slv_test error # 27 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 ns")) & " : actual"
severity error;

assert (str_to_slv("1 ps") = "01111101000") -- 0
report "str_to_slv_test error # 28 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 ps")) & " : actual"
severity error;

assert (str_to_slv("1 fs") = "01") -- 0
report "str_to_slv_test error # 29 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 fs")) & " : actual"
severity error;

assert (str_to_slv("1 as",-24) = "011110100001001000000") -- 0
report "str_to_slv_test error # 30 " & LF &
to_string("011110100001001000000") & " : expected" & LF &
to_string(str_to_slv("1 as",-24)) & " : actual"
severity error;

assert (str_to_slv("1 zs",-24) = "01111101000") -- 0
report "str_to_slv_test error # 31 " & LF &
to_string("01111101000") & " : expected" & LF &
to_string(str_to_slv("1 zs",-24)) & " : actual"
severity error;

assert (str_to_slv("1 ys",-24) = "01") -- 0
report "str_to_slv_test error # 32 " & LF &
to_string("01") & " : expected" & LF &
to_string(str_to_slv("1 ys",-24)) & " : actual"
severity error;


assert (str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs") = "01001110000111011000111100110011111100101100110000111010000000101001") -- 0
report "str_to_slv_test error # 33 " & LF &
to_string("01001110000111011000111100110011111100101100110000111010000000101001") & " : expected" & LF &
to_string(str_to_slv("1 day 1 hr 1 min 1 sec 1 ms 1 us 1 ns 1 ps 1 fs")) & " : actual"
severity error;


wait;
end process;


--function str_to_slv_high(stringVal : string) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed



--function str_to_slv_var_base(stringVal : string;
-- intVal : integer) return std_logic_vector; -- converts an Integer, in string form, of any length to a std_logic_vector using the time base passed



--function str_to_slv_var_base_high(stringVal : string;
-- intVal : integer) return integer; -- returns an integer representing the length of a vector needed to represent the intever value (in string form) passed using the timebase value



--function strh(stringVal : string) return integer;

sxt_test : process
constant slvVar : slv := "0111";
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);

begin

slv1Var := sxt2(int_to_slv(-1000),slv1Var'length);
slv2Var := sxt2(int_to_slv(-6),slv2Var'length);

assert (sxt2(slvVar,7) = "0000111") -- 7 bits
report "sxt2_test error # 1 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,7)) & " : actual"
severity error;

assert (sxt2(slvVar,4) = "0111") -- 4 bits
report "sxt2_test error # 2 " & LF &
to_string("0000111") & " : expected" & LF &
to_string(sxt2(slvVar,4)) & " : actual"
severity error;

assert (sxt2("1001",7) = "1111001") -- 7 bits
report "sxt2_test error # 3 " & LF &
to_string("1111001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;

assert (sxt2("00",7) = "0000000") -- 4 bits
report "sxt2_test error # 4 " & LF &
to_string("0000000") & " : expected" & LF &
to_string(sxt2("00",7)) & " : actual"
severity error;

assert (sxt2("1001",4) = "1001") -- 7 bits
report "sxt2_test error # 5 " & LF &
to_string("1001") & " : expected" & LF &
to_string(sxt2("1001",7)) & " : actual"
severity error;


wait;
end process;

---- synopsys translate_off
--function time_to_slv(timeVal : time;
-- clkFreqVal : frequency) return std_logic_vector;
---- synopsys translate_on
--
--function to_int(vectorVal : std_logic_vector) return integer; -- repackaging of "conv_integer" function
--
--function to_period(freqVal : frequency) return time; -- returns a one cycle period value for a given frequency
--
---- synopsys translate_off
--function to_string(intVal : integer) return string; -- returns a string value for an integer value passed
to_string_test1 : process
begin

assert (to_string(2147000000) = "2147000000")
report "to_string_test1 error # 1 " & LF &
"2147000000" & " : expected" & LF &
to_string(2147000000) & " : actual"
severity error;

assert (to_string(-2147000000) = "-2147000000")
report "to_string_test1 error # 2 " & LF &
"-2147000000" & " : expected" & LF &
to_string(-2147000000) & " : actual"
severity error;



wait;
end process;


--function to_string(realVal : real) return string; -- returns a string value for an real value passed
to_string_test2 : process
begin

assert (to_string(1.000000e+308) = "1.000000e+308")
report "to_string_test2 error # 1 " & LF &
"1.000000e+308" & " : expected" & LF &
to_string(1.000000e+308) & " : actual"
severity error;

assert (to_string(1.000000e-308) = "1.000000e-308")
report "to_string_test2 error # 2 " & LF &
"1.000000e-308" & " : expected" & LF &
to_string(1.000000e-308) & " : actual"
severity error;

assert (to_string(-1.000000e-308) = "-1.000000e-308")
report "to_string_test2 error # 2 " & LF &
"-1.000000e-308" & " : expected" & LF &
to_string(-1.000000e-308) & " : actual"
severity error;

wait;
end process;


--function to_string(timeVal : time) return string;
to_string_test3 : process
begin

assert (to_string(3 ns) = "3 ns")
report "to_string_test3 error # 1 " & LF &
"3 ns" & " : expected" & LF &
to_string(3 ns) & " : actual"
severity error;


assert (to_string(2040 ns) = "2040 ns")
report "to_string_test3 error # 1 " & LF &
"2040 ns" & " : expected" & LF &
to_string(2040 ns) & " : actual"
severity error;

wait;
end process;


--function to_string(vectorVal : std_logic_vector) return string;
---- synopsys translate_on
--
--function vhfi(intVal : integer) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the integer value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--function vhfn(natVal : natural) return natural; -- returns the high value to be used in the range declaration of a vector used to represent the natural value passed. This assumes the rest of the range declaration of the vector will be "downto 0"
--
--function vlfi(intVal : integer) return natural; -- returns an integer representing the length of a vector needed to represent the integer value passed
--function vlfn(natVal : natural) return natural; -- returns an integer representing the length of a vector needed to represent the natural value passed
--
--function vrfi(intVal : integer) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the integer value passed
--
--function vrfn(natVal : natural) return std_logic_vector; -- returns a std_logic_vector with a range just large enough to represent the natural value passed
--
--------------------------------------------------------------------------------
---- Procedure Declarations
--------------------------------------------------------------------------------
---- synopsys translate_off
--procedure clkgen(
-- constant clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- signal clkSig : out std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkPeriodSig : in time;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
--
--procedure clkgen(
-- signal clkEnSig : in boolean;
-- signal clkFreqSig : in frequency;
-- constant clkDutySig : in real;
-- signal clkResetSig : in boolean;
-- signal clkSig : inout std_logic);
---- synopsys translate_on
--
--procedure FF(
-- signal Clk : in std_logic;
-- signal Rst : in std_logic;
-- signal D : in std_logic_vector;
-- signal Q : out std_logic_vector);
--
--procedure slv_to_bcd(
-- signal BCD_RIn : in std_logic_vector;
-- signal BinIn : in std_logic_vector;
-- signal BinFBIn : in std_logic_vector;
-- signal ClkIn : in std_logic;
-- constant BCD_DigitsVal : in integer;
-- signal EnIn : in std_logic;
-- signal RstLowIn : in std_logic;
-- signal BCD_ROut : out std_logic_vector;
-- signal Bin_ROut : out std_logic_vector;
-- signal DoneOut : out std_logic);


divider_test : process
variable slv1Var : slv(11 downto 0);
variable slv2Var : slv(11 downto 0);
variable slv3Var : slv(slv1Var'range);
begin
slv1Var := ext2(int_to_slv(1000),slv1Var'length);
slv2Var := ext2(int_to_slv(6),slv2Var'length);
slv3Var := slv1Var/slv2Var;
-- assert FALSE
-- report "divider output :" & LF & to_string(to_int(slv1Var)) & " / " & to_string(to_int(slv2Var)) & " = " & to_string(to_int(slv3Var))
-- severity note;
wait;
end process;


bcd_to_led_test : process
variable slvVar : slv(27 downto 0);
begin
slvVar := bcd_to_led("0011001000010000",False); -- 3210
assert (slvVar = "1111001110110101100001111110")
report "bcd_to_led_test error # 1 "
severity error;
slvVar := bcd_to_led("0111011001010100",False); -- 7654
assert (slvVar = "1110010101111110110110110011")
report "bcd_to_led_test error # 2 "
severity error;
slvVar := bcd_to_led("0001000010011000",False); -- 1098
assert (slvVar = "0110000111111011100111111111")
report "bcd_to_led_test error # 3 "
severity error;
slvVar := bcd_to_led("0011001000010000",True); -- 3210
assert (slvVar = "0000110001001010011110000001")
report "bcd_to_led_test error # 4 "
severity error;
slvVar := bcd_to_led("0111011001010100",True); -- 7654
assert (slvVar = "0001101010000001001001001100")
report "bcd_to_led_test error # 5 "
severity error;
slvVar := bcd_to_led("0001000010011000",True); -- 1098
assert (slvVar = "1001111000000100011000000000")
report "bcd_to_led_test error # 6 "
severity error;
wait;
end process;


str_to_int_test : process
variable intVar : integer;
begin
intVar := str_to_int("10"); -- 3210
assert (intVar = 10)
report "str_to_int_test error # 1 " & LF &
"expected : 10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-10 sec"); -- 3210
assert (intVar = -10)
report "str_to_int_test error # 2 " & LF &
"expected : -10" & LF &
"actual : " & to_string(intVar)
severity error;

intVar := str_to_int("E-6 sec"); -- 3210
assert (intVar = -6)
report "str_to_int_test error # 3 " & LF &
"expected : -6" & LF &
"actual : " & to_string(intVar)
severity error;

wait;
end process;




reduce_test : process

begin

assert (reduce("00000") = "00") -- 0
report "reduce error # 1 " & LF &
to_string("11") & " : expected" & LF &
to_string(reduce("00000")) & " : actual"
severity error;

assert (reduce("00001") = "01") -- 1
report "reduce error # 2 " & LF &
"expected : " & to_string("01") & LF &
"actual : " & to_string(reduce("00001"))
severity error;

assert (reduce("11111") = "11") -- -1
report "reduce error # 3 " & LF &
"expected : " & to_string("11") & LF &
"actual : " & to_string(reduce("11111"))
severity error;

assert (reduce("10000") = "10000") -- -16
report "reduce error # 4 " & LF &
"expected : " & to_string("10000") & LF &
"actual : " & to_string(reduce("10000"))
severity error;

wait;

end process;











--exp_test : process
--variable timeBaseVar : slv(500 downto 0);
--variable lineVar : line;
--begin
-- timeBaseVar := ext("01",timeBaseVar'length);
-- for loopVar in 1 to 50 loop
-- timeBaseVar := timeBaseVar(timeBaseVar'high-4 downto 0) * "1010";
--
---- write(lineVar,to_string(real(reduce_high(timeBaseVar))/real(loopVar)));
---- write(lineVar,LF);
-- assert FALSE
-- report
-- to_string(real(reduce_high(timeBaseVar))/real(loopVar)) & LF
-- severity note;
-- end loop;
--
-- wait;
--end process;



unsigned_mult_test : process

begin

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

assert (mult_us("000","011") = "000000") -- 0
report "mult error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","011")) & " : actual"
severity error;

assert (mult_us("011","000") = "000000") -- 0
report "mult error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("011","000")) & " : actual"
severity error;

assert (mult_us("000","101") = "000000") -- 0
report "mult error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("000","101")) & " : actual"
severity error;

assert (mult_us("101","000") = "000000") -- 0
report "mult error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_us("101","000")) & " : actual"
severity error;

assert (mult_us("011","011") = "001001") -- 0
report "mult error # 7 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_us("011","011")) & " : actual"
severity error;

wait;

end process;








signed_mult_test : process

begin

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 1 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 2 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("000","011") = "000000") -- 0
report "mult_s error # 3 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","011")) & " : actual"
severity error;

assert (mult_s("011","000") = "000000") -- 0
report "mult_s error # 4 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("011","000")) & " : actual"
severity error;

assert (mult_s("000","101") = "000000") -- 0
report "mult_s error # 5 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("000","101")) & " : actual"
severity error;

assert (mult_s("101","000") = "000000") -- 0
report "mult_s error # 6 " & LF &
to_string("000000") & " : expected" & LF &
to_string(mult_s("101","000")) & " : actual"
severity error;

assert (mult_s("011","101") = "110111") -- 3 * (-3) = -9
report "mult_s error # 7 " & LF &
to_string("110111") & " : expected" & LF &
to_string(mult_s("011","101")) & " : actual"
severity error;

assert (mult_s("011","100") = "110100") -- 3 * (-4) = -12
report "mult_s error # 8 " & LF &
to_string("110100") & " : expected" & LF &
to_string(mult_s("011","100")) & " : actual"
severity error;

assert (mult_s("101","101") = "001001") -- (-3) * (-3) = 9
report "mult_s error # 9 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("101","101")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 10 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;

assert (mult_s("011","011") = "001001") -- 0
report "mult_s error # 11 " & LF &
to_string("001001") & " : expected" & LF &
to_string(mult_s("011","011")) & " : actual"
severity error;


assert (mult_s("100","100") = "010000") -- -4 * -4 = 16
report "mult_s error # 11 " & LF &
to_string("010000") & " : expected" & LF &
to_string(mult_s("100","100")) & " : actual"
severity error;



wait;

end process;








conv_to_hex_test : process
constant slvVar : slv(11 downto 0) := "101011110000";

begin

assert (conv_to_hex(slvVar) = "AF0") -- 0
report "mult_s error # 1 " & LF &
"AF0 : expected" & LF &
conv_to_hex(slvVar) & " : actual"
severity error;


wait;

end process;


--assert FALSE
--report "THIS IS THE END OF SIMULATION" & LF
--severity failure;

------------------------------------------------------------------------------
end behavioral;
-----------------------------------------------------------------------------

-- end of extension_pack testbench


-- synopsys translate_on
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,968
Messages
2,570,152
Members
46,698
Latest member
LydiaHalle

Latest Threads

Top