-- Serial port driver for external ADCs and DACs -- SNS LLRF Digital board -- Target: XC2S150 -- Larry Doolittle -- November 5, 2001 (Original Verilog) -- Justin Oo -- November 21, 2001 (VHDL adaptation) -- 2 x DAC: MAX528 -- 2 x ADC: MAX1202 -- common sclk, din, dout -- individual chip select lines -- All logic is synchronous with the 25 MHz host computer clock. -- Logic not included here should give us a single clean "write" pulse, -- along with address and data. Output data is always valid, to -- be multiplexed, latched, and driven onto the host bus to support -- read operations. -- Serial port is driven at host clock / 16, or 1.56 MHz (640 ns period). -- The MAX1202 is rated at 2.0 MHz, the MAX528 is rated at 6 MHz. -- A MAX1202 transaction takes 25 serial port clock cycles, or 16.00 uS. -- A MAX528 transaction takes 17 serial port clock cycles, or 10.88 uS. -- The host can tell that a transaction is in progress by reading from -- this device, the low bit is "1" while the port is busy. -- addr[1:0] select device -- 00 cs0 MAX528 -- 01 cs1 MAX528 -- 10 cs2 MAX1202 -- 11 cs3 MAX1202 -- MAX528 write data format: -- a7, a6, a5, a4, a3, a2, a1, a0, d7 (msb), d6, d5, d4, d3,d2, d1, d0 (lsb) -- MAX528 read data format: -- x, x, x, x, x, x, x, x, x, x, x, x, x, x, x, busy -- For the real MAX528 documentation, see http://www.maxim-ic.com/ -- or http://dbserv.maxim-ic.com/quick_view2.cfm?qv_pk=1322 -- MAX1201 write data format: -- 1, sel2, sel1, sel0, uni, sgl, pd1, pd0, 0, 0, 0, 0, 0, 0, 0, 0 -- MAX1201 read data format: -- 0, b11 (msb), b10, b9, b8, b7, b6, b5, b4, b3, b2, b1, b0 (lsb), 0, 0, busy -- For the real MAX1202 documentation, see http://www.maxim-ic.com/ -- or http://dbserv.maxim-ic.com/quick_view2.cfm?qv_pk=1668 library IEEE; use IEEE.std_logic_1164.all; use IEEE.std_logic_arith.all; use IEEE.std_logic_unsigned.all; --use IEEE.numeric_std.all; entity sport is port ( write: in std_logic; addr : in std_logic_vector (1 downto 0); idata: in std_logic_vector (15 downto 0); din : in std_logic; clk : in std_logic; dout : out std_logic; odata: out std_logic_vector (15 downto 0); sclk : out std_logic; cs0 : out std_logic; cs1 : out std_logic; cs2 : out std_logic; cs3 : out std_logic ); end sport; architecture sport_arch of sport is signal ldin : std_logic; signal cke : std_logic; signal slow : std_logic; signal stop : std_logic; signal typ : std_logic; signal running : std_logic; signal cnt : std_logic_vector (8 downto 0); signal data : std_logic_vector (15 downto 0); signal writeORslow : std_logic; signal writeORstop : std_logic; signal slow_cnt16 : std_logic; signal slow_cnt24 : std_logic; signal stop_cnt17 : std_logic; signal stop_cnt25 : std_logic; begin sclk <= cnt(3); cke <= '1' when (cnt(3 downto 0) = "1111") else '0'; slow_cnt16 <= '1' when (cnt(8 downto 4) = "01111") else '0'; slow_cnt24 <= '1' when (cnt(8 downto 4) = "10111") else '0'; stop_cnt17 <= '1' when (cnt(8 downto 4) = "10000") else '0'; stop_cnt25 <= '1' when (cnt(8 downto 4) = "11000") else '0'; dout <= data(15); odata <= data(15 downto 1) & running; slow <= cke and slow_cnt24 when (typ = '1') else cke and slow_cnt16; stop <= cke and stop_cnt25 when (typ = '1') else cke and stop_cnt17; writeORslow <= write or slow; writeORstop <= write or stop; u0: process (clk) begin if (clk'event and clk = '1') then if (writeORstop = '1') then running <= write; end if; if (writeORslow = '1') then cs0 <= not (write and (not addr(1)) and (not addr(0))); cs1 <= not (write and (not addr(1)) and ( addr(0))); cs2 <= not (write and ( addr(1)) and (not addr(0))); cs3 <= not (write and ( addr(1)) and ( addr(0))); end if; if (write = '1') then typ <= addr(1); end if; if (cnt(3 downto 0) = "0111") then ldin <= din; end if; end if; end process u0; u1: process (clk) begin if (clk'event and clk = '1') then if (running = '1') then if (stop = '1') then cnt <= (others => '0'); else cnt <= cnt + 1; end if; end if; end if; end process u1; u2: process (clk) begin if (clk'event and clk = '1') then if (running = '1') then if (cke = '1') then data <= data(14 downto 0) & ldin; end if; elsif (write = '1') then data <= idata; end if; end if; end process u2; end sport_arch; --if (running & cke) then data <= data(14 downto 0) & ldin; --elsif (write) then data <= idata;