Hello
I am designing a binary to thermometric bit converter.
for example: If I have a binary number 011 then I would want 3 bit to
go one. ie. 111. If the number is five(101) then five bits should be
set to 1 (11111).
So, if you have N bits of input, your output code has (2**N)-1 bits.
It's usually a very nice idea to describe such things as a recursive
function. The sun was shining yesterday and I've just found a
disastrous bug in a SystemVerilog simulator, so I'm feeling in
a good mood and therefore I'm going to post the whole of the
code. Recursive function, synthesisable test model (5 inputs
and 31 outputs), and a little test bench. It's left as a trivial
exercise for the student to document it
In FPGA architectures with 4-input LUTs, this 5-to-31 test model
takes only 1 LUT per output, plus two extra LUTs. I suspect
it will start to get bigger quite rapidly as the number of input
bits increases, but the logic is pretty simple and has no nasty
ripple chains. That's the beauty of recursive solutions - they
typically give you tree-structured hardware with minimal
effort from either you or the synthesis tool.
Enjoy.
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
----------------------- package contains synthesisable function
library ieee;
use ieee.std_logic_1164.all;
package thermo is
function thermo_code(s: std_logic_vector) return std_logic_vector;
end package thermo;
package body thermo is
function thermo_code(s: std_logic_vector) return std_logic_vector is
variable sn: std_logic_vector(s'length-1 downto 0);
variable c: std_logic_vector(1 to 2**(s'length-1));
variable t: std_logic_vector(2 to 2**(s'length-1));
begin
assert s'length > 0
report "Can't process null vector"
severity failure;
if s'length = 1 then
return s;
else -- s'length > 1
sn := s;
t := thermo_code(sn(sn'left-1 downto 0));
if sn(sn'left) = '1' then
c := (others => '1');
return c & t;
else
c := (others => '0');
return t & c;
end if;
end if;
end function thermo_code;
end package body thermo;
------------------------- synthesisable design 5->31 bits
library ieee;
use ieee.std_logic_1164.all;
use work.thermo.all;
entity test_thermo is
port ( value: in std_logic_vector(4 downto 0);
code: out std_logic_vector(1 to 31) );
end entity test_thermo;
architecture A of test_thermo is
begin
code <= thermo_code(value);
end architecture A; -- of test_thermo
---------------------------- test bench
library ieee;
use ieee.std_logic_1164.all;
use std.textio.all;
use ieee.std_logic_textio.all;
use ieee.numeric_std.all;
entity top_test_thermo is end;
architecture Test of top_test_thermo is
signal value: std_logic_vector(4 downto 0);
signal code: std_logic_vector(1 to 31);
begin
dut: entity work.test_thermo port map (value, code);
process
variable L: line;
begin
for i in 0 to 31 loop
value <= std_logic_vector(to_unsigned(i, value'length));
wait for 1 ns;
write(L, value);
write(L, string'(" => "));
write(L, code);
writeline(output, L);
end loop;
wait;
end process;
end;
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
--
Jonathan Bromley, Consultant
DOULOS - Developing Design Know-how
VHDL * Verilog * SystemC * e * Perl * Tcl/Tk * Project Services
Doulos Ltd., 22 Market Place, Ringwood, BH24 1AW, UK
(e-mail address removed)
http://www.MYCOMPANY.com
The contents of this message may contain personal views which
are not the views of Doulos Ltd., unless specifically stated.