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

📄 chipio.vhd

📁 VHDL-vga_core(vhdl).rar FPGA上实现 VGA的IP(VHDL)
💻 VHD
字号:
library IEEE;
use IEEE.std_logic_1164.all;
use IEEE.numeric_std.all;

--
-- xsocVGABitmap Example Project
-- Doug Hodson, Jun 2003
-- www.RetroMicro.com
--
-- Run design at 25 MHz
--
entity chipIO is
	
	port(
		pin_clkin   : in std_logic;       -- main clock input from external clock source
		pin_ce_n    : out std_logic;      -- Flash RAM chip-enable
		pin_pushbtn : in std_logic;
		
		-- vga port connections
		pin_red     : out std_logic_vector(1 downto 0);
		pin_green   : out std_logic_vector(1 downto 0);
		pin_blue    : out std_logic_vector(1 downto 0);
		pin_hsync_n : out std_logic;
		pin_vsync_n : out std_logic;

		-- SDRAM pin connections
		pin_sclkfb : in std_logic;                   -- feedback SDRAM clock with PCB delays
		pin_sclk   : out std_logic;                  -- clock to SDRAM
		pin_cke    : out std_logic;                  -- SDRAM clock-enable
		pin_cs_n   : out std_logic;                  -- SDRAM chip-select
		pin_ras_n  : out std_logic;                  -- SDRAM RAS
		pin_cas_n  : out std_logic;                  -- SDRAM CAS
		pin_we_n   : out std_logic;                  -- SDRAM write-enable
		pin_ba     : out unsigned( 1 downto 0);      -- SDRAM bank-address
		pin_sAddr  : out unsigned(11 downto 0);      -- SDRAM address bus
		pin_sData  : inout unsigned(16-1 downto 0);  -- data bus to SDRAM
		pin_dqmh   : out std_logic;                  -- SDRAM DQMH
		pin_dqml   : out std_logic                   -- SDRAM DQML			
	);
	
end chipIO;

architecture arch of chipIO is

	constant YES:	std_logic := '1';
	constant NO:	std_logic := '0';
	constant HI:	std_logic := '1';
	constant LO:	std_logic := '0';

	constant DATA_WIDTH: natural := 16;
	constant ADDR_WIDTH: natural := 23;

   signal sysClk   : std_logic;  -- system clock
   signal sysReset : std_logic;  -- system reset

	-- vga component
	component vga
		port(
		clk: in std_logic;       -- global clock
		rst: in std_logic;       -- global async reset
		vack: in std_logic;      -- video data DMA acknowledge
		pixels_in: in std_logic_vector(15 downto 0); -- video data in
		vreq: out std_logic;     -- video data DMA request
		vreset: out std_logic;   -- video data reset DMA counter request
		hsync_n: out std_logic;  -- active low horz sync
		vsync_n: out std_logic;  -- active low vert sync
		r: out std_logic_vector(1 downto 0);  -- red
		g: out std_logic_vector(1 downto 0);  -- green
		b: out std_logic_vector(1 downto 0)   -- blue		
		);
	end component;

	-- vga signals
	signal vga_clk       : std_logic;       -- global clock
	signal vga_vack      : std_logic;       -- video data DMA acknowledge
	signal vga_pixels_in : std_logic_vector(15 downto 0); -- video data in
	signal vga_vreq      : std_logic;       -- video data DMA request
	signal vga_vreset    : std_logic;       -- video data reset DMA counter request

	component sdramCntl
		generic(
			FREQ:	natural := 25_000;		-- operating frequency in KHz
			DATA_WIDTH: natural := 16;		-- host & SDRAM data width
			NROWS: natural := 4096;			-- number of rows in SDRAM array
			NCOLS: natural := 512;			-- number of columns in SDRAM array
			HADDR_WIDTH: natural := 23;	-- host-side address width
			SADDR_WIDTH: natural := 12		-- SDRAM-side address width
		);
		port(
			clkin:	in	std_logic;				-- master clock

			-- host side
			bufclk:	out std_logic;				-- buffered master clock
			clk0:		out std_logic;				-- host clock sync'ed to master clock
			clk2x:	out std_logic;				-- double-speed host clock
			lock:		out std_logic;				-- indicate when clock circuitry is locked to master clock
			rst:		in	std_logic;				-- reset
			rd:			in	std_logic;				-- read data
			wr:			in	std_logic;				-- write data
			done:		out	std_logic;				-- read/write op done
			hAddr:	in	unsigned(HADDR_WIDTH-1 downto 0);					-- address from host
			hDIn:		in	unsigned(DATA_WIDTH-1 downto 0);					-- data from host
			hDOut:	out	unsigned(DATA_WIDTH-1 downto 0);					-- data to host
			sdramCntl_state: out std_logic_vector(3 downto 0);		

			-- SDRAM side
			sclkfb:	in	std_logic;				-- clock from SDRAM after PCB delays
			sclk:		out std_logic;				-- SDRAM clock sync'ed to master clock
			cke:		out	std_logic;				-- clock-enable to SDRAM
			cs_n:		out	std_logic;				-- chip-select to SDRAM
			ras_n:	out	std_logic;				-- command input to SDRAM
			cas_n:	out	std_logic;				-- command input to SDRAM
			we_n:		out	std_logic;				-- command input to SDRAM
			ba:			out	unsigned(1 downto 0);	-- SDRAM bank address bits
			sAddr:	out	unsigned(SADDR_WIDTH-1 downto 0);					-- SDRAM row/column address
			sData:	inout unsigned(DATA_WIDTH-1 downto 0);				-- SDRAM in/out databus
			dqmh:		out	std_logic;				-- high databits I/O mask
			dqml:		out	std_logic					-- low databits I/O mask
		);
	end component;

	-- SDRAM host side signals
	signal sdram_bufclk : std_logic;    -- buffered input (non-DLL) clock
	signal sdram_clk0   : std_logic;    -- internal master clock signal
	signal sdram_lock   : std_logic;    -- SDRAM clock DLL lock indicator
	signal sdram_rst    : std_logic;    -- internal reset signal
	signal sdram_rd     : std_logic;    -- host-side read control signal
	signal sdram_wr     : std_logic;    -- host-side write control signal
	signal sdram_done   : std_logic;    -- SDRAM operation complete indicator
	signal sdram_hAddr  : unsigned(ADDR_WIDTH-1 downto 0);  -- host address bus
	signal sdram_hDIn   : unsigned(DATA_WIDTH-1 downto 0);	-- host-side data to SDRAM
	signal sdram_hDOut  : unsigned(DATA_WIDTH-1 downto 0);	-- host-side data from SDRAM

	-- memory state management variables
	type memoryStateType is (
		MEMORY_IDLE,         -- finished just waiting for a request
		MEMORY_READ,         -- need to execute a read transaction
		MEMORY_WAIT_FOR_VGA  -- needed to add one additional cycle for vga circuit
	);
	signal memoryState_r, memoryState_nxt: memoryStateType;
	signal hAddr_r, hAddr_nxt  : unsigned(ADDR_WIDTH-1 downto 0);  -- host address bus
	
begin

	pin_ce_n <= '1';		-- disable Flash RAM

	-- connect internal registers to external busses	
	sdram_hAddr <= hAddr_r;		-- memory address bus driven by memory address register

	-- memory controller state machine
	-- "process" the change in status of various signals
	process(sysReset, memoryState_r, sdram_done, vga_vreq, vga_vreset)
	begin

		-- have we been reset?
      if (sysReset = YES) then
			memoryState_nxt <= MEMORY_IDLE;
      	hAddr_nxt <= "00000000000000000000000";
      else
			sdram_rd <= NO;   -- default no memory read
			sdram_wr <= NO;   -- default no memory write
			vga_vack <= NO;   -- default no ack of new data to vga circuit
			memoryState_nxt <= memoryState_r;
			hAddr_nxt <= hAddr_r;		-- next address is the same as current address

			if (vga_vreset = YES) then          -- reset address?
				hAddr_nxt <= "00000000000000000000000";
			end if;

			case memoryState_r is

				-- memory idle, just waiting around for a request
				when MEMORY_IDLE =>
					if (vga_vreq = YES) then
					   vga_vack <= NO;
						memoryState_nxt <= MEMORY_READ;  -- more to read state
					end if;

				-- read from memory		
				when MEMORY_READ =>
					sdram_rd <= YES;                    -- keep asserting read signal
					if (sdram_done = YES) then
	 					vga_pixels_in <= std_logic_vector(sdram_hDOut);
						vga_vack <= YES;
						memoryState_nxt <= MEMORY_WAIT_FOR_VGA;  -- one cycle delay
					end if;

				-- gives the vga circuit one extra cycle (remember it's running at half
				-- the clock rate of sdram controller) to grab data			
				when MEMORY_WAIT_FOR_VGA =>
					vga_pixels_in <= std_logic_vector(sdram_hDOut);
					vga_vack <= YES;
				 	hAddr_nxt <= hAddr_r + 1;        -- increment address counter
					memoryState_nxt <= MEMORY_IDLE;  -- move to idle state
			
			end case;
			
		end if;
		
	end process;

	-- keep on move'n, don't stop!
	process(sysClk, sysReset)
	begin
		if (sysReset=YES) then
			memoryState_r <= MEMORY_IDLE;
			hAddr_r <= "00000000000000000000000";
		elsif (rising_edge(sysClk)) then
			memoryState_r <= memoryState_nxt;
			hAddr_r <= hAddr_nxt;
		end if;
	end process;
	
	-- vga component
	u1: vga
	port map(
		clk        => vga_clk,
		rst        => sysReset,
		vack       => vga_vack,
		pixels_in  => vga_pixels_in,
		vreq       => vga_vreq,
		vreset     => vga_vreset,
		hsync_n    => pin_hsync_n,
		vsync_n    => pin_vsync_n,
		r          => pin_red,
		g          => pin_green,
		b          => pin_blue
		);

	-- simple clock divider
	process(sysClk)
	begin
		if (rising_edge(sysClk)) then
			if (vga_clk=HI) then
				vga_clk <= LO;
			else
				vga_clk <= HI;
			end if;
	end if;
	end process;

	-- SDRAM memory controller module
	u2: sdramCntl
	generic map(
    	FREQ => 25_000,                  -- 25 MHz operation
		DATA_WIDTH => 16,
		NROWS => 4096,
		NCOLS => 512,
		HADDR_WIDTH => 23,
		SADDR_WIDTH => 12
	)
	port map(
		clkin           => pin_clkin,    -- master clock from external clock source (unbuffered)
		bufclk          => sdram_bufclk, -- buffered master clock output
		clk0            => sysClk,       -- synchronized master clock (accounts for delays to external SDRAM)
		clk2x           => open,         -- synchronized doubled master clock
		lock            => sdram_lock,   -- valid synchronized clocks indicator
		rst             => sysReset,     -- reset
		rd              => sdram_rd,     -- host-side SDRAM read control from memory tester
		wr              => sdram_wr,     -- host-side SDRAM write control from memory tester
		done            => sdram_done,   -- SDRAM memory read/write done indicator
		hAddr           => sdram_hAddr,  -- host-side address from memory tester
		hDIn            => sdram_hDIn,   -- always send data from xsoc to memory
		hDOut           => sdram_hDOut,  -- SDRAM data output to memory tester
		sdramCntl_state => open,         -- SDRAM controller state (for diagnostics)
	
		-- SDRAM side
		sclkfb => pin_sclkfb,   -- clock feedback with added external PCB delays
		sclk   => pin_sclk,     -- synchronized clock to external SDRAM
		cke    => pin_cke,      -- SDRAM clock enable
		cs_n   => pin_cs_n,     -- SDRAM chip-select
		ras_n  => pin_ras_n,    -- SDRAM RAS
		cas_n  => pin_cas_n,    -- SDRAM CAS
		we_n   => pin_we_n,     -- SDRAM write-enable
		ba     => pin_ba,       -- SDRAM bank address
		sAddr  => pin_sAddr,    -- SDRAM address
		sData  => pin_sData,    -- SDRAM databus
		dqmh   => pin_dqmh,     -- SDRAM DQMH
		dqml   => pin_dqml      -- SDRAM DQML
	);

	-- synchronous reset.  internal reset flag is set active by config. bitstream
	-- and then gets reset after DLL clocks start.
	process(sdram_bufclk)
	begin
		if (rising_edge(sdram_bufclk)) then
			if sdram_lock='0' then
				sysReset <= '1';     -- keep in reset until DLLs start up
			else
				--sysReset <= '0';
				sysReset <= not pin_pushbtn;  -- push button will reset
			end if;
		end if;
	end process;

	
end arch;

⌨️ 快捷键说明

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