From f3d4079cc4b34f2cfe08df9e4e107e5b5ee96510 Mon Sep 17 00:00:00 2001 From: Jan Michel Date: Thu, 31 Jan 2019 15:26:27 +0100 Subject: [PATCH] additional SPI features for non-standard interfaces --- special/spi_ltc2600.vhd | 84 +++++++++++++++++++++++++---------------- trb_net_components.vhd | 9 +++-- 2 files changed, 56 insertions(+), 37 deletions(-) diff --git a/special/spi_ltc2600.vhd b/special/spi_ltc2600.vhd index 27cf185..56fd0ff 100644 --- a/special/spi_ltc2600.vhd +++ b/special/spi_ltc2600.vhd @@ -2,6 +2,8 @@ library IEEE; use IEEE.STD_LOGIC_1164.all; use IEEE.numeric_std.all; +library work; +use trb_net_std.all; entity spi_ltc2600 is generic( @@ -21,9 +23,9 @@ entity spi_ltc2600 is BUS_DATA_OUT : out std_logic_vector(31 downto 0); -- SPI connections SPI_CS_OUT : out std_logic_vector(15 downto 0); - SPI_SDI_IN : in std_logic; - SPI_SDO_OUT : out std_logic; - SPI_SCK_OUT : out std_logic; + SPI_SDI_IN : in std_logic_vector(15 downto 0); + SPI_SDO_OUT : out std_logic_vector(15 downto 0); + SPI_SCK_OUT : out std_logic_vector(15 downto 0); SPI_CLR_OUT : out std_logic_vector(15 downto 0) ); end entity; @@ -40,11 +42,14 @@ architecture spi_ltc2600_arch of spi_ltc2600 is signal start : std_logic; signal chipselect_reg : std_logic_vector(15 downto 0) := x"0001"; signal clear_reg : std_logic_vector(15 downto 0) := x"0000"; - signal invert_reg : std_logic; - +-- signal invert_reg : std_logic; + signal override_cs, override_sck, override_sdo : std_logic_vector(15 downto 0) := x"0000"; + signal invert_cs, invert_sck, invert_sdo : std_logic_vector(15 downto 0) := x"0000"; + signal spi_cs : std_logic_vector(15 downto 0); signal spi_sck : std_logic; - signal spi_sd : std_logic; + signal spi_sdo : std_logic; + signal spi_sdi : std_logic; signal word_count : integer range 0 to BITS-1; signal bit_count : integer range 0 to BITS-1; @@ -78,8 +83,17 @@ begin ram(addr) <= BUS_DATA_IN; elsif BUS_ADDR_IN(3 downto 0) = x"4" then --0x14 clear_reg <= BUS_DATA_IN(15 downto 0); - elsif BUS_ADDR_IN(3 downto 0) = x"8" then --0x18 - invert_reg <= BUS_DATA_IN(0); + elsif BUS_ADDR_IN(3 downto 0) = x"5" then + override_sdo <= BUS_DATA_IN(15 downto 0); + invert_sdo <= BUS_DATA_IN(31 downto 16); + elsif BUS_ADDR_IN(3 downto 0) = x"6" then + override_sck <= BUS_DATA_IN(15 downto 0); + invert_sck <= BUS_DATA_IN(31 downto 16); + elsif BUS_ADDR_IN(3 downto 0) = x"7" then + override_cs <= BUS_DATA_IN(15 downto 0); + invert_cs <= BUS_DATA_IN(31 downto 16); +-- elsif BUS_ADDR_IN(3 downto 0) = x"8" then --0x18 +-- invert_reg <= BUS_DATA_IN(0); elsif BUS_ADDR_IN(3 downto 0) = x"9" then -- 0x19 word_length <= to_integer(unsigned(BUS_DATA_IN(5 downto 0))); elsif BUS_ADDR_IN(3 downto 0) = x"a" then -- 0x1a @@ -116,9 +130,18 @@ begin elsif BUS_ADDR_IN(3 downto 0) = x"4" then BUS_DATA_OUT(15 downto 0) <= clear_reg; BUS_DATA_OUT(31 downto 16) <= x"0000"; - elsif BUS_ADDR_IN(3 downto 0) = x"8" then - BUS_DATA_OUT(0) <= invert_reg; - BUS_DATA_OUT(31 downto 1) <= (others => '0'); + elsif BUS_ADDR_IN(3 downto 0) = x"5" then + BUS_DATA_OUT(31 downto 16) <= invert_sdo; + BUS_DATA_OUT(15 downto 0) <= override_sdo; + elsif BUS_ADDR_IN(3 downto 0) = x"6" then + BUS_DATA_OUT(31 downto 16) <= invert_sck; + BUS_DATA_OUT(15 downto 0) <= override_sck; + elsif BUS_ADDR_IN(3 downto 0) = x"7" then + BUS_DATA_OUT(31 downto 16) <= invert_cs; + BUS_DATA_OUT(15 downto 0) <= override_cs; +-- elsif BUS_ADDR_IN(3 downto 0) = x"8" then +-- BUS_DATA_OUT(0) <= invert_reg; +-- BUS_DATA_OUT(31 downto 1) <= (others => '0'); elsif BUS_ADDR_IN(3 downto 0) = x"9" then BUS_DATA_OUT <= (others => '0'); BUS_DATA_OUT(5 downto 0) <= std_logic_vector(to_unsigned(word_length,6)); @@ -148,10 +171,10 @@ begin bit_count <= word_length-1; time_count <= wait_cycles; fsm_state <= WAIT_STATE; - spi_cs <= not chipselect_reg; + spi_cs <= chipselect_reg; spi_sck <= '1'; else - spi_cs <= x"ffff"; + spi_cs <= x"0000"; spi_sck <= '1'; end if; @@ -166,7 +189,7 @@ begin time_count <= wait_cycles; spi_sck <= not spi_sck; if spi_sck = '1' then - spi_sd <= ram_data(bit_count); + spi_sdo <= ram_data(bit_count); if bit_count /= 0 then bit_count <= bit_count - 1; fsm_state <= WAIT_STATE; @@ -185,13 +208,13 @@ begin end if; else fsm_state <= WAIT_STATE; - readback <= readback(30 downto 0) & SPI_SDI_IN; + readback <= readback(30 downto 0) & spi_sdi; end if; when TOGGLE_CS => if time_count = 0 and spi_sck = '0' then time_count <= 7; spi_sck <= not spi_sck; - readback <= readback(30 downto 0) & SPI_SDI_IN; + readback <= readback(30 downto 0) & spi_sdi; elsif time_count = 0 and spi_sck = '1' then fsm_state <= TOGGLE_CS_0; else @@ -200,14 +223,14 @@ begin when TOGGLE_CS_0 => time_count <= time_count - 1; if time_count = 0 then - spi_cs <= x"ffff"; + spi_cs <= x"0000"; fsm_state <= TOGGLE_CS_1; time_count <= 7; end if; when TOGGLE_CS_1 => time_count <= time_count - 1; if time_count = 0 then - spi_cs <= not chipselect_reg; + spi_cs <= chipselect_reg; bit_count <= word_length-1; fsm_state <= WAIT_STATE; time_count <= wait_cycles; @@ -223,7 +246,7 @@ begin if time_count = 0 and spi_sck = '0' then time_count <= wait_cycles; spi_sck <= not spi_sck; - readback <= readback(30 downto 0) & SPI_SDI_IN; + readback <= readback(30 downto 0) & spi_sdi; elsif time_count = 0 and spi_sck = '1' then fsm_state <= IDLE; else @@ -235,22 +258,17 @@ begin end if; end process; +-- Outputs and Inputs +spi_sdi <= or_all(SPI_SDI_IN and spi_cs); --- Outputs - Invert : process(invert_reg, spi_cs,spi_sck,spi_sd) - begin - if invert_reg = '1' then - SPI_CS_OUT <= not spi_cs; - SPI_SCK_OUT <= not spi_sck; - SPI_SDO_OUT <= not spi_sd; - else - SPI_CS_OUT <= spi_cs; - SPI_SCK_OUT <= spi_sck; - SPI_SDO_OUT <= spi_sd; - end if; - end process Invert; - SPI_CLR_OUT <= clear_reg; +gen_outputs : for i in 0 to 15 generate + SPI_CS_OUT(i) <= not ((spi_cs(i) and not override_cs(i)) xor invert_cs(i)); + SPI_SDO_OUT(i) <= (spi_sdo and spi_cs(i) and not override_sdo(i)) xor invert_sdo(i); + SPI_SCK_OUT(i) <= (spi_sck and not override_sck(i)) xor invert_sck(i); +end generate; + +SPI_CLR_OUT <= clear_reg; diff --git a/trb_net_components.vhd b/trb_net_components.vhd index 027ae18..47832d0 100644 --- a/trb_net_components.vhd +++ b/trb_net_components.vhd @@ -3119,10 +3119,11 @@ end component; BUS_DATA_OUT : out std_logic_vector(31 downto 0); -- SPI connections SPI_CS_OUT : out std_logic_vector(15 downto 0); - SPI_SDI_IN : in std_logic; - SPI_SDO_OUT : out std_logic; - SPI_SCK_OUT : out std_logic; - SPI_CLR_OUT : out std_logic_vector(15 downto 0)); + SPI_SDI_IN : in std_logic_vector(15 downto 0); + SPI_SDO_OUT : out std_logic_vector(15 downto 0); + SPI_SCK_OUT : out std_logic_vector(15 downto 0); + SPI_CLR_OUT : out std_logic_vector(15 downto 0) + ); end component spi_ltc2600; component signal_sync is -- 2.43.0