library ieee; use ieee.std_logic_1164.all; use ieee.numeric_std.all; use work.gen_pkg.all; use work.textmode_vga_component_pkg.all; use work.textmode_vga_pkg.all; use work.textmode_vga_platform_dependent_pkg.all; entity beh_history_tb is end entity beh_history_tb; architecture sim of beh_history_tb is -- system signal sys_clk, sys_res_n : std_logic; -- history/display signal d_new_eingabe, d_new_result, d_new_bs : std_logic; signal d_zeile : hzeile; signal d_spalte : hspalte; signal d_get, d_done : std_logic; signal d_char : hbyte; -- history/scanner signal s_char : hbyte; signal s_take, s_done, s_backspace : std_logic; -- ps/2 signal new_data : std_logic; signal data : std_logic_vector(7 downto 0); -- vga/display signal free : std_logic; signal command : std_logic_vector(COMMAND_SIZE - 1 downto 0); signal command_data : std_logic_vector(3 * COLOR_SIZE + CHAR_SIZE -1 downto 0); -- tmp: history<>scanner signal do_it, finished : std_logic; signal stop : boolean := false; begin -- history inst : entity work.history(beh) port map ( sys_clk => sys_clk, sys_res_n => sys_res_n, -- scanner s_char => s_char, s_take => s_take, s_done => s_done, s_backspace => s_backspace, -- display d_new_eingabe => d_new_eingabe, d_new_result => d_new_result, d_new_bs => d_new_bs, d_zeile => d_zeile, d_spalte => d_spalte, d_get => d_get, d_done => d_done, d_char => d_char, -- TODO: tmp only! do_it => do_it, finished => finished ); -- display inst_disp : entity work.display(beh) port map ( sys_clk => sys_clk, sys_res_n => sys_res_n, -- history d_new_eingabe => d_new_eingabe, d_new_result => d_new_result, d_new_bs => d_new_bs, d_zeile => d_zeile, d_spalte => d_spalte, d_get => d_get, d_done => d_done, d_char => d_char, -- vga command => command, command_data => command_data, free => free ); -- scanner inst_scan : entity work.scanner(beh) port map ( sys_clk => sys_clk, sys_res_n => sys_res_n, -- ps/2 new_data => new_data, data => data, -- history s_char => s_char, s_take => s_take, s_done => s_done, s_backspace => s_backspace, -- Parser do_it => do_it, finished => finished ); process begin sys_clk <= '0'; wait for 15 ns; sys_clk <= '1'; wait for 15 ns; if stop = true then wait; end if; end process; process begin free <= '0'; wait for 15 ns; free <= '1'; wait for 30 ns; if stop = true then wait; end if; end process; process function ascii2sc (x : hbyte) return hbyte is variable y : hbyte; begin case x is when x"30" => y := SC_KP_0; when x"31" => y := SC_KP_1; when x"32" => y := SC_KP_2; when x"33" => y := SC_KP_3; when x"34" => y := SC_KP_4; when x"35" => y := SC_KP_5; when x"36" => y := SC_KP_6; when x"37" => y := SC_KP_7; when x"38" => y := SC_KP_8; when x"39" => y := SC_KP_9; when x"2b" => y := SC_KP_PLUS; when x"2d" => y := SC_KP_MINUS; when x"2a" => y := SC_KP_MUL; when x"2f" => y := SC_KP_DIV; when x"20" => y := SC_SPACE; when x"1c" => y := SC_ENTER; when x"0e" => y := SC_BKSP; when others => y := x"41"; end case; return y; end function; function valid_char (x : std_logic_vector(7 downto 0)) return boolean is variable y : boolean; begin case x is when SC_KP_0 | SC_KP_1 | SC_KP_2 | SC_KP_3 | SC_KP_4 | SC_KP_5 | SC_KP_6 | SC_KP_7 | SC_KP_8 | SC_KP_9 | SC_KP_PLUS | SC_KP_MINUS | SC_KP_MUL | SC_KP_DIV | SC_SPACE | SC_BKSP | SC_ENTER => y := true; when others => y := false; end case; return y; end function; -- textio stuff use std.textio.all; file f : text open read_mode is "../../src/history.test"; variable l : line; variable input : string(1 to 100); variable run_tc, run_inner : boolean := true; variable i, j, y : natural; begin -- init & reset sys_res_n <= '0'; new_data <= '0'; data <= (others => '0'); s_done <= '0'; finished <= '0'; icwait(sys_clk, 20); sys_res_n <= '1'; i := 1; f_loop : while not endfile(f) loop data <= (others => '0'); f1_loop : while not endfile(f) loop readline (f, l); input := (others => nul); if (l'length <= 100) then input(1 to l'length) := l.all; if (input(1) = '#') then next f1_loop; else exit f1_loop; end if; else report "fehler in history.test: eingabe zu lange in testfall " & natural'image(i); next f_loop; end if; end loop f1_loop; report "testcase(" & natural'image(i) & ").input: " & input; i := i + 1; icwait(sys_clk, 5); run_tc := true; j := 0; mainl : while run_tc loop icwait(sys_clk, 10); j := j + 1; if j = 101 then run_tc := false; assert(false) report "wtf @ schleife"; next mainl; end if; -- jedes mal release new_data <= '1'; data <= x"f0"; icwait(sys_clk, 1); new_data <= '0'; icwait(sys_clk, 1); new_data <= '1'; case input(j) is when nul => data <= ascii2sc(x"1c"); -- $ (enter) when '!' => data <= ascii2sc(x"0e"); -- ! (backspace) when others => data <= ascii2sc(std_logic_vector(to_unsigned(character'pos(input(j)),8))); end case; icwait(sys_clk, 1); new_data <= '0'; -- ack'en skippen, falls es ein "spezielles" zeichen ist (steht -- in abhaengigkeit zum vorherigen zeichen) if(not valid_char(data)) then next mainl; end if; -- wuenschswert waere das hier: -- > wait on s_backspace, s_take, do_it; -- geht aber leider nicht, weil sich die signale vllt schon -- geaendert haben run_inner := true; main_inner : while run_inner loop icwait(sys_clk, 1); run_inner := false; if s_backspace = '1' or s_take = '1' then icwait(sys_clk, 1); s_done <= '1'; wait on s_take; -- = '0' icwait(sys_clk, 1); s_done <= '0'; elsif do_it = '1' then -- dauert normalweiser noch laenger (parser braucht -- relativ lange) icwait(sys_clk, 7); finished <= '1'; wait on do_it; -- = '0' icwait(sys_clk, 1); finished <= '0'; icwait(sys_clk, 850); run_tc := false; else -- assert(false) report "history_tb: kann passieren. wenn tb haengt, dann hier auskommentieren"; run_inner := true; end if; end loop; end loop; report "=================="; end loop f_loop; icwait(sys_clk, 850); stop <= true; wait; end process; end architecture sim;