git-svn-id: http://moon:8086/svn/vhdl/trunk@1418 cc03376c-175c-47c8-b038-4cd826a8556b
395 lines
9.9 KiB
VHDL
395 lines
9.9 KiB
VHDL
--------------------------------------------------------------------------------
|
|
-- Company:
|
|
-- Engineer:
|
|
--
|
|
-- Create Date: 11:25:45 10/15/05
|
|
-- Design Name:
|
|
-- Module Name: vga_ctrl_top - Behavioral
|
|
-- Project Name:
|
|
-- Target Device:
|
|
-- Tool versions:
|
|
-- Description:
|
|
--
|
|
-- Dependencies:
|
|
--
|
|
-- Revision:
|
|
-- Revision 0.01 - File Created
|
|
-- Additional Comments:
|
|
--
|
|
--------------------------------------------------------------------------------
|
|
library IEEE;
|
|
use IEEE.STD_LOGIC_1164.ALL;
|
|
use IEEE.NUMERIC_STD.ALL;
|
|
|
|
use work.vga_types.all;
|
|
use work.cpu_pkg.all;
|
|
|
|
entity vga_ctrl_top is
|
|
Generic
|
|
(
|
|
sys_freq : real := 100.0;
|
|
fifo_depth : integer := 2048;
|
|
tsvga : vga_timespec_t := ts_vga_1280_1024_72
|
|
);
|
|
Port
|
|
(
|
|
sys_rstn_in : in std_logic;
|
|
sys_clk_in : in std_logic;
|
|
sys_vga_red : out unsigned(7 downto 0);
|
|
sys_vga_green : out unsigned(7 downto 0);
|
|
sys_vga_blue : out unsigned(7 downto 0);
|
|
sys_vga_blank_n : out std_logic;
|
|
sys_vga_sync_n : out std_logic;
|
|
sys_vga_hsync : out std_logic;
|
|
sys_vga_vsync : out std_logic;
|
|
sys_vga_clk : out std_logic;
|
|
-- Buttons and LEDs
|
|
sys_btn : in unsigned(4 downto 0);
|
|
sys_dip : in unsigned(7 downto 0);
|
|
sys_led : out unsigned(8 downto 0)
|
|
);
|
|
end vga_ctrl_top;
|
|
|
|
architecture Behavioral of vga_ctrl_top is
|
|
|
|
-- System signal
|
|
signal rst : std_logic;
|
|
signal clk : std_logic;
|
|
signal vga_rst : std_logic;
|
|
signal vga_clk : std_logic;
|
|
signal vga_ready : std_logic;
|
|
|
|
-- Timing
|
|
signal scan_rdy : std_logic;
|
|
signal scan_rdy_h : std_logic;
|
|
signal scan_rdy_v : std_logic;
|
|
signal vga_scan_x : std_logic;
|
|
signal vga_scan_y : std_logic;
|
|
signal hsync : std_logic;
|
|
signal vsync : std_logic;
|
|
|
|
signal src_pos_x : natural range 0 to tsvga.ts_h.ncyc_scan-1;
|
|
signal src_pos_y : natural range 0 to tsvga.ts_v.ncyc_scan-1;
|
|
signal vga_pos_x : natural range 0 to tsvga.ts_h.ncyc_scan-1;
|
|
signal vga_pos_y : natural range 0 to tsvga.ts_v.ncyc_scan-1;
|
|
|
|
-- Line buffers
|
|
signal color_w : color_t;
|
|
signal vga_color : color_t;
|
|
signal color_we : std_logic;
|
|
signal fifo_full : std_logic;
|
|
signal fifo_almost_full : std_logic;
|
|
signal scan_enable : std_logic;
|
|
signal src_enable : std_logic;
|
|
signal src_cnt_en : std_logic;
|
|
signal char_draw_en : std_logic;
|
|
signal cg_en : std_logic;
|
|
signal cpu_color : color_t;
|
|
|
|
-- CPU signals
|
|
signal cpu_rst : std_logic;
|
|
signal cpu_ce : std_logic;
|
|
signal cpu_int_in : std_logic;
|
|
signal cpu_int_ack : std_logic;
|
|
signal cpu_we : std_logic;
|
|
signal cpu_re : std_logic;
|
|
signal cpu_io_sel : std_logic;
|
|
signal cpu_din : dmem_data_t;
|
|
signal cpu_dout : dmem_data_t;
|
|
signal cpu_addr : dmem_addr_t;
|
|
signal cpu_xrom_data : dmem_data_t;
|
|
|
|
signal cg_ready : std_logic;
|
|
signal cg_clr_screen : std_logic;
|
|
signal cg_clr_line : std_logic;
|
|
signal cg_ascii_data : dmem_data_t;
|
|
signal cg_ascii_data_we : std_logic;
|
|
signal cg_ascii_posy_we : std_logic;
|
|
signal cg_ascii_posx_we : std_logic;
|
|
|
|
signal cpu_led : dmem_data_t;
|
|
signal cpu_red : dmem_data_t;
|
|
signal cpu_green : dmem_data_t;
|
|
signal cpu_blue : dmem_data_t;
|
|
|
|
begin
|
|
|
|
inst_vga_backend: entity work.vga_backend
|
|
GENERIC MAP
|
|
(
|
|
sys_freq => sys_freq,
|
|
fifo_depth => fifo_depth,
|
|
tsvga => tsvga
|
|
)
|
|
PORT MAP
|
|
(
|
|
sys_rst => vga_rst,
|
|
sys_clk => clk,
|
|
vga_ready => vga_ready,
|
|
color_in => color_w,
|
|
color_fifo_we => color_we,
|
|
color_fifo_full => fifo_full,
|
|
color_fifo_afull => fifo_almost_full,
|
|
direct_color_in => cpu_color,
|
|
direct_draw_en => char_draw_en,
|
|
stat_hsync => hsync,
|
|
stat_vsync => vsync,
|
|
stat_hready => scan_rdy_h,
|
|
stat_vready => scan_rdy_v,
|
|
stat_hscan => vga_scan_x,
|
|
stat_vscan => vga_scan_y,
|
|
stat_hpos => vga_pos_x,
|
|
stat_vpos => vga_pos_y,
|
|
vga_clk_out => vga_clk,
|
|
vga_color_out => vga_color,
|
|
vga_blank_n => sys_vga_blank_n,
|
|
vga_sync_n => sys_vga_sync_n,
|
|
vga_hsync => sys_vga_hsync,
|
|
vga_vsync => sys_vga_vsync
|
|
|
|
);
|
|
|
|
inst_char_gen : entity work.char_gen
|
|
GENERIC MAP
|
|
(
|
|
tsvga => tsvga,
|
|
CHARACTER_SCALE => 1,
|
|
CHAR_ROM_SIZE_X => 8, -- Pixels
|
|
CHAR_ROM_SIZE_Y => 16, -- Pixels
|
|
CHAR_ROM_DEPTH => 256, -- Chars
|
|
MAX_CHAR_PER_LINE => 80, -- Chars
|
|
MAX_LINE_PER_FRAME => 32, -- Chars
|
|
CHAR_SPACING_X => 0, -- Pixels
|
|
CHAR_SPACING_Y => 0, -- Pixels
|
|
SCREEN_OFFSET_X => 16, -- Pixels
|
|
SCREEN_OFFSET_Y => 16 -- Pixels
|
|
)
|
|
PORT MAP
|
|
(
|
|
rst => rst,
|
|
sys_clk => clk,
|
|
vga_clk => vga_clk,
|
|
ce => cg_en,
|
|
frame_pulse => scan_rdy,
|
|
clr_screen => cg_clr_screen,
|
|
clr_line => cg_clr_line,
|
|
ascii_data => cg_ascii_data,
|
|
ascii_data_we => cg_ascii_data_we,
|
|
ascii_posy_we => cg_ascii_posy_we,
|
|
ascii_posx_we => cg_ascii_posx_we,
|
|
ready => cg_ready,
|
|
pos_x => vga_pos_x,
|
|
pos_y => vga_pos_y,
|
|
char_draw_en => char_draw_en
|
|
);
|
|
|
|
inst_cpu_embedded: entity work.cpu_embedded
|
|
PORT MAP(
|
|
rst => cpu_rst,
|
|
clk => clk,
|
|
ce => cpu_ce,
|
|
int_in => cpu_int_in,
|
|
int_ack => cpu_int_ack,
|
|
xmem_we => cpu_we,
|
|
xmem_re => cpu_re,
|
|
xmem_din => cpu_din,
|
|
xmem_dout => cpu_dout,
|
|
xmem_addr => cpu_addr,
|
|
io_sel => cpu_io_sel
|
|
);
|
|
|
|
inst_xrom: entity work.xrom
|
|
PORT MAP(
|
|
clk => clk,
|
|
ce => cpu_ce,
|
|
addr => cpu_addr,
|
|
dout => cpu_xrom_data
|
|
);
|
|
|
|
---------------------------------------------------------------------------------------------
|
|
rst <= not vga_ready;
|
|
vga_rst <= not sys_rstn_in;
|
|
|
|
-- clk <= vga_clk;
|
|
clk <= sys_clk_in;
|
|
|
|
scan_rdy <= scan_rdy_h and scan_rdy_v;
|
|
|
|
sys_vga_clk <= vga_clk;
|
|
sys_vga_red <= vga_color(r);
|
|
sys_vga_green <= vga_color(g);
|
|
sys_vga_blue <= vga_color(b);
|
|
|
|
cg_en <= vga_scan_x and vga_scan_y;
|
|
cpu_ce <= '1';
|
|
|
|
---------------------------------------------------------------------------------------------
|
|
led_out: process (clk)
|
|
begin
|
|
if rising_edge(clk) then
|
|
sys_led <= '0' & cpu_led;
|
|
end if;
|
|
end process;
|
|
|
|
---------------------------------------------------------------------------------------------
|
|
cpu_reg_read:
|
|
process(clk, cpu_io_sel, cpu_xrom_data)
|
|
variable reg : dmem_data_t;
|
|
begin
|
|
|
|
if rising_edge(clk) then
|
|
case cpu_addr is
|
|
when X"00" => -- 00
|
|
reg := "000" & unsigned(sys_btn(4 downto 0));
|
|
when X"01" => -- 01
|
|
reg := cpu_led;
|
|
when X"05" => -- 05
|
|
reg := unsigned(sys_dip);
|
|
when X"0B" =>
|
|
reg := "000000" & cg_ready & vga_ready;
|
|
when others => null;
|
|
end case;
|
|
end if;
|
|
|
|
cpu_din <= cpu_xrom_data;
|
|
if cpu_io_sel = '1' then
|
|
cpu_din <= reg;
|
|
end if;
|
|
|
|
end process;
|
|
|
|
------------------------------------------------------------------
|
|
cpu_reg_write:
|
|
process(rst, clk)
|
|
variable addr : unsigned(dmem_addr_t'length-1 downto 0);
|
|
begin
|
|
if (rst = '1') then
|
|
cpu_led <= (others => '0');
|
|
cg_ascii_data <= (others => '0');
|
|
cg_ascii_posy_we <= '0';
|
|
cg_ascii_posx_we <= '0';
|
|
cg_ascii_data_we <= '0';
|
|
cg_clr_line <= '0';
|
|
cg_clr_screen <= '0';
|
|
cpu_red <= X"80";
|
|
cpu_green <= X"80";
|
|
cpu_blue <= X"80";
|
|
|
|
elsif rising_edge(clk) then
|
|
cg_ascii_posy_we <= '0';
|
|
cg_ascii_posx_we <= '0';
|
|
cg_ascii_data_we <= '0';
|
|
cg_clr_line <= '0';
|
|
cg_clr_screen <= '0';
|
|
addr := cpu_addr;
|
|
if cpu_we = '1' then
|
|
if cpu_io_sel = '1' then
|
|
case addr is
|
|
when X"01" => -- 01
|
|
cpu_led <= cpu_dout;
|
|
when X"02" => -- 04
|
|
cpu_red <= cpu_dout;
|
|
when X"03" => -- 04
|
|
cpu_green <= cpu_dout;
|
|
when X"04" => -- 04
|
|
cpu_blue <= cpu_dout;
|
|
when X"08" => -- 08
|
|
cg_ascii_data <= cpu_dout;
|
|
cg_ascii_posx_we <= '1';
|
|
when X"09" => -- 09
|
|
cg_ascii_data <= cpu_dout;
|
|
cg_ascii_posy_we <= '1';
|
|
when X"0A" => -- 0A
|
|
cg_ascii_data <= cpu_dout;
|
|
cg_ascii_data_we <= '1';
|
|
when X"0B" => -- 0B
|
|
cg_clr_screen <= cpu_dout(0);
|
|
cg_clr_line <= cpu_dout(1);
|
|
when others => null;
|
|
end case;
|
|
end if;
|
|
end if;
|
|
end if;
|
|
end process;
|
|
|
|
---------------------------------------------------------------------------------------------
|
|
--- Test
|
|
---------------------------------------------------------------------------------------------
|
|
cpu_start: process (rst, vga_clk)
|
|
begin
|
|
if (rst = '1') then
|
|
cpu_rst <= '1';
|
|
elsif rising_edge(vga_clk) and scan_rdy = '1' then
|
|
cpu_rst <= '0';
|
|
end if;
|
|
end process;
|
|
|
|
scan_start: process (rst, clk)
|
|
begin
|
|
if (rst = '1') then
|
|
scan_enable <= '0';
|
|
elsif rising_edge(clk) then
|
|
scan_enable <= '1';
|
|
end if;
|
|
end process;
|
|
|
|
color_sel: process (vga_clk)
|
|
begin
|
|
if rising_edge(vga_clk) and scan_rdy = '1' then
|
|
cpu_color <= (cpu_red, cpu_green, cpu_blue);
|
|
end if;
|
|
end process;
|
|
|
|
color_we <= scan_enable and src_enable and not fifo_full;
|
|
|
|
src_inc_reg: process (rst, clk)
|
|
begin
|
|
if (rst = '1') then
|
|
src_enable <= '0';
|
|
elsif rising_edge(clk) then
|
|
if fifo_full = '1' then
|
|
src_enable <= '0';
|
|
elsif fifo_almost_full = '0' then
|
|
src_enable <= '1';
|
|
end if;
|
|
end if;
|
|
end process;
|
|
|
|
color_ctrl: process (rst, clk)
|
|
variable enable : std_logic;
|
|
begin
|
|
if (rst = '1') then
|
|
src_pos_x <= 0;
|
|
src_pos_y <= 0;
|
|
elsif rising_edge(clk) then
|
|
if color_we = '1' then
|
|
if src_pos_x < tsvga.ts_h.ncyc_scan-1 then
|
|
src_pos_x <= src_pos_x + 1;
|
|
else
|
|
src_pos_x <= 0;
|
|
if src_pos_y < tsvga.ts_v.ncyc_scan-1 then
|
|
src_pos_y <= src_pos_y + 1;
|
|
else
|
|
src_pos_y <= 0;
|
|
end if;
|
|
end if;
|
|
end if;
|
|
end if;
|
|
end process;
|
|
|
|
color_gen: process (src_pos_x, src_pos_y)
|
|
begin
|
|
color_w <= (X"00", X"00", X"00");
|
|
if src_pos_y = 0 then
|
|
color_w <= (X"00", X"FF", X"00");
|
|
elsif src_pos_y = (tsvga.ts_v.ncyc_scan-1) then
|
|
color_w <= (X"00", X"FF", X"00");
|
|
elsif src_pos_x = 0 then
|
|
color_w <= (X"FF", X"00", X"00");
|
|
elsif src_pos_x = (tsvga.ts_h.ncyc_scan-1) then
|
|
color_w <= (X"00", X"00", X"FF");
|
|
end if;
|
|
end process;
|
|
|
|
end Behavioral;
|