From 6d0263f280b4fdbed51c638f3e4195bd36726f1e Mon Sep 17 00:00:00 2001 From: David Banks Date: Wed, 26 Apr 2017 18:15:47 +0100 Subject: [PATCH] Removed obsolete VSYNC logic from CPLD, pass through CSYNC to ARM Change-Id: I01c855dfd71e225bafbc5a03841581e9ff5c33cb --- src/defs.h | 8 ++----- src/rgb_to_fb.S | 48 ++++++++++++++-------------------------- src/rgb_to_hdmi.c | 4 +--- vhdl/RGBtoHDMI.ucf | 10 +++------ vhdl/RGBtoHDMI.vhdl | 53 ++++++++++----------------------------------- 5 files changed, 34 insertions(+), 89 deletions(-) diff --git a/src/defs.h b/src/defs.h index 7c3b76fa..cf0e9137 100644 --- a/src/defs.h +++ b/src/defs.h @@ -20,16 +20,12 @@ #define PIXEL_BASE (2) #define PSYNC_PIN (17) -#define HSYNC_PIN (18) -#define VSYNC_PIN (19) -#define FIELD_PIN (20) +#define CSYNC_PIN (18) #define GPCLK_PIN (21) #define LED_PIN (47) #define PSYNC_MASK (1 << PSYNC_PIN) -#define HSYNC_MASK (1 << HSYNC_PIN) -#define VSYNC_MASK (1 << VSYNC_PIN) -#define FIELD_MASK (1 << FIELD_PIN) +#define CSYNC_MASK (1 << CSYNC_PIN) #endif diff --git a/src/rgb_to_fb.S b/src/rgb_to_fb.S index 181879c0..c73de1e5 100644 --- a/src/rgb_to_fb.S +++ b/src/rgb_to_fb.S @@ -1,15 +1,11 @@ #include "rpi-base.h" #include "defs.h" -// If LINE_DOUBLE is set, then each line in the field -// is written to two adjacent lines. This greatly -// improved the look of 50Hz games like Rocket Raid. -// -// At the moment, this only works with non-interlace -// video, as there is a bug in the CPLD that introduces -// line jitter with interlaced video. - -// #define LINE_DOUBLE +// TODO: +// - detection of none-interlaced video and auto line double +// - fix slight horizontal offset in the different modes +// - somehow autodetect Mode 7 +// - switch clock and sampling point dynamically betweem modes Modes 0-6 and Mode 7 .text .global rgb_to_fb @@ -22,37 +18,28 @@ // r3 = unused // -// Note, in this version we are using HSYNC which is the inverse of CSYNC .macro WAIT_FOR_CSYNC_0 - WAIT_FOR_HSYNC_1 +wait\@: + // Read the GPLEV0 + ldr r8, [r4] + tst r8, #CSYNC_MASK + bne wait\@ + // Check again in case of noise + ldr r8, [r4] + tst r8, #CSYNC_MASK + bne wait\@ .endm .macro WAIT_FOR_CSYNC_1 - WAIT_FOR_HSYNC_0 -.endm - -.macro WAIT_FOR_HSYNC_0 wait\@: // Read the GPLEV0 ldr r8, [r4] - tst r8, #HSYNC_MASK - bne wait\@ - // Check again in case of noise - ldr r8, [r4] - tst r8, #HSYNC_MASK - bne wait\@ -.endm - -.macro WAIT_FOR_HSYNC_1 -wait\@: - // Read the GPLEV0 - ldr r8, [r4] - tst r8, #HSYNC_MASK + tst r8, #CSYNC_MASK beq wait\@ // Check again in case of noise ldr r8, [r4] - tst r8, #HSYNC_MASK + tst r8, #CSYNC_MASK beq wait\@ .endm @@ -234,9 +221,6 @@ process_chars_loop: and r9, r8, #(7 << (PIXEL_BASE + 9)) orr r10, r10, r9, lsl #13 -#ifdef LINE_DOUBLE - str r10, [r12, r2] -#endif str r10, [r12], #4 subs r6, r6, #1 diff --git a/src/rgb_to_hdmi.c b/src/rgb_to_hdmi.c index 6a65c25a..bef18921 100644 --- a/src/rgb_to_hdmi.c +++ b/src/rgb_to_hdmi.c @@ -204,9 +204,7 @@ void init_hardware() { RPI_SetGpioPinFunction(PIXEL_BASE + i, FS_INPUT); } RPI_SetGpioPinFunction(PSYNC_PIN, FS_INPUT); - RPI_SetGpioPinFunction(HSYNC_PIN, FS_INPUT); - RPI_SetGpioPinFunction(VSYNC_PIN, FS_INPUT); - RPI_SetGpioPinFunction(FIELD_PIN, FS_INPUT); + RPI_SetGpioPinFunction(CSYNC_PIN, FS_INPUT); // Configure the GPCLK to 64MHz RPI_SetGpioPinFunction(GPCLK_PIN, FS_ALT5); diff --git a/vhdl/RGBtoHDMI.ucf b/vhdl/RGBtoHDMI.ucf index 34c4430a..09d257f1 100644 --- a/vhdl/RGBtoHDMI.ucf +++ b/vhdl/RGBtoHDMI.ucf @@ -10,7 +10,7 @@ NET "clk" LOC = "P43"; # input NET "R" LOC = "P12"; # input NET "G" LOC = "P13"; # input NET "B" LOC = "P14"; # input -NET "nCSYNC" LOC = "P16"; # input +NET "S" LOC = "P16"; # input NET "SW" LOC = "P18"; # input NET "quad(0)" LOC = "P37"; # output @@ -26,9 +26,7 @@ NET "quad(9)" LOC = "P29"; # output NET "quad(10)" LOC = "P21"; # output NET "quad(11)" LOC = "P20"; # output NET "psync" LOC = "P33"; # output -NET "hsync" LOC = "P32"; # output -NET "vsync" LOC = "P19"; # output -NET "field" LOC = "P2"; # output +NET "csync" LOC = "P32"; # output NET "LED1" LOC = "P39"; # output NET "LED2" LOC = "P38"; # output @@ -45,8 +43,6 @@ NET "quad(9)" SLOW; NET "quad(10)" SLOW; NET "quad(11)" SLOW; NET "psync" SLOW; -NET "hsync" SLOW; -NET "vsync" SLOW; -NET "field" SLOW; +NET "csync" SLOW; NET "LED1" SLOW; NET "LED2" SLOW; diff --git a/vhdl/RGBtoHDMI.vhdl b/vhdl/RGBtoHDMI.vhdl index ae6b4b35..49cb203d 100644 --- a/vhdl/RGBtoHDMI.vhdl +++ b/vhdl/RGBtoHDMI.vhdl @@ -19,7 +19,7 @@ entity RGBtoHDMI is R: in std_logic; G: in std_logic; B: in std_logic; - nCSYNC: in std_logic; + S: in std_logic; -- From Pi clk: in std_logic; @@ -27,9 +27,7 @@ entity RGBtoHDMI is -- To PI GPIO quad: out std_logic_vector(11 downto 0); psync: out std_logic; - hsync: out std_logic; - vsync: out std_logic; - field: out std_logic; + csync: out std_logic; -- Test SW: in std_logic; @@ -42,14 +40,13 @@ architecture Behavorial of RGBtoHDMI is -- For Mode 7 -- constant sample_point : unsigned(10 downto 0) := to_unsigned(2048 - 48 * 2 + 3, 11); - + -- For Modes 6..0 constant sample_point : unsigned(10 downto 0) := to_unsigned(2048 - 32 * 23 + 3, 11); signal shift : std_logic_vector(11 downto 0); - signal nCSYNC1 : std_logic; - signal nCSYNC2 : std_logic; + signal CSYNC1 : std_logic; -- The counter runs at 4x pixel clock -- @@ -75,9 +72,9 @@ architecture Behavorial of RGBtoHDMI is begin - process(nCSYNC) + process(S) begin - if rising_edge(nCSYNC) then + if rising_edge(S) then led_counter <= led_counter + 1; end if; end process; @@ -85,40 +82,14 @@ begin process(clk) begin if rising_edge(clk) then - -- synchronize nCSYNC to the sampling clock - nCSYNC1 <= nCSYNC; - nCSYNC2 <= nCSYNC1; + -- synchronize CSYNC to the sampling clock + CSYNC1 <= S; - if nCSYNC1 = '0' and nCSYNC2 = '1' then - -- start of horizontal line sync pulse - hsync <= '1'; + if CSYNC1 = '0' then + -- in the line sync psync <= '0'; - -- counter is used to measure how long the pulse is - counter <= to_unsigned(0, counter'length); - - elsif nCSYNC1 = '1' and nCSYNC2 = '0' then - -- end of horizontal line sync pulse - hsync <= '0'; - - -- test for vertical sync - -- a normal line sync pulse is 4us - -- a saturated counter (512 == 8us) value can only happen during vsync - if counter = 512 then - vsync <= '1'; - else - vsync <= '0'; - end if; - -- counter is used to find sampling point for first pixel counter <= sample_point; - - elsif nCSYNC1 = '0' then - -- within the line sync pulse - -- saturate counter at 8us. - if counter < 512 then - counter <= counter + 1; - end if; - else -- within the line if counter = 31 then @@ -142,8 +113,8 @@ begin end if; end process; - field <= '1'; - + csync <= CSYNC1; + LED1 <= not SW; LED2 <= led_counter(led_counter'left);