⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 vga_ctrl.vhd

📁 VGA模块的VHDL代码和软件驱动
💻 VHD
字号:
library IEEE;
use IEEE.std_logic_1164.all;

entity vga_ctrl is
	port
	(
		clk:			in std_logic;	-- from bus
		reset:			in std_logic;	-- from bus
		chipselect:		in std_logic;	-- from bus	
		address:		in std_logic_vector( 17 downto 0 ); -- from bus
		read_n:			in std_logic;	-- from bus
		write_n:		in std_logic;	-- from bus
		writedata:		in std_logic_vector( 15 downto 0 ); -- from bus
		byteenable_n:	in std_logic_vector( 1 downto 0 ); -- from bus
		vd_inuse:		in std_logic;	-- from vga_display (async)
		vd_scan:		in std_logic;	-- from vga_ctrl (async)
		vd_addr:		in std_logic_vector( 16 downto 0 ); -- from vga_display
		vd_read_n:		in std_logic;	-- from vga_display
		vd_be_n:		in std_logic_vector( 1 downto 0 ); -- from vga_display
		sram_dq:		inout std_logic_vector( 15 downto 0 );
		sram_addr:		out std_logic_vector( 17 downto 0 ); -- export to sram
		sram_we_n:		out std_logic;	-- export to sram
		sram_oe_n:		out std_logic;	-- export to sram
		sram_ub_n:		out std_logic;	-- export to sram
		sram_lb_n:		out std_logic;	-- export to sram
		sram_ce_n:		out std_logic;	-- export to sram
		vd_ena:			out std_logic;	-- to vga_display
		vd_data:		out std_logic_vector( 15 downto 0 ); -- to vga_display
		waitrequest:	out std_logic;	-- to bus
		readdata:		out std_logic_vector( 15 downto 0 )	-- to bus
	);
end vga_ctrl;

architecture RTL of vga_ctrl is
	
	type VC_STAT is ( VC_INIT, VC_IDLE, VC_WR_STATE, VC_RD_STATE, VC_WAIT_RW, VC_RW_DATA );
	
	constant WRITABLE_BIT:	integer := 0;	-- I
	constant DISP_EN_BIT:	integer := 1;	-- I/O
	constant SWITCH_BIT:	integer := 2;	-- O
	
	signal stat:		VC_STAT;
	signal stat_next:	VC_STAT;
	
	signal switch:		std_logic;	-- latch
	signal switch_next:	std_logic;	-- latch
	signal displsel:	std_logic;
	signal rwsel:		std_logic;
	signal disp_en:		std_logic;	-- latch
	signal vd_inuse_r:	std_logic;
	signal vd_scan_r:	std_logic;
	signal unready:		std_logic;
	signal unready_dl:	std_logic;
	signal unready_dl2:	std_logic;
	
begin
	
	Reg_async: process( clk, vd_inuse, vd_scan )
	begin
		if( rising_edge( clk ) ) then
			vd_inuse_r <= vd_inuse;
			vd_scan_r <= vd_scan;
		end if;
	end process Reg_async;
	
	sram_ce_n <= '0';
	displsel <= switch;
	rwsel <= not switch;
	
	Stat_P: process( clk, reset, stat_next )
	begin
		if( rising_edge( clk ) ) then
			if( reset = '1' ) then
				stat <= VC_INIT;
			else
				stat <= stat_next;
			end if;
		end if;
	end process Stat_P;
	
	Stat_next_P: process( stat, chipselect, address, write_n, read_n, switch, switch_next )
	begin
		case stat is
			
			when VC_INIT =>
				stat_next <= VC_IDLE;
			
			when VC_IDLE =>
				stat_next <= VC_IDLE;
				if( chipselect = '1' ) then
					if( address(17) = '1' ) then
						if( write_n = '0' ) then
							stat_next <= VC_WR_STATE;
						end if;
						if( read_n = '0' ) then
							stat_next <= VC_RD_STATE;
						end if;
					else
						if( switch = switch_next ) then
							stat_next <= VC_RW_DATA;
						else
							stat_next <= VC_WAIT_RW;
						end if;
					end if;
				end if;
			
			when VC_WR_STATE =>
				if( chipselect = '0' ) then
					stat_next <= VC_IDLE;
				else
					stat_next <= VC_WR_STATE;
				end if;
			
			when VC_RD_STATE =>
				if( chipselect = '0' ) then
					stat_next <= VC_IDLE;
				else
					stat_next <= VC_RD_STATE;
				end if;
			
			when VC_WAIT_RW =>
				if( switch = switch_next ) then
					stat_next <= VC_RW_DATA;
				else
					stat_next <= VC_WAIT_RW;
				end if;
			
			when VC_RW_DATA =>
				if( chipselect = '0' ) then
					stat_next <= VC_IDLE;
				else
					stat_next <= VC_RW_DATA;
				end if;
			
			when others =>
				stat_next <= VC_INIT;
			
		end case;
	end process Stat_next_P;
	
	Unready_P: process( stat, vd_inuse_r )
	begin
		case stat is
			
			when VC_RW_DATA =>					
				unready <= vd_inuse_r;
			
			when others =>
				unready <= '1';
			
		end case;
	end process Unready_P;
	
	Unready_delay: process( clk, unready, unready_dl )
	begin
		if( rising_edge( clk ) ) then
			unready_dl2 <= unready_dl;
			unready_dl <= unready;
		end if;
	end process Unready_delay;
	
	Mux: process( clk, vd_scan_r, stat, unready, unready_dl, displsel, disp_en, vd_addr, vd_read_n, vd_be_n, sram_dq, chipselect, address, write_n, writedata, byteenable_n )
	begin
		if( rising_edge( clk ) ) then
			
			if( vd_scan_r = '0' ) then
				switch <= switch_next;
			else
				switch <= switch;
			end if;
			
			switch_next <= switch_next;
			disp_en <= disp_en;
			
			vd_ena <= disp_en;
			
			vd_data <= sram_dq;
			sram_dq <= ( others => 'Z' );
			sram_addr <= displsel & vd_addr;
			sram_we_n <= '1';
			sram_oe_n <= vd_read_n;
			sram_ub_n <= vd_be_n(1);
			sram_lb_n <= vd_be_n(0);
			
			waitrequest <= '1';
			readdata <= ( others => '0' );
			
			case stat is
				
				when VC_INIT =>
					switch <= '0';
					switch_next <= '0';
					disp_en <= '0';
				
				when VC_IDLE =>
				
				when VC_WR_STATE =>
					waitrequest <= '0';
					if( write_n = '0' ) then
						disp_en <= writedata( DISP_EN_BIT );
						if( writedata(SWITCH_BIT) = '1' ) then
							switch <= switch;
							switch_next <= not switch;
						end if;
					end if;
				
				when VC_RD_STATE =>
					waitrequest <= '0';
--					if( (vd_scan_r = '0') and (switch = switch_next) ) then
--						readdata( WRITABLE_BIT ) <= '1';
--					else
--						readdata( WRITABLE_BIT ) <= '0';
--					end if;
					readdata( WRITABLE_BIT ) <= (not vd_scan_r) and (not (switch xor switch_next));
					readdata( DISP_EN_BIT ) <= disp_en;
					
				when VC_WAIT_RW =>
					waitrequest <= '1';
					switch <= switch_next;
				
				when VC_RW_DATA =>
					if( unready = '0' or unready_dl2 = '0' ) then
						
						waitrequest <= unready or unready_dl2;
						
						vd_data <= ( others => '0' );
						
						sram_addr <= rwsel & address( 16 downto 0 );
						if( write_n = '0' ) then
							sram_dq <= writedata;
						else
							sram_dq <= ( others => 'Z' );
						end if;
						sram_we_n <= write_n;
						sram_oe_n <= read_n;
						sram_ub_n <= byteenable_n(1);
						sram_lb_n <= byteenable_n(0);
						
						readdata <= sram_dq;
						
					end if;
				
				when others =>
				
			end case;
			
		end if;
	end process Mux;
	
end RTL;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -