OpenCores
URL https://opencores.org/ocsvn/forth-cpu/forth-cpu/trunk

Subversion Repositories forth-cpu

[/] [forth-cpu/] [trunk/] [vga.vhd] - Diff between revs 3 and 5

Show entire file | Details | Blame | View Log

Rev 3 Rev 5
Line 1... Line 1...
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
--| @file vga.vhd
--| @file vga.vhd
--| @brief      Text Mode Video Controller VHDL Module and VT100
--| @brief      Text Mode Video Controller VHDL Module and VT100
--|             Terminal Emulator
--|             Terminal Emulator
--| @author     Javier Valcarce García
--| @author     Javier Valcarce García
--| @author     Richard James Howe
--| @author     Richard James Howe (vt100, vt100_tb, atoi, color attributes)
--| @copyright  Copyright 2007 Javier Valcarce García, 2017 Richard James Howe
--| @copyright  Copyright 2007 Javier Valcarce García, 2017, 2019 Richard James Howe
--| @license    LGPL version 3
--| @license    LGPL version 3
--| @email      javier.valcarce@gmail.com
--| @email      javier.valcarce@gmail.com
--| @note       (Modifications and repackaging by Richard James Howe)
--| @note       (Modifications and repackaging by Richard James Howe)
--|
--|
--| This is a modified version of the text terminal available at
--| This is a modified version of the text terminal available at
--| <https://opencores.org/project,interface_vga80x40>. Additions include per
--| <https://opencores.org/project,interface_vga80x40>. Additions include per
--| character attributes information and a VT100 terminal interface.
--| character attribute information (color, bold, reverse video, blink text)
 
--| and a VT100 terminal interface.
 
--|
 
--| See also <http://www.javiervalcarce.eu/html/vhdl-vga80x40-en.html>.
--|
--|
--| @todo Make a VT100 test bench
 
--| @todo Fix/Remove processing of semi-colon separated attribute values
 
--| @todo Add scrolling by changing the base address "text_a", adding
 
--| a line
 
--| @todo Turn this into a stand alone project
 
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
 
 
----- VGA Package -------------------------------------------------------------
----- VGA Package -------------------------------------------------------------
library ieee,work;
library ieee,work;
use ieee.std_logic_1164.all;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.numeric_std.all;
 
use work.util.common_generics;
 
 
package vga_pkg is
package vga_pkg is
        type vga_physical_interface is record
        type vga_physical_interface is record
                red:   std_ulogic_vector(2 downto 0);
                red:   std_ulogic_vector(2 downto 0);
                green: std_ulogic_vector(2 downto 0);
                green: std_ulogic_vector(2 downto 0);
Line 55... Line 54...
                        cry => '0',
                        cry => '0',
                        crx => '0',
                        crx => '0',
                        ctl => '0');
                        ctl => '0');
 
 
        component vga_top is
        component vga_top is
 
        generic(g: common_generics);
        port(
        port(
                clk:         in  std_ulogic;
                clk:         in  std_ulogic;
                clk25MHz:    in  std_ulogic;
                clk25MHz:    in  std_ulogic;
                rst:         in  std_ulogic;
                rst:         in  std_ulogic;
 
 
                -- VGA Text buffer interface
                -- VGA Text buffer interface
                vga_we_ram:  in  std_ulogic; -- Write enable RAM
                vga_we_ram:  in  std_ulogic; -- Write enable RAM
                vga_din:     in  std_ulogic_vector(15 downto 0);
                vga_din:     in  std_ulogic_vector(15 downto 0);
                vga_addr:    in  std_ulogic_vector(12 downto 0);
                vga_addr:    in  std_ulogic_vector(12 downto 0);
                vga_dout:    out std_ulogic_vector(15 downto 0):= (others => '0');
                base:        in  std_ulogic_vector(12 downto 0);
 
 
                -- VGA control registers
                -- VGA control registers
 
                i_font_sel:       in std_ulogic_vector(0 downto 0);
                i_vga_control_we: in vga_control_registers_we_interface;
                i_vga_control_we: in vga_control_registers_we_interface;
                i_vga_control:    in vga_control_registers_interface;
                i_vga_control:    in vga_control_registers_interface;
 
 
                o_vga:    out vga_physical_interface);
                o_vga:    out vga_physical_interface);
        end component;
        end component;
 
 
        -- VGA test bench, not-synthesizeable
 
        component vga_core is
        component vga_core is
 
        generic(g: common_generics);
        port (
        port (
                rst:       in  std_ulogic;
                rst:       in  std_ulogic;
                clk25MHz:  in  std_ulogic;
                clk25MHz:  in  std_ulogic;
                text_a:    out std_ulogic_vector(11 downto 0); -- text buffer
                text_a:    out std_ulogic_vector(11 downto 0); -- text buffer
                text_d:    in  std_ulogic_vector( 7 downto 0);
                text_d:    in  std_ulogic_vector(15 downto 0);
                font_a:    out std_ulogic_vector(11 downto 0); -- font buffer
                font_a:    out std_ulogic_vector(12 downto 0); -- font buffer
                font_d:    in  std_ulogic_vector( 7 downto 0);
                font_d:    in  std_ulogic_vector( 7 downto 0);
 
                font_sel:  in  std_ulogic_vector(0 downto 0);
                 --
                 --
                ocrx:      in  std_ulogic_vector(6 downto 0);
                ocrx:      in  std_ulogic_vector(6 downto 0);
                ocry:      in  std_ulogic_vector(5 downto 0);
                ocry:      in  std_ulogic_vector(5 downto 0);
                octl:      in  std_ulogic_vector(3 downto 0);
                octl:      in  std_ulogic_vector(4 downto 0);
                --
                --
                foreground_draw: out std_ulogic;
                o_vga: out vga_physical_interface);
                background_draw: out std_ulogic;
 
                hsync:     out std_ulogic;
 
                vsync:     out std_ulogic);
 
        end component;
        end component;
 
 
        component losr is
        component losr is
        generic (N: positive := 4);
        generic (g: common_generics; N: positive := 4);
        port
        port
        (
        (
                rst:  in  std_ulogic;
                rst:  in  std_ulogic;
                clk:  in  std_ulogic;
                clk:  in  std_ulogic;
                load: in  std_ulogic;
                load: in  std_ulogic;
Line 106... Line 105...
                do:   out std_ulogic := '0';
                do:   out std_ulogic := '0';
                di:   in  std_ulogic_vector(N - 1 downto 0));
                di:   in  std_ulogic_vector(N - 1 downto 0));
        end component;
        end component;
 
 
        component ctrm is
        component ctrm is
        generic (M: positive := 8);
        generic (g: common_generics; M: positive := 8);
        port (
        port (
                rst: in  std_ulogic; -- asynchronous rst
                rst: in  std_ulogic; -- asynchronous rst
                clk: in  std_ulogic;
                clk: in  std_ulogic;
                ce:  in  std_ulogic; -- enable counting
                ce:  in  std_ulogic; -- enable counting
                rs:  in  std_ulogic; -- synchronous rst
                rs:  in  std_ulogic; -- synchronous rst
                do:  out integer range (M-1) downto 0 := 0);
                do:  out integer range (M-1) downto 0 := 0);
        end component;
        end component;
 
 
        component vt100 is
        component vt100 is
 
        generic (g: common_generics);
        port(
        port(
                clk:        in  std_ulogic;
                clk:        in  std_ulogic;
                clk25MHz:   in  std_ulogic;
                clk25MHz:   in  std_ulogic;
                rst:        in  std_ulogic;
                rst:        in  std_ulogic;
                we:         in  std_ulogic;
                we:         in  std_ulogic;
Line 127... Line 127...
 
 
                busy:       out std_ulogic;
                busy:       out std_ulogic;
                o_vga:      out vga_physical_interface);
                o_vga:      out vga_physical_interface);
        end component;
        end component;
 
 
 
        -- VGA test bench, not-synthesizeable
        component vt100_tb is
        component vt100_tb is
                generic(clock_frequency: positive);
                generic(g: common_generics);
        end component;
        end component;
 
 
        component atoi is
        component atoi is
                generic(
                generic(g: common_generics; N: positive := 16);
                        N:      positive := 16);
 
                port(
                port(
                        clk:    in  std_ulogic;
                        clk:    in  std_ulogic;
                        rst:    in  std_ulogic;
                        rst:    in  std_ulogic;
                        we:     in  std_ulogic;
                        we:     in  std_ulogic;
                        init:   in  std_ulogic;
                        init:   in  std_ulogic;
                        char:   in  std_ulogic_vector(7 downto 0);
                        char:   in  std_ulogic_vector(7 downto 0);
                        char_o: out std_ulogic_vector(7 downto 0);
                        char_o: out std_ulogic_vector(7 downto 0);
                        done_o: out std_ulogic;
                        done_o: out std_ulogic;
                        ready:  out std_ulogic;
                        -- ready:  out std_ulogic;
                        n_o:    out unsigned(N - 1 downto 0));
                        n_o:    out unsigned(N - 1 downto 0));
        end component;
        end component;
 
 
end package;
end package;
 
 
----- VGA Package -------------------------------------------------------------
----- VGA Package -------------------------------------------------------------
 
 
----- VGA Test Bench ----------------------------------------------------------
----- VGA Test Bench ----------------------------------------------------------
 
 
library ieee;
library ieee, work;
use ieee.std_logic_1164.all;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.numeric_std.all;
use work.vga_pkg.all;
 
use ieee.math_real.all;
use ieee.math_real.all;
 
use work.vga_pkg.all;
use work.util.all;
use work.util.all;
 
 
entity vt100_tb is
entity vt100_tb is
        generic(clock_frequency: positive);
        generic(g: common_generics);
end entity;
end entity;
 
 
architecture behav of vt100_tb is
architecture behav of vt100_tb is
        constant clock_period: time := 1000 ms / clock_frequency;
        constant clock_period: time := 1000 ms / g.clock_frequency;
        signal clk, rst: std_ulogic := '0';
        signal clk, rst: std_ulogic := '0';
        signal stop:     std_ulogic := '0';
        signal stop:     std_ulogic := '0';
        signal clk25MHz, rst25MHz: std_ulogic := '0';
        signal clk25MHz, rst25MHz: std_ulogic := '0';
 
 
        signal char:     std_ulogic_vector(7 downto 0);
        signal char:     std_ulogic_vector(7 downto 0);
Line 187... Line 186...
        constant GREEN: string := CSI & "32m";
        constant GREEN: string := CSI & "32m";
        constant NL:  string := CR & LF;
        constant NL:  string := CR & LF;
        constant test_string: string := "Hello!" & HT & "World!" & RED & NL & "How are you?" & RESET & NL ;
        constant test_string: string := "Hello!" & HT & "World!" & RED & NL & "How are you?" & RESET & NL ;
        shared variable test_vector: ulogic_string(test_string'range) := to_std_ulogic_vector(test_string);
        shared variable test_vector: ulogic_string(test_string'range) := to_std_ulogic_vector(test_string);
        shared variable index: integer := 1; -- starts at '1' due to string range
        shared variable index: integer := 1; -- starts at '1' due to string range
 
 
 
        constant g_cs25MHz: common_generics := (clock_frequency => 25_000_000, asynchronous_reset => g.asynchronous_reset, delay => g.delay);
begin
begin
        cs: entity work.clock_source_tb
        cs: entity work.clock_source_tb
                generic map(clock_frequency => clock_frequency, hold_rst => 2)
                generic map(g => g, hold_rst => 2)
                port map(stop => stop, clk => clk, rst => rst);
                port map(stop => stop, clk => clk, rst => rst);
 
 
        cs25MHz: entity work.clock_source_tb
        cs25MHz: entity work.clock_source_tb
                generic map(clock_frequency => 25000000, hold_rst => 2)
                generic map(g => g_cs25MHz, hold_rst => 2)
                port map(stop => stop, clk => clk25MHz, rst => rst25MHz);
                port map(stop => stop, clk => clk25MHz, rst => rst25MHz);
 
 
 
 
        uut: work.vga_pkg.vt100
        uut: work.vga_pkg.vt100
 
        generic map(g => g)
        port map(
        port map(
                clk      => clk,
                clk      => clk,
                clk25MHz => clk25MHz,
                clk25MHz => clk25MHz,
                rst      => rst,
                rst      => rst,
                we       => we,
                we       => we,
Line 257... Line 259...
 
 
library ieee,work;
library ieee,work;
use ieee.std_logic_1164.all;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.numeric_std.all;
use work.vga_pkg.all;
use work.vga_pkg.all;
 
use work.util.common_generics;
 
 
entity atoi is
entity atoi is
        generic(
        generic(g: common_generics; N: positive := 16);
                N:      positive := 16);
 
        port(
        port(
                clk:    in  std_ulogic;
                clk:    in  std_ulogic;
                rst:    in  std_ulogic;
                rst:    in  std_ulogic;
                we:     in  std_ulogic;
                we:     in  std_ulogic;
                init:   in  std_ulogic;
                init:   in  std_ulogic;
                char:   in  std_ulogic_vector(7 downto 0);
                char:   in  std_ulogic_vector(7 downto 0);
                char_o: out std_ulogic_vector(7 downto 0);
                char_o: out std_ulogic_vector(7 downto 0);
                done_o: out std_ulogic;
                done_o: out std_ulogic;
                ready:  out std_ulogic;
                -- ready:  out std_ulogic;
                n_o:    out unsigned(N - 1 downto 0));
                n_o:    out unsigned(N - 1 downto 0));
end entity;
end entity;
 
 
architecture rlt of atoi is
architecture rlt of atoi is
        type state_type is (RESET, WAITING, COMMAND, ACCUMULATE, WRITE, FINISHED);
        type state_type is (RESET, WAITING, COMMAND, ACCUMULATE, WRITE, FINISHED);
Line 282... Line 284...
        signal n_c, n_n: unsigned(n_o'range)  := (others => '0');
        signal n_c, n_n: unsigned(n_o'range)  := (others => '0');
        signal f_c, f_n: boolean              := true;
        signal f_c, f_n: boolean              := true;
begin
begin
        char_o <= std_ulogic_vector(c_c);
        char_o <= std_ulogic_vector(c_c);
        n_o    <= n_c;
        n_o    <= n_c;
        ready  <= '1' when state_c = WAITING else '0';
        -- ready  <= '1' when state_c = WAITING else '0';
 
 
        process(clk, rst)
        process(clk, rst)
                variable akk: unsigned((2 * N) - 1 downto 0) := (others => '0');
                variable akk: unsigned((2 * N) - 1 downto 0) := (others => '0');
        begin
        begin
                if rst = '1' then
                if rst = '1' and g.asynchronous_reset then
                        state_n   <= RESET;
                        state_n   <= RESET;
                elsif rising_edge(clk) then
                elsif rising_edge(clk) then
 
                        if rst = '1' and not g.asynchronous_reset then
 
                                state_n <= RESET;
 
                        else
                        state_c <= state_n;
                        state_c <= state_n;
                        c_c     <= c_n;
                        c_c     <= c_n;
                        n_c     <= n_n;
                        n_c     <= n_n;
                        f_c     <= f_n;
                        f_c     <= f_n;
                        done_o  <= '0';
                        done_o  <= '0';
Line 346... Line 351...
                        if init = '1' then
                        if init = '1' then
                                assert state_c = FINISHED report "Lost Conversion" severity error;
                                assert state_c = FINISHED report "Lost Conversion" severity error;
                                state_n <= RESET;
                                state_n <= RESET;
                        end if;
                        end if;
                end if;
                end if;
 
                end if;
        end process;
        end process;
 
 
end architecture;
end architecture;
----- ATOI --------------------------------------------------------------------
----- ATOI --------------------------------------------------------------------
 
 
Line 367... Line 373...
 
 
library ieee,work;
library ieee,work;
use ieee.std_logic_1164.all;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.numeric_std.all;
use work.vga_pkg.all;
use work.vga_pkg.all;
 
use work.util.common_generics;
 
 
entity vt100 is
entity vt100 is
 
        generic(g: common_generics);
        port(
        port(
                clk:        in  std_ulogic;
                clk:        in  std_ulogic;
                clk25MHz:   in  std_ulogic;
                clk25MHz:   in  std_ulogic;
                rst:        in  std_ulogic;
                rst:        in  std_ulogic;
                we:         in  std_ulogic;
                we:         in  std_ulogic;
Line 390... Line 398...
        constant width:  positive := 80;
        constant width:  positive := 80;
        constant height: positive := 40;
        constant height: positive := 40;
        constant number: positive := 8;
        constant number: positive := 8;
 
 
        type state_type is (RESET, ACCEPT, NORMAL, WRAP, LIMIT, CSI, COMMAND,
        type state_type is (RESET, ACCEPT, NORMAL, WRAP, LIMIT, CSI, COMMAND,
        NUMBER1, NUMBER2, COMMAND1, COMMAND2, WRITE, ERASING, ATTRIB1, ATTRIB2, ADVANCE);
        NUMBER1, NUMBER2, COMMAND1, COMMAND2, WRITE, ERASING, ATTRIB, ADVANCE);
        signal state_c, state_n: state_type := RESET;
        signal state_c, state_n: state_type := RESET;
 
 
        constant esc:          unsigned(char'range) := x"1b";
 
        constant lsqb:         unsigned(char'range) := x"5b"; -- '['
 
        constant tab:          unsigned(char'range) := x"09";
        constant tab:          unsigned(char'range) := x"09";
        constant cr:           unsigned(char'range) := x"0d";
 
        constant lf:           unsigned(char'range) := x"0a";
 
        constant backspace:    unsigned(char'range) := x"08";
        constant backspace:    unsigned(char'range) := x"08";
 
        constant ascii_bell:   unsigned(char'range) := x"07";
 
        constant lf:           unsigned(char'range) := x"0a";
 
        constant cr:           unsigned(char'range) := x"0d";
 
        constant esc:          unsigned(char'range) := x"1b";
        constant blank:        unsigned(char'range) := x"20";
        constant blank:        unsigned(char'range) := x"20";
        constant ascii_c:      unsigned(char'range) := x"63"; -- c
        constant asterisk:     unsigned(char'range) := x"2A";
 
        constant ascii_7:      unsigned(char'range) := x"37"; -- '7'
 
        constant ascii_8:      unsigned(char'range) := x"38"; -- '8'
 
        constant lsqb:         unsigned(char'range) := x"5b"; -- '['
 
        constant ascii_c:      unsigned(char'range) := x"63"; -- 'c'
        constant attr_default: unsigned(7 downto 0) := "00111000";
        constant attr_default: unsigned(7 downto 0) := "00111000";
        constant ctl_default:  unsigned(4 downto 0) := "01111";
        constant ctl_default:  unsigned(4 downto 0) := "01111";
 
 
        signal addr:           std_ulogic_vector(12 downto 0) := (others => '0');
        signal addr:           std_ulogic_vector(12 downto 0) := (others => '0');
        signal data_we:        std_ulogic                     := '0';
        signal data_we:        std_ulogic                     := '0';
Line 440... Line 452...
 
 
        signal count_c, count_n:    unsigned(addr'range) := (others => '0');
        signal count_c, count_n:    unsigned(addr'range) := (others => '0');
        signal limit_c, limit_n:    unsigned(addr'high - 3 downto 0) := (others => '0');
        signal limit_c, limit_n:    unsigned(addr'high - 3 downto 0) := (others => '0');
 
 
        signal akk_done_o:  std_ulogic := '0';
        signal akk_done_o:  std_ulogic := '0';
        signal akk_ready_o: std_ulogic := '0';
        -- signal akk_ready_o: std_ulogic := '0';
        signal akk_init:    std_ulogic := '0';
        signal akk_init:    std_ulogic := '0';
        signal n_o:         unsigned(number - 1 downto 0) := (others => '0');
        signal n_o:         unsigned(number - 1 downto 0) := (others => '0');
        signal akk_char_o:  std_ulogic_vector(char'range)  := (others => '0');
        signal akk_char_o:  std_ulogic_vector(char'range)  := (others => '0');
 
 
 
        signal font_sel_c, font_sel_n: std_ulogic_vector(0 downto 0) := (others => '0');
 
 
 
        signal saved_x_n, saved_x_c:       unsigned(x'range)    := (others => '0');
 
        signal saved_y_n, saved_y_c:       unsigned(y'range)    := (others => '0');
 
        signal saved_attr_n, saved_attr_c: unsigned(attr_default'range) := (others => '0');
 
 
 
        signal reverse_video_c, reverse_video_n: boolean := false;
 
        signal base_n, base_c: unsigned(addr'high downto 4) := (others => '0');
 
        signal addr_sel:       unsigned(addr'range) := (others => '0');
 
 
 
        signal saved_base_n, saved_base_c: unsigned(base_c'range) := (others => '0');
 
        signal is_base_saved_n, is_base_saved_c: boolean := false;
 
 
begin
begin
        accumulator_0: work.vga_pkg.atoi
        accumulator_0: work.vga_pkg.atoi
                generic map(N => number)
                generic map(g => g, N => number)
                port map(
                port map(
                        clk    => clk,
                        clk    => clk,
                        rst    => rst,
                        rst    => rst,
                        we     => we,
                        we     => we,
                        init   => akk_init,
                        init   => akk_init,
                        char   => char,
                        char   => char,
                        char_o => akk_char_o,
                        char_o => akk_char_o,
                        done_o => akk_done_o,
                        done_o => akk_done_o,
                        ready  => akk_ready_o,
                        -- ready  => akk_ready_o,
                        n_o    => n_o);
                        n_o    => n_o);
 
 
        address: block
        address: block
                signal addr_int: unsigned(addr'range) := (others => '0');
 
                signal mul: unsigned(15 downto 0)     := (others => '0');
                signal mul: unsigned(15 downto 0)     := (others => '0');
 
                signal addr_int: unsigned(addr'range) := (others => '0');
        begin
        begin
                mul      <= to_unsigned(to_integer(y_c) * width, mul'length);
                mul      <= to_unsigned(to_integer(y_c) * width, mul'length);
                addr_int <= mul(addr_int'range) + ("000000" & x_c);
                addr_int <= mul(addr_int'range) + ("000000" & x_c);
                addr     <= std_ulogic_vector(addr_int) when state_c /= ERASING else std_ulogic_vector(count_c);
                addr_sel <= addr_int when state_c /= ERASING else count_c;
 
                addr     <= std_ulogic_vector(addr_sel + (base_c & "0000"));
        end block;
        end block;
 
 
        x_minus_one         <= x_c - 1;
        x_minus_one         <= x_c - 1;
        x_plus_one          <= x_c + 1;
        x_plus_one          <= x_c + 1;
        x_underflow         <= true when x_minus_one > width  - 1 else false;
        x_overflow          <= x_c         >  (width  - 1);
        x_overflow          <= true when x_c         > width  - 1 else false;
        x_underflow         <= x_minus_one >= (width  - 1);
        x_minus_one_limited <= (others => '0') when x_underflow else x_minus_one;
        x_minus_one_limited <= (others => '0') when x_underflow else x_minus_one;
        x_plus_one_limited  <= to_unsigned(width - 1, x_c'length) when x_overflow else x_plus_one;
        x_plus_one_limited  <= to_unsigned(width - 1, x_c'length) when x_overflow else x_plus_one;
 
 
        y_plus_one          <= y_c + 1;
        y_plus_one          <= y_c + 1;
        y_minus_one         <= y_c - 1;
        y_minus_one         <= y_c - 1;
        y_overflow          <= true when y_c         > height - 1 else false;
        y_overflow          <= y_c         >= (height - 1); -- NB. > for 1 more row, slightly off edge of screen
        y_underflow         <= true when y_minus_one > height - 1 else false;
        y_underflow         <= y_minus_one >  (height - 1);
        y_minus_one_limited <= (others => '0') when y_underflow else y_minus_one;
        y_minus_one_limited <= (others => '0') when y_underflow else y_minus_one;
        y_plus_one_limited  <= to_unsigned(height - 1, y_c'length) when y_overflow else y_plus_one;
        y_plus_one_limited  <= to_unsigned(height - 1, y_c'length) when y_overflow else y_plus_one;
 
 
        busy                <= '0' when state_c = ACCEPT
        busy <= '1' when state_c = ERASING
                                       or state_c = CSI
                        or state_c = WRITE
                                       or state_c = NUMBER1
                        or state_c = RESET
                                       or state_c = NUMBER2 else '1';
                        or state_c = WRAP
 
                        or state_c = ATTRIB
 
                        or state_c = ADVANCE
 
                        else '0';
 
 
        vga_blk: block
        vga_blk: block
                signal vga_din:    std_ulogic_vector(15 downto 0)     := (others => '0');
                signal vga_din:    std_ulogic_vector(15 downto 0)     := (others => '0');
                signal vga_ctr_we: vga_control_registers_we_interface := vga_control_registers_we_initialize;
                signal vga_ctr_we: vga_control_registers_we_interface := vga_control_registers_we_initialize;
                signal vga_ctr:    vga_control_registers_interface    := vga_control_registers_initialize;
                signal vga_ctr:    vga_control_registers_interface    := vga_control_registers_initialize;
                signal attr:       unsigned(attr_c'range)             := attr_default;
                signal attr:       unsigned(attr_c'range)             := attr_default;
                signal char:       std_ulogic_vector(c_c'range)       := (others => '0');
                signal ch:         std_ulogic_vector(c_c'range)       := (others => '0');
        begin
        begin
                char           <= x"2a" when conceal_c else std_ulogic_vector(c_c);
                ch             <= std_ulogic_vector(asterisk) when conceal_c else std_ulogic_vector(c_c);
                attr           <= attr_c when state_c /= ERASING else attr_default;
                attr           <= attr_c when state_c /= ERASING else attr_default;
                vga_din        <= std_ulogic_vector(attr) & char;
                vga_din        <= std_ulogic_vector(attr) & ch;
                vga_ctr.crx    <= std_ulogic_vector(x_plus_one);
                vga_ctr.crx    <= std_ulogic_vector(x_plus_one); -- not limited, goes off screen edge
                vga_ctr.cry    <= std_ulogic_vector(y_c);
                vga_ctr.cry    <= std_ulogic_vector(y_c);
                vga_ctr.ctl    <= std_ulogic_vector(ctl_c);
                vga_ctr.ctl    <= std_ulogic_vector(ctl_c);
                vga_ctr_we.crx <= cursor_we;
                vga_ctr_we.crx <= cursor_we;
                vga_ctr_we.cry <= cursor_we;
                vga_ctr_we.cry <= cursor_we;
                vga_ctr_we.ctl <= cursor_we;
                vga_ctr_we.ctl <= cursor_we;
 
 
                vga_0: work.vga_pkg.vga_top
                vga_0: work.vga_pkg.vga_top
 
                generic map(g => g)
                port map(
                port map(
                        clk               =>  clk,
                        clk               =>  clk,
                        clk25MHz          =>  clk25MHz,
                        clk25MHz          =>  clk25MHz,
                        rst               =>  rst,
                        rst               =>  rst,
                        vga_we_ram        =>  data_we,
                        vga_we_ram        =>  data_we,
                        vga_din           =>  vga_din,
                        vga_din           =>  vga_din,
                        vga_addr          =>  addr,
                        vga_addr          =>  addr,
 
                        base(base_c'range)=>  std_ulogic_vector(base_c),
 
                        base(3 downto 0)  =>  "0000",
 
                        i_font_sel        =>  font_sel_c,
                        i_vga_control_we  =>  vga_ctr_we,
                        i_vga_control_we  =>  vga_ctr_we,
                        i_vga_control     =>  vga_ctr,
                        i_vga_control     =>  vga_ctr,
                        o_vga             =>  o_vga);
                        o_vga             =>  o_vga);
        end block;
        end block;
 
 
Line 527... Line 561...
        -- CUB, CNL, CPL and CHA
        -- CUB, CNL, CPL and CHA
        fsm: process(clk, rst)
        fsm: process(clk, rst)
                variable limit_value: unsigned(addr'range) := (others => '0');
                variable limit_value: unsigned(addr'range) := (others => '0');
                variable repeat:      boolean    := false;
                variable repeat:      boolean    := false;
                variable exit_repeat: state_type := RESET;
                variable exit_repeat: state_type := RESET;
 
                procedure reverse_video(a: unsigned(2 downto 0); foreground: boolean) is
        begin
        begin
                if rst = '1' then
                        if foreground then
 
                                if reverse_video_c then
 
                                        attr_n(2 downto 0) <= a;
 
                                else
 
                                        attr_n(5 downto 3) <= a;
 
                                end if;
 
                        else
 
                                if reverse_video_c then
 
                                        attr_n(5 downto 3) <= a;
 
                                else
 
                                        attr_n(2 downto 0) <= a;
 
                                end if;
 
                        end if;
 
                end procedure;
 
        begin
 
                if rst = '1' and g.asynchronous_reset then
                        state_c <= RESET;
                        state_c <= RESET;
                elsif rising_edge(clk) then
                elsif rising_edge(clk) then
 
                        if rst = '1' and not g.asynchronous_reset then
 
                                state_c <= RESET;
 
                        else
                        x_c       <= x_n;
                        x_c       <= x_n;
                        y_c       <= y_n;
                        y_c       <= y_n;
                        c_c       <= c_n;
                        c_c       <= c_n;
                        count_c   <= count_n;
                        count_c   <= count_n;
                        limit_c   <= limit_n;
                        limit_c   <= limit_n;
Line 545... Line 598...
                        cursor_we <= '0';
                        cursor_we <= '0';
                        akk_init  <= '0';
                        akk_init  <= '0';
                        attr_c    <= attr_n;
                        attr_c    <= attr_n;
                        ctl_c     <= ctl_n;
                        ctl_c     <= ctl_n;
                        conceal_c <= conceal_n;
                        conceal_c <= conceal_n;
 
                                font_sel_c      <= font_sel_n;
 
                                saved_x_c       <= saved_x_n;
 
                                saved_y_c       <= saved_y_n;
 
                                saved_attr_c    <= saved_attr_n;
 
                                reverse_video_c <= reverse_video_n;
 
                                base_c          <= base_n;
 
                                saved_base_c    <= saved_base_n;
 
                                is_base_saved_c <= is_base_saved_n;
 
 
                        if state_c = RESET then
                        if state_c = RESET then
                                n1_n      <= (others => '0');
                                n1_n      <= (others => '0');
                                n2_n      <= (others => '0');
                                n2_n      <= (others => '0');
                                x_n       <= (others => '0');
                                x_n       <= (others => '0');
                                y_n       <= (others => '0');
                                y_n       <= (others => '0');
                                c_n       <= (others => '0');
                                c_n       <= (others => '0');
                                count_n   <= (others => '0');
                                count_n   <= (others => '0');
                                limit_n   <= (others => '0');
                                limit_n   <= (others => '0');
 
                                        saved_x_n    <= (others => '0');
 
                                        saved_y_n    <= (others => '0');
 
                                        saved_attr_n <= (others => '0');
 
                                        font_sel_n   <= (others => '0');
                                state_n   <= ACCEPT;
                                state_n   <= ACCEPT;
                                attr_n    <= attr_default;
                                attr_n    <= attr_default;
                                ctl_n     <= ctl_default;
                                ctl_n     <= ctl_default;
                                conceal_n <= false;
                                conceal_n <= false;
 
                                        reverse_video_n <= false;
 
                                        base_n       <= (others => '0');
 
                                        is_base_saved_n <= false;
 
                                        saved_base_n <= (others => '0');
                        elsif state_c = ACCEPT then
                        elsif state_c = ACCEPT then
                                if we = '1' then
                                if we = '1' then
                                        c_n   <= unsigned(char);
                                        c_n   <= unsigned(char);
                                        state_n <= NORMAL;
                                        state_n <= NORMAL;
                                end if;
                                end if;
 
                                        -- This behavior does not really mix well
 
                                        -- with the eForth interpreter.
 
                                        --
 
                                        -- if is_base_saved_c then
 
                                        --      is_base_saved_n <= false;
 
                                        --      base_n          <= saved_base_c;
 
                                        -- end if;
                        elsif state_c = NORMAL then
                        elsif state_c = NORMAL then
                                case c_c is
                                case c_c is
                                when tab =>
                                when tab =>
                                        x_n     <= (x_c and "1111000") + 8;
                                        x_n     <= (x_c and "1111000") + 8;
                                        state_n <= ERASING;
                                        state_n <= ERASING;
                                        c_n     <= blank;
                                        c_n     <= blank;
                                        limit_value := unsigned(addr and "1111111111000") + 8;
                                        limit_value := unsigned(addr and "1111111111000") + 8;
                                        limit_n <= limit_value(limit_n'high + 3 downto limit_n'low + 3);
                                        limit_n <= limit_value(limit_n'high + 3 downto limit_n'low + 3);
                                        count_n <= unsigned(addr);
                                        count_n <= unsigned(addr);
 
                                        when ascii_bell =>
 
                                                ctl_n(4) <= not ctl_c(4); -- ctr_n(4) goes to edge triggered logic
 
                                                state_n  <= ACCEPT;
                                when cr =>
                                when cr =>
                                        y_n     <= y_plus_one;
                                        y_n     <= y_plus_one;
                                        state_n <= WRAP;
                                        state_n <= WRAP;
                                when lf =>
                                when lf =>
                                        x_n     <= (others => '0');
                                        x_n     <= (others => '0');
Line 597... Line 676...
                                        c_n <= unsigned(char);
                                        c_n <= unsigned(char);
                                        state_n <= COMMAND;
                                        state_n <= COMMAND;
                                end if;
                                end if;
                        elsif state_c = COMMAND then
                        elsif state_c = COMMAND then
                                case c_c is
                                case c_c is
                                when ascii_c => -- @todo Erase screen as well
                                        when ascii_c =>
                                        state_n <= RESET;
                                                x_n     <= (others => '0');
 
                                                y_n     <= (others => '0');
 
                                                c_n     <= blank;
 
                                                count_n <= (others => '0');
 
                                                limit_n <= "1000000000";
 
                                                state_n <= ERASING;
 
                                                base_n  <= (others => '0');
                                when lsqb =>
                                when lsqb =>
                                        state_n  <= NUMBER1;
                                        state_n  <= NUMBER1;
                                        akk_init <= '1';
                                        akk_init <= '1';
 
 
 
                                        when ascii_7 => -- 'ESC 7'; Save Cursor and Attributes
 
                                                saved_x_n    <= x_c;
 
                                                saved_y_n    <= y_c;
 
                                                saved_attr_n <= attr_c;
 
                                                state_n      <= ACCEPT;
 
                                        when ascii_8 => -- 'ESC 8'; Restore Cursor and Attributes
 
                                                x_n          <= saved_x_c;
 
                                                y_n          <= saved_y_c;
 
                                                attr_n       <= saved_attr_c;
 
                                                state_n      <= ACCEPT;
                                when others => -- Error
                                when others => -- Error
                                        state_n <= ACCEPT;
                                        state_n <= ACCEPT;
                                end case;
                                end case;
                        elsif state_c = NUMBER1 then
                        elsif state_c = NUMBER1 then
                                if akk_done_o = '1' then
                                if akk_done_o = '1' then
Line 645... Line 741...
                                        x_n      <= n1_c(x_n'range);
                                        x_n      <= n1_c(x_n'range);
                                        state_n  <= LIMIT;
                                        state_n  <= LIMIT;
                                when x"4a" => -- CSI n 'J'
                                when x"4a" => -- CSI n 'J'
                                        x_n       <= (others => '0');
                                        x_n       <= (others => '0');
                                        y_n       <= (others => '0');
                                        y_n       <= (others => '0');
 
                                                base_n    <= (others => '0');
                                        cursor_we <= '1';
                                        cursor_we <= '1';
                                        state_n   <= ERASING;
                                        state_n   <= ERASING;
                                        c_n       <= blank;
                                        c_n       <= blank;
                                        count_n   <= (others => '0');
                                        count_n   <= (others => '0');
                                        limit_n   <= "1000000000";
                                        limit_n   <= "1000000000";
                                when x"3b" => -- ESC n ';' ...
                                when x"3b" => -- ESC n ';' ...
                                        state_n <= NUMBER2;
                                        state_n <= NUMBER2;
                                        akk_init <= '1';
                                        akk_init <= '1';
                                when x"6d" => -- CSI n 'm' : SGR
                                when x"6d" => -- CSI n 'm' : SGR
                                        state_n <= ATTRIB1;
                                                state_n <= ATTRIB;
 
 
 
                                        -- NB. Number parameter does nothing.
                                when x"53" => -- CSI n 'S' : scroll up
                                when x"53" => -- CSI n 'S' : scroll up
                                        ctl_n(4) <= '0';
                                                saved_base_n <= base_c;
 
                                                is_base_saved_n <= true;
 
                                                base_n   <= (others => '0');
                                        state_n  <= WRITE;
                                        state_n  <= WRITE;
                                when x"54" => -- CSI n 'T' : scroll down
                                when x"54" => -- CSI n 'T' : scroll down
                                        ctl_n(4) <= '1';
 
                                        state_n  <= WRITE;
                                        state_n  <= WRITE;
                                -- when x"3f" => -- ESC ? 25 (l,h)
                                                if is_base_saved_c then
                                --      state_n  <= NUMBER2;
                                                        base_n <= saved_base_c;
                                --      akk_init <= '1';
                                                        is_base_saved_n <= false;
 
                                                end if;
 
                                        when x"73" => -- CSI 's': SCP (Secure, Contain, Protect the Cursor Position)
 
                                                saved_x_n    <= x_c;
 
                                                saved_y_n    <= y_c;
 
                                                state_n      <= ACCEPT;
 
                                        when x"75" => -- CSI 'u': RCP Restore Cursor Position
 
                                                x_n          <= saved_x_c;
 
                                                y_n          <= saved_y_c;
 
                                                state_n      <= ACCEPT;
 
 
                                -- @warning This is an extension! It is for setting the
                                        -- This is an extension, it is for setting the
                                -- control lines of the VGA module directly.
                                -- control lines of the VGA module directly.
                                when x"78" => -- ESC n 'x' : Set VGA control registers directly
                                when x"78" => -- ESC n 'x' : Set VGA control registers directly
                                        ctl_n    <= n1_c(ctl_n'range);
                                        ctl_n    <= n1_c(ctl_n'range);
                                        state_n  <= WRITE;
                                        state_n  <= WRITE;
                                when others => -- Error
                                when others => -- Error
                                        state_n <= ACCEPT;
                                        state_n <= ACCEPT;
                                end case;
                                end case;
 
 
                                if repeat then
                                if repeat then
                                        if n1_c = 0 then
                                                if n1_c <= 1 then
                                                state_n <= exit_repeat;
                                                state_n <= exit_repeat;
                                        else
                                        else
                                                n1_n <= n1_c - 1;
                                                n1_n <= n1_c - 1;
                                        end if;
                                        end if;
                                end if;
                                end if;
Line 699... Line 808...
                                        y_n       <= n1_c(y_n'range) - 1;
                                        y_n       <= n1_c(y_n'range) - 1;
                                        x_n       <= n2_c(x_n'range) - 1;
                                        x_n       <= n2_c(x_n'range) - 1;
                                        cursor_we <= '1';
                                        cursor_we <= '1';
                                        state_n   <= LIMIT;
                                        state_n   <= LIMIT;
                                when x"6d" => -- ESC n ';' m 'm'
                                when x"6d" => -- ESC n ';' m 'm'
                                        state_n <= ATTRIB1;
                                                state_n <= ATTRIB;
                                when others =>
                                when others =>
                                        state_n <= ACCEPT;
                                        state_n <= ACCEPT;
                                end case;
                                end case;
                        elsif state_c = WRAP then
                        elsif state_c = WRAP then
                                if x_overflow then
                                if x_overflow then
                                        x_n <= (others => '0');
                                        x_n <= (others => '0');
                                        y_n <= y_plus_one;
                                        y_n <= y_plus_one;
                                elsif y_overflow then
                                elsif y_overflow then
                                        x_n     <= (others => '0');
                                        x_n     <= (others => '0');
                                        y_n     <= (others => '0');
                                                y_n     <= y_minus_one;
                                        state_n <= ERASING;
                                        state_n <= ERASING;
                                        c_n     <= blank;
                                        c_n     <= blank;
                                        count_n <= (others => '0');
                                                count_n <= unsigned(addr_sel);
                                        limit_n <= "1000000000";
                                                limit_value := unsigned(addr_sel) + (3*width);
 
                                                limit_n <= limit_value(limit_n'high + 3 downto limit_n'low + 3);
 
                                                base_n  <= base_c + (width / 16);
                                else
                                else
                                        state_n <= WRITE;
                                        state_n <= WRITE;
                                end if;
                                end if;
                        elsif state_c = LIMIT then
                        elsif state_c = LIMIT then
                                if x_overflow then
                                if x_overflow then
Line 735... Line 846...
                                        count_n <= count_c + 1;
                                        count_n <= count_c + 1;
                                        data_we <= '1';
                                        data_we <= '1';
                                else
                                else
                                        state_n <= WRAP;
                                        state_n <= WRAP;
                                end if;
                                end if;
                        elsif state_c = ATTRIB1 then
                                elsif state_c = ATTRIB then
                                case n1_c is
                                case n1_c is
                                when x"00"  =>
                                when x"00"  =>
                                        attr_n    <= attr_default;
                                        attr_n    <= attr_default;
                                        conceal_n <= false;
                                        conceal_n <= false;
 
                                                reverse_video_n <= false;
                                when x"01"  => attr_n(6) <= '1'; -- bold
                                when x"01"  => attr_n(6) <= '1'; -- bold
                                when x"07"  => attr_n(7) <= '1'; -- reverse video
                                        -- when x"02"  => -- faint
 
                                        when x"16"  => attr_n(6) <= '0'; -- normal brightness
 
                                        when x"05"  => attr_n(7) <= '1'; -- slow blink
 
                                        when x"19"  => attr_n(7) <= '0'; -- blink off
 
                                        when x"07"  =>
 
                                                if not reverse_video_c then
 
                                                        attr_n    <= attr_c(7 downto 6) & attr_c(2 downto 0) & attr_c(5 downto 3);
 
                                                end if;
 
                                                reverse_video_n <= true;
 
                                        when x"1B" =>
 
                                                if reverse_video_c then
 
                                                        attr_n    <= attr_c(7 downto 6) & attr_c(2 downto 0) & attr_c(5 downto 3);
 
                                                end if;
 
                                                reverse_video_n <= false;
                                when x"08"  => conceal_n <= true;
                                when x"08"  => conceal_n <= true;
 
                                        when x"1C"  => conceal_n <= false;
 
 
 
                                        when x"0A"  => font_sel_n <= (others => '0');
 
                                        when x"0B"  => font_sel_n <= "1";
 
 
                                -- when x"6c" => if n2_c = x"19" then ctl_n(2) <= '0'; end if; -- l, hide cursor
                                        when x"1E"  => reverse_video("000", true); -- 30
                                -- when x"68" => if n2_c = x"19" then ctl_n(2) <= '1'; end if; -- h, show cursor
                                        when x"1F"  => reverse_video("001", true);
 
                                        when x"20"  => reverse_video("010", true);
 
                                        when x"21"  => reverse_video("011", true);
 
                                        when x"22"  => reverse_video("100", true);
 
                                        when x"23"  => reverse_video("101", true);
 
                                        when x"24"  => reverse_video("110", true);
 
                                        when x"25"  => reverse_video("111", true);
 
 
 
                                        when x"28"  => reverse_video("000", false); -- 40
 
                                        when x"29"  => reverse_video("001", false);
 
                                        when x"2A"  => reverse_video("010", false);
 
                                        when x"2B"  => reverse_video("011", false);
 
                                        when x"2C"  => reverse_video("100", false);
 
                                        when x"2D"  => reverse_video("101", false);
 
                                        when x"2E"  => reverse_video("110", false);
 
                                        when x"2F"  => reverse_video("111", false);
 
 
                                -- @todo This should make the _text_ blink, not the cursor!
 
                                when x"05"  => ctl_n(1) <= '1'; -- blink slow
 
                                when x"19"  => ctl_n(1) <= '0'; -- blink off
 
 
 
                                when x"1E"  => attr_n(5 downto 3) <= "000"; -- 30
 
                                when x"1F"  => attr_n(5 downto 3) <= "001";
 
                                when x"20"  => attr_n(5 downto 3) <= "010";
 
                                when x"21"  => attr_n(5 downto 3) <= "011";
 
                                when x"22"  => attr_n(5 downto 3) <= "100";
 
                                when x"23"  => attr_n(5 downto 3) <= "101";
 
                                when x"24"  => attr_n(5 downto 3) <= "110";
 
                                when x"25"  => attr_n(5 downto 3) <= "111";
 
 
 
                                when x"28"  => attr_n(2 downto 0) <= "000"; -- 40
 
                                when x"29"  => attr_n(2 downto 0) <= "001";
 
                                when x"2A"  => attr_n(2 downto 0) <= "010";
 
                                when x"2B"  => attr_n(2 downto 0) <= "011";
 
                                when x"2C"  => attr_n(2 downto 0) <= "100";
 
                                when x"2D"  => attr_n(2 downto 0) <= "101";
 
                                when x"2E"  => attr_n(2 downto 0) <= "110";
 
                                when x"2F"  => attr_n(2 downto 0) <= "111";
 
                                when others =>
                                when others =>
                                end case;
                                end case;
                                state_n <= ATTRIB2;
 
                        elsif state_c = ATTRIB2 then
 
                                -- @todo Implement two attributes in a row
 
                                state_n <= ACCEPT;
                                state_n <= ACCEPT;
                        else
                        else
                                state_n <= RESET;
                                state_n <= RESET;
                                report "Invalid State" severity failure;
                                report "Invalid State" severity failure;
                        end if;
                        end if;
                end if;
                end if;
 
                end if;
        end process;
        end process;
end architecture;
end architecture;
----- VT100 Terminal Emulator -------------------------------------------------
----- VT100 Terminal Emulator -------------------------------------------------
 
 
----- VGA Top Level Component -------------------------------------------------
----- VGA Top Level Component -------------------------------------------------
library ieee,work;
library ieee,work;
use ieee.std_logic_1164.all;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.numeric_std.all;
use work.vga_pkg.all;
use work.vga_pkg.all;
use work.util.file_format;
use work.util.file_format;
use work.util.FILE_HEX;
use work.util.file_hex;
use work.util.FILE_BINARY;
use work.util.file_binary;
 
use work.util.common_generics;
 
 
entity vga_top is
entity vga_top is
 
        generic(g: common_generics);
        port(
        port(
                clk:              in  std_ulogic;
                clk:              in  std_ulogic;
                clk25MHz:         in  std_ulogic;
                clk25MHz:         in  std_ulogic;
                rst:              in  std_ulogic;
                rst:              in  std_ulogic;
 
 
                -- VGA Text buffer interface
                -- VGA Text buffer interface
                vga_we_ram:       in  std_ulogic; -- Write enable RAM
                vga_we_ram:       in  std_ulogic; -- Write enable RAM
                vga_din:          in  std_ulogic_vector(15 downto 0);
                vga_din:          in  std_ulogic_vector(15 downto 0);
                vga_addr:         in  std_ulogic_vector(12 downto 0);
                vga_addr:         in  std_ulogic_vector(12 downto 0);
                vga_dout:         out std_ulogic_vector(15 downto 0) := (others => '0');
                base:             in  std_ulogic_vector(12 downto 0);
 
 
                -- VGA control registers
                -- VGA control registers
 
                i_font_sel:       in std_ulogic_vector(0 downto 0);
                i_vga_control_we: in vga_control_registers_we_interface;
                i_vga_control_we: in vga_control_registers_we_interface;
                i_vga_control:    in vga_control_registers_interface;
                i_vga_control:    in vga_control_registers_interface;
 
 
                o_vga:            out vga_physical_interface);
                o_vga:            out vga_physical_interface);
end;
end;
 
 
architecture behav of vga_top is
architecture behav of vga_top is
 
 
        -- Setup for text buffer memory
        -- Setup for text buffer memory
        constant text_addr_length: positive    := 13;
        constant text_addr_length: positive    := 13;
        constant text_data_length: positive    := 16;
        constant text_data_length: positive    := 16;
        constant text_file_name:   string      := "text.hex";
        constant text_file_name:   string      := "text.hex";
        constant text_file_type:   file_format := FILE_HEX;
        constant text_file_type:   file_format := FILE_HEX;
 
 
        -- Setup for font buffer memory
        -- Setup for font buffer memory
        constant font_addr_length: positive    := 12;
        constant font_addr_length: positive    := 13;
        constant font_data_length: positive    := 8;
        constant font_data_length: positive    := 8;
        constant font_file_name:   string      := "font.bin";
        constant font_file_name:   string      := "font.bin";
        constant font_file_type:   file_format := FILE_BINARY;
        constant font_file_type:   file_format := FILE_BINARY;
 
 
        -- Internal signals for mapping output <--> VGA module
        -- Internal signals for mapping output <--> VGA module
Line 835... Line 958...
        signal  text_din:        std_ulogic_vector(15 downto 0) := (others => '0');
        signal  text_din:        std_ulogic_vector(15 downto 0) := (others => '0');
        signal  text_addr:       std_ulogic_vector(11 downto 0) := (others => '0');
        signal  text_addr:       std_ulogic_vector(11 downto 0) := (others => '0');
        signal  text_addr_full:  std_ulogic_vector(12 downto 0) := (others => '0');
        signal  text_addr_full:  std_ulogic_vector(12 downto 0) := (others => '0');
 
 
        -- Font ROM signals, ROM<-->VGA module
        -- Font ROM signals, ROM<-->VGA module
        signal  font_addr:       std_ulogic_vector(11 downto 0) := (others => '0');
        signal  font_addr:       std_ulogic_vector(12 downto 0) := (others => '0');
        signal  font_dout:       std_ulogic_vector( 7 downto 0) := (others => '0');
        signal  font_dout:       std_ulogic_vector( 7 downto 0) := (others => '0');
 
 
        signal  control_c, control_n: vga_control_registers_interface := vga_control_registers_initialize;
        signal  control_c, control_n: vga_control_registers_interface := vga_control_registers_initialize;
 
 
        signal  foreground_draw: std_ulogic := '0';
        signal  foreground_draw: std_ulogic := '0';
        signal  background_draw: std_ulogic := '0';
        signal  background_draw: std_ulogic := '0';
begin
begin
 
 
        color_block: block
 
                signal red_on:   std_ulogic := '0';
 
                signal green_on: std_ulogic := '0';
 
                signal blue_on:  std_ulogic := '0';
 
                signal bold:     std_ulogic := '0';
 
                signal reverse:  std_ulogic := '0';
 
                signal set:      std_ulogic_vector(2 downto 0) := "110";
 
                signal final:    std_ulogic_vector(2 downto 0) := "111";
 
        begin
 
                bold        <= text_dout(14);
 
                reverse     <= text_dout(15);
 
                set         <= "100" when bold = '0' else "111";
 
                final       <= set   when reverse = '0' else not set;
 
 
 
                red_on      <= text_dout(11) when foreground_draw = '1' else
 
                               text_dout(8)  when background_draw = '1' else '0';
 
                green_on    <= text_dout(12) when foreground_draw = '1' else
 
                               text_dout(9)  when background_draw = '1' else '0';
 
                blue_on     <= text_dout(13) when foreground_draw = '1' else
 
                               text_dout(10) when background_draw = '1' else '0';
 
 
 
                o_vga.red   <= final             when red_on    = '1' else "000";
 
                o_vga.green <= final             when green_on  = '1' else "000";
 
                o_vga.blue  <= final(2 downto 1) when blue_on   = '1' else "00";
 
        end block;
 
 
 
        -- Internal control registers
 
        -- Next state on clk edge rising
 
        vga_ns: process(clk, rst)
        vga_ns: process(clk, rst)
        begin
        begin
                if rst = '1' then
                if rst = '1' and g.asynchronous_reset then
                        control_c   <= vga_control_registers_initialize;
                        control_c   <= vga_control_registers_initialize;
                elsif rising_edge(clk) then
                elsif rising_edge(clk) then
 
                        if rst = '1' and not g.asynchronous_reset then
 
                                control_c <= vga_control_registers_initialize;
 
                        else
                        control_c   <= control_n;
                        control_c   <= control_n;
                end if;
                end if;
 
                end if;
        end process;
        end process;
 
 
        -- Internal control register
 
        -- We write into the registers here.
 
        vga_creg_we: process(
        vga_creg_we: process(
                control_c,
                control_c,
                i_vga_control,
                i_vga_control,
                i_vga_control_we)
                i_vga_control_we)
        begin
        begin
Line 895... Line 992...
                if i_vga_control_we.crx = '1' then control_n.crx <= i_vga_control.crx; end if;
                if i_vga_control_we.crx = '1' then control_n.crx <= i_vga_control.crx; end if;
                if i_vga_control_we.cry = '1' then control_n.cry <= i_vga_control.cry; end if;
                if i_vga_control_we.cry = '1' then control_n.cry <= i_vga_control.cry; end if;
                if i_vga_control_we.ctl = '1' then control_n.ctl <= i_vga_control.ctl; end if;
                if i_vga_control_we.ctl = '1' then control_n.ctl <= i_vga_control.ctl; end if;
        end process;
        end process;
 
 
        -- The actual VGA module
        u_vga: work.vga_pkg.vga_core
        u_vga: work.vga_pkg.vga_core port map (
                generic map(g => g)
 
                port map (
                rst       => rst,
                rst       => rst,
                clk25MHz  => clk25MHz,
                clk25MHz  => clk25MHz,
 
 
                text_a    => text_addr,
                text_a    => text_addr,
                text_d    => text_dout(7 downto 0),
                text_d    => text_dout,
 
 
                font_a    => font_addr,
                font_a    => font_addr,
                font_d    => font_dout,
                font_d    => font_dout,
 
 
 
                font_sel  => i_font_sel,
 
 
                ocrx      => control_c.crx,
                ocrx      => control_c.crx,
                ocry      => control_c.cry,
                ocry      => control_c.cry,
                octl      => control_c.ctl(3 downto 0),
                octl      => control_c.ctl,
 
 
 
                o_vga     => o_vga);
 
 
 
        text_addr_full <= std_ulogic_vector(unsigned(base) + unsigned(text_addr));
 
 
                foreground_draw => foreground_draw,
        u_text_memory: entity work.dual_port_block_ram -- holds at least 80x40 characters
                background_draw => background_draw,
        generic map(g => g,
                hsync     => o_vga.hsync,
 
                vsync     => o_vga.vsync);
 
 
 
        text_addr_full <= control_c.ctl(4) & text_addr;
 
 
 
        --| @brief This RAM module holds the text we want to display on to the
 
        --| monitor. The text buffer holds at least 80*40 characters.
 
        u_text: entity work.dual_port_block_ram
 
        generic map(
 
            addr_length => text_addr_length,
            addr_length => text_addr_length,
            data_length => text_data_length,
            data_length => text_data_length,
            file_name   => text_file_name,
            file_name   => text_file_name,
            file_type   => text_file_type)
            file_type   => text_file_type)
        port map (
        port map (
Line 932... Line 1027...
                -- External interface
                -- External interface
                a_dwe   => vga_we_ram,
                a_dwe   => vga_we_ram,
                a_dre   => '1',
                a_dre   => '1',
                a_addr  => vga_addr,
                a_addr  => vga_addr,
                a_din   => vga_din,
                a_din   => vga_din,
                a_dout  => vga_dout,
                a_dout  => open,
                -- Internal interface
                -- Internal interface
                b_clk   => clk25MHz,
                b_clk   => clk25MHz,
                b_dwe   => '0',
                b_dwe   => '0',
                b_dre   => '1',
                b_dre   => '1',
                b_addr  => text_addr_full,
                b_addr  => text_addr_full,
                b_din   => (others => '0'),
                b_din   => (others => '0'),
                b_dout  => text_dout);
                b_dout  => text_dout);
 
 
        --| VGA Font memory
        u_font_memory: entity work.single_port_block_ram
        u_font: entity work.single_port_block_ram
        generic map(g => g,
        generic map(
 
                addr_length => font_addr_length,
                addr_length => font_addr_length,
                data_length => font_data_length,
                data_length => font_data_length,
                file_name   => font_file_name,
                file_name   => font_file_name,
                file_type   => font_file_type)
                file_type   => font_file_type)
        port map (
        port map (
Line 965... Line 1059...
----- VGA Core ----------------------------------------------------------------
----- VGA Core ----------------------------------------------------------------
 
 
library ieee;
library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.numeric_std.all;
use work.vga_pkg.ctrm;
use work.vga_pkg.all;
use work.vga_pkg.losr;
use work.util.common_generics;
 
 
entity vga_core is
entity vga_core is
 
        generic(g: common_generics);
        port (
        port (
                rst:      in  std_ulogic;
                rst:      in  std_ulogic;
                clk25MHz: in  std_ulogic;
                clk25MHz: in  std_ulogic;
                text_a:   out std_ulogic_vector(11 downto 0); -- text buffer
                text_a:   out std_ulogic_vector(11 downto 0); -- text buffer
                text_d:   in  std_ulogic_vector( 7 downto 0);
                text_d:   in  std_ulogic_vector(15 downto 0);
                font_a:   out std_ulogic_vector(11 downto 0); -- font buffer
                font_a:   out std_ulogic_vector(12 downto 0); -- font buffer
                font_d:   in  std_ulogic_vector( 7 downto 0);
                font_d:   in  std_ulogic_vector( 7 downto 0);
 
                font_sel: in  std_ulogic_vector(0 downto 0);
                 --
                 --
                ocrx:     in  std_ulogic_vector(6 downto 0);
                ocrx:     in  std_ulogic_vector(6 downto 0);
                ocry:     in  std_ulogic_vector(5 downto 0);
                ocry:     in  std_ulogic_vector(5 downto 0);
                octl:     in  std_ulogic_vector(3 downto 0);
                octl:     in  std_ulogic_vector(4 downto 0);
                --
                --
                foreground_draw: out std_ulogic; -- If '1', we should draw the character
                o_vga:    out vga_physical_interface);
                background_draw: out std_ulogic;
 
                hsync:     out std_ulogic;
 
                vsync:     out std_ulogic);
 
end entity;
end entity;
 
 
architecture rtl of vga_core is
architecture rtl of vga_core is
 
 
        signal foreground_draw_int, background_draw_int: std_ulogic := '0';
        signal foreground_draw_int, background_draw_int: std_ulogic := '0';
        signal hsync_int: std_ulogic := '1';
        signal hsync_int: std_ulogic := '1';
        signal vsync_int: std_ulogic := '1';
        signal vsync_int: std_ulogic := '1';
 
 
        signal blank: std_ulogic := '0';
        signal blank: std_ulogic := '0';
        signal hctr:  integer range 793 downto 0 := 0;
        signal hctr:  integer range 793 downto 0 := 0;
        signal vctr:  integer range 524 downto 0 := 0;
        signal vctr:  integer range 524 downto 0 := 0;
 
 
        -- character/pixel position on the screen
        -- character/pixel position on the screen
        signal scry:  integer range 39 downto 0 := 0;  -- chr row   < 40 (6 bits)
        signal scry_text:  integer range 39 downto 0 := 0; -- chr row   < 40 (6 bits)
        signal scrx:  integer range 79 downto 0 := 0;  -- chr col   < 80 (7 bits)
        signal scrx_text:  integer range 79 downto 0 := 0; -- chr col   < 80 (7 bits)
        signal chry:  integer range 11 downto 0 := 0;  -- chr high  < 12 (4 bits)
        signal chry:  integer range 11 downto 0 := 0; -- chr hight < 12 (4 bits)
        signal chrx:  integer range 7  downto 0 := 0;  -- chr width < 08 (3 bits)
        signal chrx:  integer range 7  downto 0 := 0;  -- chr width < 08 (3 bits)
 
 
        signal losr_ce: std_ulogic := '0';
        signal losr_ce: std_ulogic := '0';
        signal losr_ld: std_ulogic := '0';
        signal losr_ld: std_ulogic := '0';
        signal losr_do: std_ulogic := '0';
        signal losr_do: std_ulogic := '0';
        signal y:       std_ulogic := '0';  -- character luminance pixel value (0 or 1)
        signal y:       std_ulogic := '0';  -- character luminance pixel value (0 or 1)
 
 
        -- control io register
        -- control io register
        signal ctl:       std_ulogic_vector(7 downto 0):= (others =>'0');
        signal bell:      std_ulogic := '0';
        signal vga_en:    std_ulogic := '0';
        signal vga_en:    std_ulogic := '0';
        signal cur_en:    std_ulogic := '0';
        signal cur_en:    std_ulogic := '0';
        signal cur_mode:  std_ulogic := '0';
        signal cur_mode:  std_ulogic := '0';
        signal cur_blink: std_ulogic := '0';
        signal cur_blink: std_ulogic := '0';
 
 
 
        signal background_draw, foreground_draw: std_ulogic := '0';
 
        signal attr:          std_ulogic_vector(7 downto 0) := (others =>'0');
 
        signal attr_we_delay: std_ulogic := '0';
 
        signal slowclk, slowclk_cr: std_ulogic := '0';
 
 
 
        signal bell_c, bell_n: std_ulogic := '0';
 
        signal bell_on_c, bell_on_n: std_ulogic := '0';
 
begin
 
        -- Control register. Individual control signal
 
        bell_n    <= octl(4);
 
        bell      <= bell_c xor bell_n;
 
        vga_en    <= octl(3);
 
        cur_en    <= octl(2);
 
        cur_blink <= octl(1);
 
        cur_mode  <= octl(0);
 
 
 
        -- bell register
 
        process (rst, clk25MHz)
 
        begin
 
                if rst = '1' and g.asynchronous_reset then
 
                        bell_c    <= '0';
 
                        bell_on_c <= '0';
 
                elsif rising_edge(clk25MHz) then
 
                        if rst = '1' and not g.asynchronous_reset then
 
                                bell_c    <= '0';
 
                                bell_on_c <= '0';
 
                        else
 
                                bell_c    <= bell_n;
 
                                bell_on_c <= bell_on_n;
 
                        end if;
 
                end if;
 
        end process;
 
 
 
        process (bell_on_c, slowclk, bell)
begin
begin
 
                bell_on_n <= bell_on_c;
 
                slowclk_cr <= '0';
 
                if bell = '1' then
 
                        bell_on_n  <= '1';
 
                        slowclk_cr <= '1';
 
                elsif slowclk = '1' then
 
                        bell_on_n <= '0';
 
                end if;
 
        end process;
 
 
        -- hsync generator, initialized with '1'
        -- hsync generator, initialized with '1'
        process (rst, clk25MHz)
        process (rst, clk25MHz)
        begin
        begin
                if rst = '1' then
                if rst = '1' and g.asynchronous_reset then
                        hsync_int <= '1';
                        hsync_int <= '1';
                elsif rising_edge(clk25MHz) then
                elsif rising_edge(clk25MHz) then
 
                        if rst = '1' and not g.asynchronous_reset then
 
                                hsync_int <= '1';
 
                        else
                        if (hctr > 663) and (hctr < 757) then
                        if (hctr > 663) and (hctr < 757) then
                                hsync_int <= '0';
                                hsync_int <= '0';
                        else
                        else
                                hsync_int <= '1';
                                hsync_int <= '1';
                        end if;
                        end if;
                end if;
                end if;
 
                end if;
        end process;
        end process;
 
 
        -- vsync generator, initialized with '1'
        -- vsync generator, initialized with '1'
        process (rst, clk25MHz)
        process (rst, clk25MHz)
        begin
        begin
                if rst = '1' then
                if rst = '1' and g.asynchronous_reset then
                        vsync_int <= '1';
                        vsync_int <= '1';
                elsif rising_edge(clk25MHz) then
                elsif rising_edge(clk25MHz) then
 
                        if rst = '1' and not g.asynchronous_reset then
 
                                vsync_int <= '1';
 
                        else
                        if (vctr > 499) and (vctr < 502) then
                        if (vctr > 499) and (vctr < 502) then
                                vsync_int <= '0';
                                vsync_int <= '0';
                        else
                        else
                                vsync_int <= '1';
                                vsync_int <= '1';
                        end if;
                        end if;
                end if;
                end if;
 
                end if;
        end process;
        end process;
 
 
        -- Blank signal, 0 = no draw, 1 = visible/draw zone
        -- Blank signal, 0 = no draw, 1 = visible/draw zone
 
 
        -- Proboscide99 31/08/08
        -- Proboscide99 31/08/08
        blank <= '0' when (hctr < 8) or (hctr > 647) or (vctr > 479) else '1';
        blank <= '0' when (hctr < 8) or (hctr > 647) or (vctr > 479) else '1';
 
 
        -- flip-flips for sync of R, G y B signal, initialized with '0'
        -- flip-flops for sync of R, G y B signal, initialized with '0'
        process (rst, clk25MHz)
        process (rst, clk25MHz)
        begin
        begin
                if rst = '1' then
                if rst = '1' and g.asynchronous_reset then
                        foreground_draw <= '0';
                        foreground_draw <= '0';
                elsif rising_edge(clk25MHz) then
                elsif rising_edge(clk25MHz) then
 
                        if rst = '1' and not g.asynchronous_reset then
 
                                foreground_draw <= '0';
 
                        else
                        foreground_draw <= foreground_draw_int;
                        foreground_draw <= foreground_draw_int;
                        background_draw <= background_draw_int;
                        background_draw <= background_draw_int;
                end if;
                end if;
 
                end if;
        end process;
        end process;
 
 
        -- Control register. Individual control signal
 
 
 
        vga_en    <= octl(3);
 
        cur_en    <= octl(2);
 
        cur_blink <= octl(1);
 
        cur_mode  <= octl(0);
 
 
 
        -- counters, hctr, vctr, srcx, srcy, chrx, chry
        -- counters, hctr, vctr, srcx, srcy, chrx, chry
        counters: block
        counters: block
 
 
                signal hctr_ce: std_ulogic := '0';
                signal hctr_ce: std_ulogic := '0';
                signal hctr_rs: std_ulogic := '0';
                signal hctr_rs: std_ulogic := '0';
                signal vctr_ce: std_ulogic := '0';
                signal vctr_ce: std_ulogic := '0';
                signal vctr_rs: std_ulogic := '0';
                signal vctr_rs: std_ulogic := '0';
 
 
Line 1095... Line 1234...
                -- RAM read, ROM read
                -- RAM read, ROM read
                signal ram_tmp: unsigned(11 downto 0) := (others => '0'); -- range 3199 downto 0
                signal ram_tmp: unsigned(11 downto 0) := (others => '0'); -- range 3199 downto 0
                signal mul:     unsigned(15 downto 0) := (others => '0');
                signal mul:     unsigned(15 downto 0) := (others => '0');
                signal rom_tmp: unsigned(11 downto 0) := (others => '0'); -- range 3071 downto 0;
                signal rom_tmp: unsigned(11 downto 0) := (others => '0'); -- range 3071 downto 0;
 
 
                -- @todo Rename these signals to something more sensible
                signal text_d_tmp: std_ulogic_vector(7 downto 0) := (others => '0');
        begin
        begin
                u_hctr: work.vga_pkg.ctrm generic map (M => 794) port map (rst, clk25MHz, hctr_ce, hctr_rs, hctr);
                u_hctr: work.vga_pkg.ctrm generic map (g => g, M => 794)
                u_vctr: work.vga_pkg.ctrm generic map (M => 525) port map (rst, clk25MHz, vctr_ce, vctr_rs, vctr);
                                        port map (rst, clk25MHz, hctr_ce, hctr_rs, hctr);
 
                u_vctr: work.vga_pkg.ctrm generic map (g => g, M => 525)
 
                                        port map (rst, clk25MHz, vctr_ce, vctr_rs, vctr);
 
 
                hctr_ce <= '1';
                hctr_ce <= '1';
                hctr_rs <= '1' when hctr = 793 else '0';
                hctr_rs <= '1' when hctr = 793 else '0';
                vctr_ce <= '1' when hctr = 663 else '0';
                vctr_ce <= '1' when hctr = 663 else '0';
                vctr_rs <= '1' when vctr = 524 else '0';
                vctr_rs <= '1' when vctr = 524 else '0';
 
 
                u_chrx: work.vga_pkg.ctrm generic map (M => 8)  port map (rst, clk25MHz, chrx_ce, chrx_rs, chrx);
                u_chrx: work.vga_pkg.ctrm generic map (g => g, M => 8)
                u_chry: work.vga_pkg.ctrm generic map (M => 12) port map (rst, clk25MHz, chry_ce, chry_rs, chry);
                                        port map (rst, clk25MHz, chrx_ce, chrx_rs, chrx);
                u_scrx: work.vga_pkg.ctrm generic map (M => 80) port map (rst, clk25MHz, scrx_ce, scrx_rs, scrx);
                u_chry: work.vga_pkg.ctrm generic map (g => g, M => 12)
                u_scry: work.vga_pkg.ctrm generic map (M => 40) port map (rst, clk25MHz, scry_ce, scry_rs, scry);
                                        port map (rst, clk25MHz, chry_ce, chry_rs, chry);
 
                u_scrx: work.vga_pkg.ctrm generic map (g => g, M => 80)
 
                                        port map (rst, clk25MHz, scrx_ce, scrx_rs, scrx_text);
 
                u_scry: work.vga_pkg.ctrm generic map (g => g, M => 40)
 
                                        port map (rst, clk25MHz, scry_ce, scry_rs, scry_text);
 
 
                hctr_639 <= '1' when hctr = 639 else '0';
                hctr_639 <= '1' when hctr = 639 else '0';
                vctr_479 <= '1' when vctr = 479 else '0';
                vctr_479 <= '1' when vctr = 479 else '0';
                chrx_007 <= '1' when chrx = 7 else '0';
                chrx_007 <= '1' when chrx = 7 else '0';
                chry_011 <= '1' when chry = 11 else '0';
                chry_011 <= '1' when chry = 11 else '0';
Line 1125... Line 1270...
                chrx_ce <= '1' and blank;
                chrx_ce <= '1' and blank;
                scrx_ce <= chrx_007;
                scrx_ce <= chrx_007;
                chry_ce <= hctr_639 and blank;
                chry_ce <= hctr_639 and blank;
                scry_ce <= chry_011 and hctr_639;
                scry_ce <= chry_011 and hctr_639;
 
 
                ram_tmp <=  (to_unsigned(scry,ram_tmp'length) sll 4) +
                ram_tmp <=  (to_unsigned(scry_text, ram_tmp'length) sll 4) +
                                (to_unsigned(scry,ram_tmp'length) sll 6) +
                                (to_unsigned(scry_text, ram_tmp'length) sll 6) +
                                to_unsigned(scrx,ram_tmp'length);
                                to_unsigned(scrx_text, ram_tmp'length);
 
 
 
                text_d_tmp <= text_d(7 downto 0);
                text_a  <= std_ulogic_vector(ram_tmp);
                text_a  <= std_ulogic_vector(ram_tmp);
                mul     <= unsigned(text_d) * 12;
                mul     <= unsigned(text_d_tmp) * 12;
                rom_tmp <= mul(rom_tmp'range) + chry;
                rom_tmp <= mul(rom_tmp'range) + chry;
                font_a  <= std_ulogic_vector(rom_tmp);
                font_a  <= font_sel & std_ulogic_vector(rom_tmp);
 
        end block;
 
 
 
        color_block: block
 
                signal red_on:   std_ulogic := '0';
 
                signal green_on: std_ulogic := '0';
 
                signal blue_on:  std_ulogic := '0';
 
                signal bold:     std_ulogic := '0';
 
                signal reverse:  std_ulogic := '0';
 
                signal final:    std_ulogic_vector(2 downto 0) := "111";
 
        begin
 
                reverse     <= bell_on_c when attr(7) = '0' else slowclk;
 
                bold        <= attr(6);
 
                final       <= "100" when bold = '0' else "111";
 
 
 
                red_on      <= (reverse   xor attr(3)) when foreground_draw = '1' else
 
                               (bell_on_c xor attr(0)) when background_draw = '1' else '0';
 
                green_on    <= (reverse   xor attr(4)) when foreground_draw = '1' else
 
                               (bell_on_c xor attr(1)) when background_draw = '1' else '0';
 
                blue_on     <= (reverse   xor attr(5)) when foreground_draw = '1' else
 
                               (bell_on_c xor attr(2)) when background_draw = '1' else '0';
 
 
 
                o_vga.red   <= final             when red_on    = '1' else "000";
 
                o_vga.green <= final             when green_on  = '1' else "000";
 
                o_vga.blue  <= final(2 downto 1) when blue_on   = '1' else "00";
        end block;
        end block;
 
 
        u_losr: work.vga_pkg.losr generic map (N => 8)
        u_reg_delay: work.util.reg generic map (g => g, N => 1)
        port map (rst, clk25MHz, losr_ld, losr_ce, losr_do, FONT_D);
        port map(clk => clk25MHz, rst => rst, we => '1', di(0) => losr_ld, do(0) => attr_we_delay);
 
 
 
        u_reg_attr: work.util.reg generic map (g => g, N => 8)
 
        port map(clk => clk25MHz, rst => rst, we => attr_we_delay, di => text_d(15 downto 8), do => attr);
 
 
 
        u_losr: work.vga_pkg.losr generic map (g => g, N => font_d'length)
 
        port map (rst => rst, clk => clk25MHz, load => losr_ld, ce => losr_ce, do => losr_do, di => font_d);
 
 
        losr_ce <= blank;
        losr_ce <= blank;
        losr_ld <= '1' when (chrx = 7) else '0';
        losr_ld <= '1' when (chrx = 7) else '0';
 
 
        -- video out, vga_en control signal enable/disable vga signal
        -- video out, vga_en control signal enable/disable vga signal
        foreground_draw_int <=      y  and blank;
        foreground_draw_int <=      y  and blank;
        background_draw_int <= (not y) and blank;
        background_draw_int <= (not y) and blank;
 
 
        hsync <= hsync_int and vga_en;
        o_vga.hsync <= hsync_int and vga_en;
        vsync <= vsync_int and vga_en;
        o_vga.vsync <= vsync_int and vga_en;
 
 
        -- Hardware Cursor
        -- Hardware Cursor
        hw_cursor: block
        hw_cursor: block
                signal small:   std_ulogic := '0';
                signal small:   std_ulogic := '0';
                signal curen2:  std_ulogic := '0';
                signal curen2:  std_ulogic := '0';
                signal slowclk: std_ulogic := '0';
 
                signal curpos:  std_ulogic := '0';
                signal curpos:  std_ulogic := '0';
                signal yint:    std_ulogic := '0';
                signal yint:    std_ulogic := '0';
                -- signal crx:     integer range 79 downto 0;
 
                -- signal cry:     integer range 39 downto 0;
 
                signal crx:     integer range 127 downto 0;
                signal crx:     integer range 127 downto 0;
                signal cry:     integer range 64 downto 0;
                signal cry:     integer range 64 downto 0;
                signal counter: unsigned(22 downto 0) := (others => '0');
                signal counter: unsigned(24 downto 0) := (others => '0');
 
                signal cursorclk: std_ulogic := '0';
 
        begin
 
                process (counter, slowclk_cr, clk25MHz)
        begin
        begin
 
                        counter <= counter;
 
                        if rising_edge(clk25MHz) then
 
                                if slowclk_cr = '1' then
 
                                        counter <= (others => '0');
 
                                else
 
                                        counter <= counter + 1;
 
                                end if;
 
                        end if;
 
                end process;
 
 
                -- slowclk for blink hardware cursor
                cursorclk <= counter(22); -- 2.98Hz
                counter <= counter + 1 when rising_edge(clk25MHz) else counter;
                slowclk   <= counter(24); -- 0.745Hz
                slowclk <= counter(22); --2.98Hz
 
 
 
                crx <= to_integer(unsigned(ocrx(6 downto 0)));
                crx <= to_integer(unsigned(ocrx(6 downto 0)));
                cry <= to_integer(unsigned(ocry(5 downto 0)));
                cry <= to_integer(unsigned(ocry(5 downto 0)));
 
 
                --
                --
                curpos <= '1' when scry = cry and scrx = crx else '0';
                curpos <= '1' when scry_text = cry and scrx_text = crx else '0';
                small  <= '1' when (chry > 8)                else '0';
                small  <= '1' when (chry > 8)                else '0';
                curen2 <= (slowclk or (not cur_blink)) and cur_en;
                curen2 <= (cursorclk or (not cur_blink)) and cur_en;
                yint   <= '1' when cur_mode = '0'            else small;
                yint   <= '1' when cur_mode = '0'            else small;
                y      <= (yint and curpos and curen2) xor losr_do;
                y      <= (yint and curpos and curen2) xor losr_do;
        end block;
        end block;
end;
end;
----- VGA Core ----------------------------------------------------------------
----- VGA Core ----------------------------------------------------------------
Line 1188... Line 1372...
--| @author         Javier Valcarce García
--| @author         Javier Valcarce García
--| @copyright      Copyright 2007 Javier Valcarce García
--| @copyright      Copyright 2007 Javier Valcarce García
--| @license        LGPL version 3
--| @license        LGPL version 3
--| @email          javier.valcarce@gmail.com
--| @email          javier.valcarce@gmail.com
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
library ieee;
library ieee, work;
use ieee.std_logic_1164.all;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.numeric_std.all;
 
use work.util.common_generics;
 
 
entity ctrm is
entity ctrm is
        generic (M: positive := 8);
        generic (g: common_generics; M: positive := 8);
        port (
        port (
                rst: in  std_ulogic; -- asynchronous rst
                rst: in  std_ulogic; -- asynchronous rst
                clk: in  std_ulogic;
                clk: in  std_ulogic;
                ce:  in  std_ulogic; -- enable counting
                ce:  in  std_ulogic; -- enable counting
                rs:  in  std_ulogic; -- synchronous rst
                rs:  in  std_ulogic; -- synchronous rst
                do:  out integer range (M-1) downto 0 := 0);
                do:  out integer range (M-1) downto 0 := 0);
end ctrm;
end entity;
 
 
architecture rtl of ctrm is
architecture rtl of ctrm is
        signal c: integer range (M-1) downto 0:= 0;
        signal c: integer range (M-1) downto 0:= 0;
begin
begin
        do <= c;
        do <= c;
        process(rst, clk)
        process(rst, clk)
        begin
        begin
                if rst = '1' then
                if rst = '1' and g.asynchronous_reset then
                        c <= 0;
                        c <= 0 after g.delay;
                elsif rising_edge(clk) then
                elsif rising_edge(clk) then
 
                        if rst = '1' and not g.asynchronous_reset then
 
                                c <= 0 after g.delay;
 
                        else
                        if ce = '1' then
                        if ce = '1' then
                                if rs = '1' then
                                if rs = '1' then
                                        c <= 0;
                                                c <= 0 after g.delay;
                                else
                                else
                                        c <= c + 1;
                                        -- elsif c /= (M - 1) then
 
                                                c <= c + 1 after g.delay;
 
                                        end if;
                                end if;
                                end if;
                        end if;
                        end if;
                end if;
                end if;
        end process;
        end process;
end;
end;
Line 1231... Line 1421...
--| @author         Javier Valcarce García
--| @author         Javier Valcarce García
--| @copyright      Copyright 2007 Javier Valcarce García
--| @copyright      Copyright 2007 Javier Valcarce García
--| @license        LGPL version 3
--| @license        LGPL version 3
--| @email          javier.valcarce@gmail.com
--| @email          javier.valcarce@gmail.com
-------------------------------------------------------------------------------
-------------------------------------------------------------------------------
library ieee;
 
 
library ieee, work;
use ieee.std_logic_1164.all;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
use ieee.numeric_std.all;
 
use work.util.common_generics;
 
 
entity losr is
entity losr is
        generic (N: positive := 4);
        generic (g: common_generics; N: positive := 4);
        port
        port
        (
        (
                rst:  in  std_ulogic;
                rst:  in  std_ulogic;
                clk:  in  std_ulogic;
                clk:  in  std_ulogic;
                load: in  std_ulogic;
                load: in  std_ulogic;
                ce:   in  std_ulogic;
                ce:   in  std_ulogic;
                do:   out std_ulogic := '0';
                do:   out std_ulogic := '0';
                di:   in  std_ulogic_vector(N - 1 downto 0));
                di:   in  std_ulogic_vector(N - 1 downto 0));
end losr;
end entity;
 
 
architecture rtl of losr is
architecture rtl of losr is
begin
begin
        process(rst, clk)
        process(rst, clk)
                variable data : std_ulogic_vector(N - 1 downto 0) := (others => '0');
                variable data : std_ulogic_vector(N - 1 downto 0) := (others => '0');
        begin
        begin
                if rst = '1' then
                if rst = '1' and g.asynchronous_reset then
                        data := (others => '0');
                        data := (others => '0');
                elsif rising_edge(clk) then
                elsif rising_edge(clk) then
 
                        if rst = '1' and not g.asynchronous_reset then
 
                                data := (others => '0');
 
                        else
                        if load = '1' then
                        if load = '1' then
                                data := di;
                                data := di;
                        elsif ce = '1' then
                        elsif ce = '1' then
                                data := data(N-2 downto 0) & "0";
                                data := data(N-2 downto 0) & "0";
                        end if;
                        end if;
                end if;
                end if;
                do <= data(N-1);
                end if;
 
                do <= data(N-1) after g.delay;
        end process;
        end process;
end;
end;
 
 
 
 
 No newline at end of file
 No newline at end of file

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.