- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hi,
I am trying to create a component which will behave like a ROM in simulation. I would like it to take an input text file. I am trying to use the textio functionality. The component will have an address input and a rd input. It will have a rddata output. When rd is set high I want to read the data from the text file at the line set by address and make rddata the value read. e.g. prog_file.txt : 01 02 a1 a2 If address=X"03" and rising edge on rd. rddata should equal a1. Here is what I have so far:LIBRARY ieee;
USE ieee.std_logic_1164.all;
USE ieee.numeric_std.all;
USE ieee.std_logic_textio.all;
LIBRARY STD;
USE STD.textio.all;
LIBRARY work;
ENTITY test_program_file_io IS
GENERIC
(
filename : string = prog_file.txt;
data_width : integer = 8;
addr_width : integer = 15
);
PORT
(
address : IN std_logic_vector(addr_width-1 DOWNTO 0);
rd : IN std_logic;
rddata : OUT std_logic_vector(data_width-1 DOWNTO 0)
);
END ENTITY;
ARCHITECTURE sim OF test_program_file_io IS
FILE file_input : text;
SIGNAL value_read : std_logic_vector(data_width-1 DOWNTO 0);
SIGNAL count : integer := 0;
BEGIN
rddata <= value_read;
read_hex_value_from_file : PROCESS
VARIABLE v_in_line : line;
VARIABLE v_value : std_logic_vector(data_width-1 DOWNTO 0);
BEGIN
WAIT ON rd UNTIL rd = '1';
count <= to_integer(unsigned(address));
file_open(file_input, filename, read_mode);
WHILE((NOT ENDFILE(file_input)) AND (count > 0) LOOP
READLINE(file_input,v_in_line);
count <= count - 1;
END LOOP;
HREAD(v_in_line,v_value);
WAIT ON rd UNTIL rd = '0';
value_read <= v_value;
file_close(file_input);
END PROCESS;
END ARCHITECTURE;
I believe that the loop using count is not working because it is in a concurrent statement but I am not sure how to do this without them, I am thinking that to get the functionality I want, if address is 3 then i need to perform 3 readline ops (while checking for endline) and then do the hread and output the value. I cant think of a way of doing a variable number of readline ops without the loop. note hread is only compatible with vhdl-2008 Any help or ideas would be greatly appreciated. Thanks James
Link Copied
3 Replies
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Why not just read the text file into an array using an initialisation function? and then just access the array with the address? This will perform far better than opening and closing the file on every single read access.
--- Quote Start --- note hread is only compatible with vhdl-2008 --- Quote End --- technically correct, but you included the non-standard library std_logic_textio which is a 3rd party library that gave you the ability to read/write directly to std_logic/std_logic_vector with VHDL 1993. The functionality of this package is included in std_logic_1164 in VHDL 2008.- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Is there any reason you're making an asynchronous rom? and not a synchronous one?
btw, heres what I think you want:
architecture sim of my_rom is
type rom_t is array(0 to N-1) of std_logic_vector(7 downto 0);
function init_rom return rom_t is
file rom_file : text open read_mode is filename;
variable ret : rom_t;
variable l : line;
begin
for i in 0 to N-1 loop
readline(rom_file, l);
hread(l, ret(i));
end loop;
return ret;
end function init_rom;
constant ROM : rom_t := init_rom;
begin
process(rd, addr)
begin
if rd='1' then
rddata <= ROM( to_integer( to_unsigned( address ) );
end if;
end process;
end architecture sim;
- Mark as New
- Bookmark
- Subscribe
- Mute
- Subscribe to RSS Feed
- Permalink
- Report Inappropriate Content
Hi Tricky,
Thanks for your response. With a bit of playing I managed to get your code working and I have used it in my simulation. I had to declare the function as impure and I put in a check for the end of file for a bit of safety. This is what i ended up with:LIBRARY ieee;
USE ieee.std_logic_1164.all;
USE ieee.numeric_std.all;
LIBRARY STD;
USE STD.textio.all;
LIBRARY work;
ENTITY test_program_file_io IS
GENERIC
(
filename : string := "prog_file.txt";
data_width : integer := 8;
addr_width : integer := 15
);
PORT
(
address : IN std_logic_vector(addr_width-1 DOWNTO 0);
rd : IN std_logic;
rddata : OUT std_logic_vector(data_width-1 DOWNTO 0)
);
END ENTITY;
ARCHITECTURE sim OF test_program_file_io IS
CONSTANT N : integer := (2**addr_width);
TYPE rom_t IS ARRAY (0 TO N-1) OF std_logic_vector(7 DOWNTO 0);
IMPURE FUNCTION init_rom RETURN rom_t IS
FILE rom_file : text OPEN read_mode IS filename;
VARIABLE ret : rom_t;
VARIABLE l : line;
BEGIN
FOR i IN 0 TO N-1 LOOP
IF(NOT ENDFILE(rom_file)) THEN
readline(rom_file, l);
hread(l, ret(i));
END IF;
END LOOP;
RETURN ret;
END FUNCTION init_rom;
CONSTANT ROM : rom_t := init_rom;
BEGIN
PROCESS(rd, address)
BEGIN
IF(rd='1')THEN
rddata <= ROM(to_integer(unsigned(address)));
END IF;
END PROCESS;
END ARCHITECTURE;
--- Quote Start --- technically correct, but you included the non-standard library std_logic_textio which is a 3rd party library that gave you the ability to read/write directly to std_logic/std_logic_vector with VHDL 1993. The functionality of this package is included in std_logic_1164 in VHDL 2008. --- Quote End --- Yes you are right, I was working with vhdl-1993 but updated my simulation to use vhdl-2008 so I could use the hread and cut a corner. I missed removing that library. --- Quote Start --- Is there any reason you're making an asynchronous rom? and not a synchronous one? --- Quote End --- Not really, the application might not be the best. I was trying to improve my simulation skills and using it like a ROM I could connect it in my work simulation. My aim was to be able to read in a selected line from a input text file so I can dump a hex program to a text file and load it into my simulation sequentially. I also wanted to be able to start from somewhere other than the start of the file. After playing I think that you are right and initializing an array is the simplest path. Thanks James
Reply
Topic Options
- Subscribe to RSS Feed
- Mark Topic as New
- Mark Topic as Read
- Float this Topic for Current User
- Bookmark
- Subscribe
- Printer Friendly Page