2 use ieee.std_logic_1164.all;
3 use ieee.numeric_std.all;
8 function fls_32 (val: std_ulogic_vector(31 downto 0)) return integer;
9 function ffs_32 (val: std_ulogic_vector(31 downto 0)) return integer;
11 function fls_64 (val: std_ulogic_vector(63 downto 0)) return integer;
12 function ffs_64 (val: std_ulogic_vector(63 downto 0)) return integer;
14 function popcnt8(val: std_ulogic_vector(7 downto 0)) return std_ulogic_vector;
15 function popcnt32(val: std_ulogic_vector(31 downto 0)) return std_ulogic_vector;
16 function popcnt64(val: std_ulogic_vector(63 downto 0)) return std_ulogic_vector;
18 function cmp_one_byte(a, b: std_ulogic_vector(7 downto 0)) return std_ulogic_vector;
20 function ppc_signed_compare(a, b: signed(63 downto 0)) return std_ulogic_vector;
21 function ppc_unsigned_compare(a, b: unsigned(63 downto 0)) return std_ulogic_vector;
23 function ra_or_zero(ra: std_ulogic_vector(63 downto 0); reg: std_ulogic_vector(4 downto 0)) return std_ulogic_vector;
25 function byte_reverse(val: std_ulogic_vector(63 downto 0); size: integer) return std_ulogic_vector;
27 function sign_extend(val: std_ulogic_vector(63 downto 0); size: natural) return std_ulogic_vector;
30 package body helpers is
31 function fls_32 (val: std_ulogic_vector(31 downto 0)) return integer is
32 variable ret: integer;
35 for i in val'range loop
45 function ffs_32 (val: std_ulogic_vector(31 downto 0)) return integer is
46 variable ret: integer;
49 for i in val'reverse_range loop
59 function fls_64 (val: std_ulogic_vector(63 downto 0)) return integer is
60 variable ret: integer;
63 for i in val'range loop
73 function ffs_64 (val: std_ulogic_vector(63 downto 0)) return integer is
74 variable ret: integer;
77 for i in val'reverse_range loop
87 function popcnt8(val: std_ulogic_vector(7 downto 0)) return std_ulogic_vector is
88 variable ret: unsigned(3 downto 0) := (others => '0');
90 for i in val'range loop
91 ret := ret + ("000" & val(i));
94 return std_ulogic_vector(resize(ret, val'length));
97 function popcnt32(val: std_ulogic_vector(31 downto 0)) return std_ulogic_vector is
98 variable ret: unsigned(5 downto 0) := (others => '0');
100 for i in val'range loop
101 ret := ret + ("00000" & val(i));
104 return std_ulogic_vector(resize(ret, val'length));
107 function popcnt64(val: std_ulogic_vector(63 downto 0)) return std_ulogic_vector is
108 variable ret: unsigned(6 downto 0) := (others => '0');
110 for i in val'range loop
111 ret := ret + ("000000" & val(i));
114 return std_ulogic_vector(resize(ret, val'length));
117 function cmp_one_byte(a, b: std_ulogic_vector(7 downto 0)) return std_ulogic_vector is
118 variable ret: std_ulogic_vector(7 downto 0);
129 function ppc_signed_compare(a, b: signed(63 downto 0)) return std_ulogic_vector is
130 variable ret: std_ulogic_vector(3 downto 0);
143 function ppc_unsigned_compare(a, b: unsigned(63 downto 0)) return std_ulogic_vector is
144 variable ret: std_ulogic_vector(3 downto 0);
157 function ra_or_zero(ra: std_ulogic_vector(63 downto 0); reg: std_ulogic_vector(4 downto 0)) return std_ulogic_vector is
159 if to_integer(unsigned(reg)) = 0 then
160 return x"0000000000000000";
166 function byte_reverse(val: std_ulogic_vector(63 downto 0); size: integer) return std_ulogic_vector is
167 variable ret : std_ulogic_vector(63 downto 0) := (others => '0');
169 -- Vivado doesn't support non constant vector slices, so we have to code
173 for_2 : for k in 0 to 1 loop
174 ret(((8*k)+7) downto (8*k)) := val((8*(1-k)+7) downto (8*(1-k)));
177 for_4 : for k in 0 to 3 loop
178 ret(((8*k)+7) downto (8*k)) := val((8*(3-k)+7) downto (8*(3-k)));
181 for_8 : for k in 0 to 7 loop
182 ret(((8*k)+7) downto (8*k)) := val((8*(7-k)+7) downto (8*(7-k)));
185 report "bad byte reverse length " & integer'image(size) severity failure;
191 function sign_extend(val: std_ulogic_vector(63 downto 0); size: natural) return std_ulogic_vector is
192 variable ret : signed(63 downto 0) := (others => '0');
193 variable upper : integer := 0;
197 ret := resize(signed(val(15 downto 0)), 64);
199 ret := resize(signed(val(31 downto 0)), 64);
201 ret := resize(signed(val(63 downto 0)), 64);
203 report "bad byte reverse length " & integer'image(size) severity failure;
206 return std_ulogic_vector(ret);
209 end package body helpers;