aboutsummaryrefslogtreecommitdiff
path: root/basys3
diff options
context:
space:
mode:
Diffstat (limited to 'basys3')
-rw-r--r--basys3/basys3.srcs/ppu.vhd40
-rw-r--r--basys3/basys3.srcs/ppu_addr_dec.vhdl51
-rw-r--r--basys3/basys3.srcs/ppu_addr_dec_tb.vhdl86
-rw-r--r--basys3/basys3.srcs/ppu_consts.vhd22
-rw-r--r--basys3/basys3.xpr23
5 files changed, 197 insertions, 25 deletions
diff --git a/basys3/basys3.srcs/ppu.vhd b/basys3/basys3.srcs/ppu.vhd
index efe2125..28134c6 100644
--- a/basys3/basys3.srcs/ppu.vhd
+++ b/basys3/basys3.srcs/ppu.vhd
@@ -1,38 +1,23 @@
library ieee;
+library work;
+
use ieee.std_logic_1164.all;
--use ieee.numeric_std.all;
+use work.ppu_consts.all;
entity ppu is port(
CLK100: in std_logic; -- system clock
RESET: in std_logic; -- global (async) system reset
EN: in std_logic; -- PPU VRAM enable (enable ADDR and DATA tri-state drivers)
WEN: in std_logic; -- PPU VRAM write enable
- ADDR: in std_logic_vector(15 downto 0); -- PPU VRAM ADDR
- DATA: in std_logic_vector(15 downto 0);
- R,G,B: out std_logic_vector(3 downto 0);
+ ADDR: in std_logic_vector(PPU_RAM_BUS_ADDR_WIDTH-1 downto 0); -- PPU VRAM ADDR
+ DATA: in std_logic_vector(PPU_RAM_BUS_DATA_WIDTH-1 downto 0);
+ R,G,B: out std_logic_vector(PPU_COLOR_OUTPUT_DEPTH-1 downto 0);
NVSYNC, NHSYNC: out std_logic; -- native VGA out
TVSYNC, TVBLANK, THSYNC, THBLANK: out std_logic); -- tiny VGA out
end ppu;
architecture Behavioral of ppu is
- constant PPU_FG_SPRITE_COUNT: natural := 128; -- amount of foreground sprites
- constant PPU_COLOR_OUTPUT_DEPTH: natural := 4; -- VGA output channel depth
- constant PPU_PALETTE_IDX_WIDTH: natural := 3; -- palette index width (within sprite)
- constant PPU_PALETTE_WIDTH: natural := 3; -- palette index width (palette table)
- constant PPU_PALETTE_CIDX_WIDTH: natural := PPU_PALETTE_IDX_WIDTH + PPU_PALETTE_WIDTH; -- global palette index width
- constant PPU_TMM_ADDR_WIDTH: natural := 16;
- constant PPU_TMM_DATA_WIDTH: natural := 16;
- constant PPU_BAM_ADDR_WIDTH: natural := 11;
- constant PPU_BAM_DATA_WIDTH: natural := 15;
- constant PPU_FAM_ADDR_WIDTH: natural := 8;
- constant PPU_FAM_DATA_WIDTH: natural := 16;
- constant PPU_PAL_ADDR_WIDTH: natural := 6;
- constant PPU_PAL_DATA_WIDTH: natural := 12;
- constant PPU_AUX_ADDR_WIDTH: natural := 2;
- constant PPU_AUX_DATA_WIDTH: natural := 16;
- constant PPU_POS_H_WIDTH: natural := 9; -- amount of bits for horizontal screen offset
- constant PPU_POS_V_WIDTH: natural := 8; -- amount of bits for vertical screen offset
-
component ppu_pceg port( -- pipeline clock edge generator
CLK: in std_logic; -- system clock
RESET: in std_logic; -- async reset
@@ -48,7 +33,7 @@ architecture Behavioral of ppu is
PAL_WEN,
AUX_WEN: out std_logic; -- write enable MUX
EN: in std_logic; -- EXT *ADDR enable (switch *AO to ADDR instead of *AI)
- ADDR: in std_logic_vector(15 downto 0); -- address in
+ ADDR: in std_logic_vector(PPU_RAM_BUS_ADDR_WIDTH-1 downto 0); -- address in
TMM_AI: in std_logic_vector(PPU_TMM_ADDR_WIDTH-1 downto 0);
BAM_AI: in std_logic_vector(PPU_BAM_ADDR_WIDTH-1 downto 0);
FAM_AI: in std_logic_vector(PPU_FAM_ADDR_WIDTH-1 downto 0);
@@ -150,7 +135,7 @@ architecture Behavioral of ppu is
PAL_ADDR: in std_logic_vector(PPU_PAL_ADDR_WIDTH-1 downto 0); -- VRAM PAL address
PAL_DATA: in std_logic_vector(PPU_PAL_DATA_WIDTH-1 downto 0); -- VRAM PAL data
- R,G,B: out std_logic_vector(3 downto 0)); -- VGA color out
+ R,G,B: out std_logic_vector(PPU_COLOR_OUTPUT_DEPTH-1 downto 0)); -- VGA color out
end component;
component ppu_vga_tiny port( -- tiny vga signal generator
CLK: in std_logic; -- system clock
@@ -203,6 +188,15 @@ begin
SYSCLK <= CLK100;
SYSRST <= RESET;
+ -- internal unused lines
+ --
+ -- these lines would be used if components use memory blocks as RAM blocks
+ -- (like how TMM and BAM work), the registers of these memory regions are
+ -- directly exposed internally, and are as such not used as RAM blocks
+ AUX_AI <= (others => '0');
+ FAM_AI <= (others => '0');
+ PAL_AI <= (others => '0');
+
pipeline_clock_edge_generator: component ppu_pceg port map(
CLK => SYSCLK,
RESET => SYSRST,
diff --git a/basys3/basys3.srcs/ppu_addr_dec.vhdl b/basys3/basys3.srcs/ppu_addr_dec.vhdl
new file mode 100644
index 0000000..28c22fc
--- /dev/null
+++ b/basys3/basys3.srcs/ppu_addr_dec.vhdl
@@ -0,0 +1,51 @@
+library ieee;
+library work;
+use ieee.std_logic_1164.all;
+--use ieee.numeric_std.all;
+use work.ppu_consts.all;
+
+entity ppu_addr_dec is port(
+ EN: in std_logic; -- EXT *ADDR enable (switch *AO to ADDR instead of *AI)
+ WEN: in std_logic; -- EXT write enable
+ TMM_WEN,
+ BAM_WEN,
+ FAM_WEN,
+ PAL_WEN,
+ AUX_WEN: out std_logic; -- write enable MUX
+ ADDR: in std_logic_vector(PPU_RAM_BUS_ADDR_WIDTH-1 downto 0); -- address in
+ TMM_AI: in std_logic_vector(PPU_TMM_ADDR_WIDTH-1 downto 0);
+ BAM_AI: in std_logic_vector(PPU_BAM_ADDR_WIDTH-1 downto 0);
+ FAM_AI: in std_logic_vector(PPU_FAM_ADDR_WIDTH-1 downto 0);
+ PAL_AI: in std_logic_vector(PPU_PAL_ADDR_WIDTH-1 downto 0);
+ AUX_AI: in std_logic_vector(PPU_AUX_ADDR_WIDTH-1 downto 0);
+ TMM_AO: out std_logic_vector(PPU_TMM_ADDR_WIDTH-1 downto 0);
+ BAM_AO: out std_logic_vector(PPU_BAM_ADDR_WIDTH-1 downto 0);
+ FAM_AO: out std_logic_vector(PPU_FAM_ADDR_WIDTH-1 downto 0);
+ PAL_AO: out std_logic_vector(PPU_PAL_ADDR_WIDTH-1 downto 0);
+ AUX_AO: out std_logic_vector(PPU_AUX_ADDR_WIDTH-1 downto 0));
+end ppu_addr_dec;
+
+architecture Behavioral of ppu_addr_dec is
+ signal TMM_RANGE, BAM_RANGE, FAM_RANGE, PAL_RANGE, AUX_RANGE: std_logic := '0'; -- ADDR in range of memory area
+begin
+ -- address MUX
+ TMM_AO <= ADDR(PPU_TMM_ADDR_WIDTH-1 downto 0) when EN = '1' else TMM_AI;
+ BAM_AO <= ADDR(PPU_BAM_ADDR_WIDTH-1 downto 0) when EN = '1' else BAM_AI;
+ FAM_AO <= ADDR(PPU_FAM_ADDR_WIDTH-1 downto 0) when EN = '1' else FAM_AI;
+ PAL_AO <= ADDR(PPU_PAL_ADDR_WIDTH-1 downto 0) when EN = '1' else PAL_AI;
+ AUX_AO <= ADDR(PPU_AUX_ADDR_WIDTH-1 downto 0) when EN = '1' else AUX_AI;
+
+ -- WEN MUX
+ TMM_WEN <= TMM_RANGE and WEN;
+ BAM_WEN <= BAM_RANGE and WEN;
+ FAM_WEN <= FAM_RANGE and WEN;
+ PAL_WEN <= PAL_RANGE and WEN;
+ AUX_WEN <= AUX_RANGE and WEN;
+
+ -- address ranges
+ TMM_RANGE <= '1' when not (ADDR(15) = '1' and ADDR(14) = '1') else '0';
+ BAM_RANGE <= '1' when (ADDR(15) = '1' and ADDR(14) = '1') and (ADDR(11) = '0') else '0';
+ FAM_RANGE <= '1' when (ADDR(15) = '1' and ADDR(14) = '1') and (ADDR(11) = '1' and ADDR(10) = '0') else '0';
+ PAL_RANGE <= '1' when (ADDR(15) = '1' and ADDR(14) = '1') and (ADDR(11) = '1' and ADDR(10) = '1' and ADDR(9) = '0') else '0';
+ AUX_RANGE <= '1' when (ADDR(15) = '1' and ADDR(14) = '1') and (ADDR(11) = '1' and ADDR(10) = '1' and ADDR(9) = '1') else '0';
+end Behavioral;
diff --git a/basys3/basys3.srcs/ppu_addr_dec_tb.vhdl b/basys3/basys3.srcs/ppu_addr_dec_tb.vhdl
new file mode 100644
index 0000000..5c7119d
--- /dev/null
+++ b/basys3/basys3.srcs/ppu_addr_dec_tb.vhdl
@@ -0,0 +1,86 @@
+library ieee;
+library unisim;
+library work;
+
+use ieee.std_logic_1164.all;
+use ieee.numeric_std.all;
+use unisim.vcomponents.all;
+use work.ppu_consts.all;
+
+entity ppu_addr_dec_tb is
+end ppu_addr_dec_tb;
+
+architecture behavioral of ppu_addr_dec_tb is
+ component ppu_addr_dec port(
+ EN: in std_logic; -- EXT *ADDR enable (switch *AO to ADDR instead of *AI)
+ WEN: in std_logic; -- EXT write enable
+ TMM_WEN,
+ BAM_WEN,
+ FAM_WEN,
+ PAL_WEN,
+ AUX_WEN: out std_logic; -- write enable MUX
+ ADDR: in std_logic_vector(PPU_RAM_BUS_ADDR_WIDTH-1 downto 0); -- address in
+ TMM_AI: in std_logic_vector(PPU_TMM_ADDR_WIDTH-1 downto 0);
+ BAM_AI: in std_logic_vector(PPU_BAM_ADDR_WIDTH-1 downto 0);
+ FAM_AI: in std_logic_vector(PPU_FAM_ADDR_WIDTH-1 downto 0);
+ PAL_AI: in std_logic_vector(PPU_PAL_ADDR_WIDTH-1 downto 0);
+ AUX_AI: in std_logic_vector(PPU_AUX_ADDR_WIDTH-1 downto 0);
+ TMM_AO: out std_logic_vector(PPU_TMM_ADDR_WIDTH-1 downto 0);
+ BAM_AO: out std_logic_vector(PPU_BAM_ADDR_WIDTH-1 downto 0);
+ FAM_AO: out std_logic_vector(PPU_FAM_ADDR_WIDTH-1 downto 0);
+ PAL_AO: out std_logic_vector(PPU_PAL_ADDR_WIDTH-1 downto 0);
+ AUX_AO: out std_logic_vector(PPU_AUX_ADDR_WIDTH-1 downto 0));
+ end component;
+ signal EN: std_logic;
+ signal WEN: std_logic;
+ signal TMM_WEN, BAM_WEN, FAM_WEN, PAL_WEN, AUX_WEN: std_logic;
+ signal ADDR: std_logic_vector(PPU_RAM_BUS_ADDR_WIDTH-1 downto 0);
+ signal TMM_AI: std_logic_vector(PPU_TMM_ADDR_WIDTH-1 downto 0);
+ signal BAM_AI: std_logic_vector(PPU_BAM_ADDR_WIDTH-1 downto 0);
+ signal FAM_AI: std_logic_vector(PPU_FAM_ADDR_WIDTH-1 downto 0);
+ signal PAL_AI: std_logic_vector(PPU_PAL_ADDR_WIDTH-1 downto 0);
+ signal AUX_AI: std_logic_vector(PPU_AUX_ADDR_WIDTH-1 downto 0);
+ signal TMM_AO: std_logic_vector(PPU_TMM_ADDR_WIDTH-1 downto 0);
+ signal BAM_AO: std_logic_vector(PPU_BAM_ADDR_WIDTH-1 downto 0);
+ signal FAM_AO: std_logic_vector(PPU_FAM_ADDR_WIDTH-1 downto 0);
+ signal PAL_AO: std_logic_vector(PPU_PAL_ADDR_WIDTH-1 downto 0);
+ signal AUX_AO: std_logic_vector(PPU_AUX_ADDR_WIDTH-1 downto 0);
+begin
+ uut: ppu_addr_dec port map(
+ EN => EN,
+ WEN => WEN,
+ TMM_WEN => TMM_WEN,
+ BAM_WEN => BAM_WEN,
+ FAM_WEN => FAM_WEN,
+ PAL_WEN => PAL_WEN,
+ AUX_WEN => AUX_WEN,
+ ADDR => ADDR,
+ TMM_AI => TMM_AI,
+ BAM_AI => BAM_AI,
+ FAM_AI => FAM_AI,
+ PAL_AI => PAL_AI,
+ AUX_AI => AUX_AI,
+ TMM_AO => TMM_AO,
+ BAM_AO => BAM_AO,
+ FAM_AO => FAM_AO,
+ PAL_AO => PAL_AO,
+ AUX_AO => AUX_AO);
+
+ EN <= '1';
+ WEN <= '1';
+
+ TMM_AI <= (others => '1');
+ BAM_AI <= (others => '0');
+ FAM_AI <= (others => '1');
+ PAL_AI <= (others => '0');
+ AUX_AI <= (others => '0');
+
+ tb: process
+ begin
+ for i in 0 to 65535 loop
+ ADDR <= std_logic_vector(to_unsigned(i,16));
+ wait for 10 ps;
+ end loop;
+ wait; -- stop for simulator
+ end process;
+end;
diff --git a/basys3/basys3.srcs/ppu_consts.vhd b/basys3/basys3.srcs/ppu_consts.vhd
new file mode 100644
index 0000000..d3c8403
--- /dev/null
+++ b/basys3/basys3.srcs/ppu_consts.vhd
@@ -0,0 +1,22 @@
+package ppu_consts is
+ constant PPU_RAM_BUS_ADDR_WIDTH: natural := 16; -- RAM bus address width
+ constant PPU_RAM_BUS_DATA_WIDTH: natural := 16; -- RAM bus data width
+ constant PPU_FG_SPRITE_COUNT: natural := 128; -- amount of foreground sprites
+ constant PPU_COLOR_OUTPUT_DEPTH: natural := 4; -- VGA output channel depth
+ constant PPU_PALETTE_IDX_WIDTH: natural := 3; -- palette index width (within sprite)
+ constant PPU_PALETTE_WIDTH: natural := 3; -- palette index width (palette table)
+ constant PPU_PALETTE_CIDX_WIDTH: natural := PPU_PALETTE_IDX_WIDTH + PPU_PALETTE_WIDTH; -- global palette index width
+ constant PPU_TMM_ADDR_WIDTH: natural := 16;
+ constant PPU_TMM_DATA_WIDTH: natural := 16;
+ constant PPU_BAM_ADDR_WIDTH: natural := 11;
+ constant PPU_BAM_DATA_WIDTH: natural := 15;
+ constant PPU_FAM_ADDR_WIDTH: natural := 8;
+ constant PPU_FAM_DATA_WIDTH: natural := 16;
+ constant PPU_PAL_ADDR_WIDTH: natural := 6;
+ constant PPU_PAL_DATA_WIDTH: natural := 12;
+ constant PPU_AUX_ADDR_WIDTH: natural := 2;
+ constant PPU_AUX_DATA_WIDTH: natural := 16;
+ constant PPU_POS_H_WIDTH: natural := 9; -- amount of bits for horizontal screen offset
+ constant PPU_POS_V_WIDTH: natural := 8; -- amount of bits for vertical screen offset
+end package ppu_consts;
+
diff --git a/basys3/basys3.xpr b/basys3/basys3.xpr
index 1a6d509..5df2675 100644
--- a/basys3/basys3.xpr
+++ b/basys3/basys3.xpr
@@ -59,7 +59,7 @@
<Option Name="IPStaticSourceDir" Val="$PIPUSERFILESDIR/ipstatic"/>
<Option Name="EnableBDX" Val="FALSE"/>
<Option Name="DSABoardId" Val="basys3"/>
- <Option Name="WTXSimLaunchSim" Val="4"/>
+ <Option Name="WTXSimLaunchSim" Val="12"/>
<Option Name="WTModelSimLaunchSim" Val="0"/>
<Option Name="WTQuestaLaunchSim" Val="0"/>
<Option Name="WTIesLaunchSim" Val="0"/>
@@ -90,6 +90,18 @@
<FileSets Version="1" Minor="31">
<FileSet Name="sources_1" Type="DesignSrcs" RelSrcDir="$PSRCDIR/sources_1" RelGenDir="$PGENDIR/sources_1">
<Filter Type="Srcs"/>
+ <File Path="$PSRCDIR/ppu_consts.vhd">
+ <FileInfo>
+ <Attr Name="UsedIn" Val="synthesis"/>
+ <Attr Name="UsedIn" Val="simulation"/>
+ </FileInfo>
+ </File>
+ <File Path="$PSRCDIR/ppu_addr_dec.vhdl">
+ <FileInfo>
+ <Attr Name="UsedIn" Val="synthesis"/>
+ <Attr Name="UsedIn" Val="simulation"/>
+ </FileInfo>
+ </File>
<File Path="$PSRCDIR/ppu_pceg.vhdl">
<FileInfo>
<Attr Name="UsedIn" Val="synthesis"/>
@@ -116,15 +128,22 @@
</FileSet>
<FileSet Name="sim_1" Type="SimulationSrcs" RelSrcDir="$PSRCDIR/sim_1" RelGenDir="$PGENDIR/sim_1">
<Filter Type="Srcs"/>
+ <File Path="$PSRCDIR/ppu_addr_dec_tb.vhdl">
+ <FileInfo>
+ <Attr Name="UsedIn" Val="synthesis"/>
+ <Attr Name="UsedIn" Val="simulation"/>
+ </FileInfo>
+ </File>
<File Path="$PSRCDIR/ppu_pceg_tb.vhdl">
<FileInfo>
+ <Attr Name="AutoDisabled" Val="1"/>
<Attr Name="UsedIn" Val="synthesis"/>
<Attr Name="UsedIn" Val="simulation"/>
</FileInfo>
</File>
<Config>
<Option Name="DesignMode" Val="RTL"/>
- <Option Name="TopModule" Val="ppu_pceg_tb"/>
+ <Option Name="TopModule" Val="ppu_addr_dec_tb"/>
<Option Name="TopLib" Val="xil_defaultlib"/>
<Option Name="TransportPathDelay" Val="0"/>
<Option Name="TransportIntDelay" Val="0"/>