]> jspc29.x-matter.uni-frankfurt.de Git - trbnet.git/commitdiff
added regIO for addresses, Jan
authorhadeshyp <hadeshyp>
Wed, 2 Apr 2008 13:08:32 +0000 (13:08 +0000)
committerhadeshyp <hadeshyp>
Wed, 2 Apr 2008 13:08:32 +0000 (13:08 +0000)
12 files changed:
testbench/trb_net16_dummy_apl.vhd
trb_net16_addresses.vhd [new file with mode: 0644]
trb_net16_api_base.vhd
trb_net16_hub_base.vhd
trb_net16_hub_logic.vhd
trb_net16_ibuf.vhd
trb_net16_regIO.vhd
trb_net_ram.vhd
trb_net_ram_16x8_dp.vhd [new file with mode: 0644]
trb_net_ram_dp.vhd [new file with mode: 0644]
trb_net_ram_true_dp.vhd [new file with mode: 0644]
trb_net_std.vhd

index 1ce0a85dfe040d9853523012d5b26522060e935c..bf957ffd63159cab8c571e6ac7f245eacaf75dfd 100644 (file)
@@ -15,8 +15,8 @@ use work.trb_net_std.all;
 entity trb_net16_dummy_apl is
   generic (
     TARGET_ADDRESS : std_logic_vector (15 downto 0) := x"F001";
-    PREFILL_LENGTH  : integer := 1;
-    TRANSFER_LENGTH  : integer := 1  -- length of dummy data
+    PREFILL_LENGTH  : integer := 2;
+    TRANSFER_LENGTH  : integer := 2  -- length of dummy data
                                   -- might not work with transfer_length > api_fifo
                                   -- because of incorrect handling of fifo_full_in!
 
@@ -67,7 +67,7 @@ begin
 --   address <= x"0008";
 --   reghigh <= x"DEAD";
 --   reglow  <= x"AFFE";
-  address <= x"0003";
+  address <= x"AD01";
   reghigh <= x"000B";
   reglow  <= x"000D";
 
@@ -84,7 +84,7 @@ begin
     end process;
 
   APL_READ_OUT <= '1';                  --just read, do not check
-  APL_DTYPE_OUT <= "1001";
+  APL_DTYPE_OUT <= "1111";
   APL_ERROR_PATTERN_OUT <= x"12345678";
   APL_TARGET_ADDRESS_OUT <= TARGET_ADDRESS;
   --APL_DATA_OUT <= reg_counter;
diff --git a/trb_net16_addresses.vhd b/trb_net16_addresses.vhd
new file mode 100644 (file)
index 0000000..b0a887e
--- /dev/null
@@ -0,0 +1,188 @@
+LIBRARY IEEE;
+USE IEEE.std_logic_1164.ALL;
+USE IEEE.std_logic_ARITH.ALL;
+USE IEEE.std_logic_UNSIGNED.ALL;
+library work;
+use work.trb_net_std.all;
+
+
+entity trb_net16_addresses is
+  generic(
+    INIT_ADDRESS   : std_logic_vector(15 downto 0) := x"FFFF";
+    INIT_UNIQUE_ID : std_logic_vector(95 downto 0) := x"1000_2000_3654_4876_5bcd_6ef1"
+    );
+  port(
+    CLK    : in std_logic;
+    RESET  : in std_logic;
+    CLK_EN : in std_logic;
+    API_DATA_IN       : in  std_logic_vector(15 downto 0);
+    API_DATAREADY_IN  : in  std_logic;
+    API_READ_OUT      : out std_logic;
+    RAM_DATA_IN       : in  std_logic_vector(15 downto 0);
+    RAM_DATA_OUT      : out std_logic_vector(15 downto 0);
+    RAM_ADDR_IN       : in  std_logic_vector(2 downto 0);
+    RAM_WR_IN         : in  std_logic;
+    API_DATA_OUT      : out std_logic_vector(15 downto 0);
+    API_PACKET_NUM_OUT: out std_logic_vector(1 downto 0);
+    API_DATAREADY_OUT : out std_logic;
+    API_READ_IN       : in  std_logic;
+    ADDRESS_REJECTED  : out std_logic; 
+    ADDRESS_OUT       : out std_logic_vector(15 downto 0)
+    );
+end entity;
+
+architecture trb_net16_addresses_arch of trb_net16_addresses is
+  component trb_net_ram_16x8_dp is
+    generic(
+      INIT0 : std_logic_vector(15 downto 0) := x"0000";
+      INIT1 : std_logic_vector(15 downto 0) := x"0000";
+      INIT2 : std_logic_vector(15 downto 0) := x"0000";
+      INIT3 : std_logic_vector(15 downto 0) := x"0000";
+      INIT4 : std_logic_vector(15 downto 0) := x"0000";
+      INIT5 : std_logic_vector(15 downto 0) := x"0000";
+      INIT6 : std_logic_vector(15 downto 0) := x"0000";
+      INIT7 : std_logic_vector(15 downto 0) := x"0000"
+      );
+    port(
+      CLK   : in  std_logic;
+      wr1   : in  std_logic;
+      a1    : in  std_logic_vector(2 downto 0);
+      dout1 : out std_logic_vector(15 downto 0);
+      din1  : in  std_logic_vector(15 downto 0);
+      a2    : in  std_logic_vector(2 downto 0);
+      dout2 : out std_logic_vector(15 downto 0)
+      );
+  end component;
+
+signal write_ADDRESS : std_logic;
+signal ram_read_addr : std_logic_vector(2 downto 0);
+signal ram_read_dout : std_logic_vector(15 downto 0);
+signal matching_counter : std_logic_vector(2 downto 0);
+signal ram_read_addr1 : std_logic_vector(2 downto 0);
+signal ram_read_addr2 : std_logic_vector(2 downto 0);
+signal buf_API_READ_OUT, next_API_READ_OUT : std_logic;
+
+type state_t is (IDLE, SEND1, SEND2, SEND3);
+signal next_state, state : state_t;
+
+--memory
+--00: SET_ADDRESS & endpoint_id
+--01: unique_id_0
+--02: unique_id_1
+--03: unique_id_2
+--04: unique_id_3
+--05: 00 & board_info0
+--06: board_info1
+--07: ACK_ADDRESS
+
+begin
+
+
+  ram_read_addr <= ram_read_addr1 or ram_read_addr2;
+
+  read_id : process(CLK)
+    begin
+      if rising_edge(CLK) then
+        if RESET = '1' then
+          ADDRESS_OUT <= INIT_ADDRESS;
+          ram_read_addr1 <= (others => '0');
+          matching_counter <= (others => '0');
+        else
+          buf_API_READ_OUT <= '1';
+          write_ADDRESS <= '0';
+          ADDRESS_REJECTED <= '0';
+          if API_DATAREADY_IN = '1' and buf_API_READ_OUT = '1' then
+            buf_API_READ_OUT <= '0';
+            ram_read_addr1 <= ram_read_addr1 + 1;
+            if API_DATA_IN = ram_read_dout then
+              matching_counter <= matching_counter + 1;
+            end if;
+            if ram_read_addr1 = "101" then
+              matching_counter <= "000";
+              ram_read_addr1 <= "000";
+              if matching_counter = "101" then
+                ADDRESS_OUT <= API_DATA_IN;
+                write_ADDRESS <= '1';
+              else
+                ADDRESS_REJECTED <= '1';
+              end if;
+            end if;
+          end if;
+        end if;
+      end if;
+    end process;
+
+  send_ack : process(write_ADDRESS, state, API_READ_IN, ram_read_dout)
+    begin
+      next_state <= state;
+      API_DATAREADY_OUT <= '0';
+      API_PACKET_NUM_OUT <= "01";
+      API_DATA_OUT <= ram_read_dout;
+      ram_read_addr2 <= "000";
+
+      case state is
+        when IDLE =>
+          if write_ADDRESS = '1' then
+            ram_read_addr2 <= "101";
+            next_state <= SEND1;
+          end if;
+        when SEND1 =>
+          API_DATAREADY_OUT <= '1';
+          API_PACKET_NUM_OUT <= "01";
+          ram_read_addr2 <= "101";
+          if API_READ_IN = '1' then
+            ram_read_addr2 <= "110";
+            next_state <= SEND2;
+          end if;
+        when SEND2 =>
+          API_DATAREADY_OUT <= '1';
+          API_PACKET_NUM_OUT <= "10";
+          ram_read_addr2 <= "110";
+          if API_READ_IN = '1' then
+            ram_read_addr2 <= "111";
+            next_state <= SEND3;
+          end if;
+        when SEND3 =>
+          API_DATAREADY_OUT <= '1';
+          API_PACKET_NUM_OUT <= "11";
+          ram_read_addr2 <= "111";
+          if API_READ_IN = '1' then
+            next_state <= IDLE;
+            ram_read_addr2 <= "000";
+          end if;
+      end case;
+    end process;
+
+
+  process(CLK)
+    begin
+      if rising_edge(CLK) then
+        state <= next_state;
+       -- buf_API_READ_OUT <= next_API_READ_OUT;
+      end if;
+    end process;
+
+  STAT_RAM : trb_net_ram_16x8_dp
+    generic map(
+      INIT0 => SET_ADDRESS & INIT_UNIQUE_ID(71 downto 64),
+      INIT1 => INIT_UNIQUE_ID(15 downto 0),
+      INIT2 => INIT_UNIQUE_ID(31 downto 16),
+      INIT3 => INIT_UNIQUE_ID(47 downto 32),
+      INIT4 => INIT_UNIQUE_ID(63 downto 48),
+      INIT5 => ACK_ADDRESS,
+      INIT6 => x"00" & INIT_UNIQUE_ID(79 downto 72),
+      INIT7 => INIT_UNIQUE_ID(95 downto 80)
+      )
+    port map(
+      CLK     => CLK,
+      wr1     => RAM_WR_IN,
+      a1      => RAM_ADDR_IN,
+      din1    => RAM_DATA_IN,
+      dout1   => RAM_DATA_OUT,
+      a2      => ram_read_addr,
+      dout2   => ram_read_dout
+      );
+
+API_READ_OUT <= buf_API_READ_OUT;
+
+end architecture;
\ No newline at end of file
index abf7201fb8e020a36812a622146fee3c59151538..2df06311ec8a79938c6027d70e032b2a667224ff 100644 (file)
@@ -18,7 +18,9 @@ entity trb_net16_api_base is
     USE_VENDOR_CORES  : integer range 0 to 1 := c_YES;
     SECURE_MODE_TO_APL: integer range 0 to 1 := c_YES;
     SECURE_MODE_TO_INT: integer range 0 to 1 := c_YES;
-    APL_WRITE_4_PACKETS:integer range 0 to 1 := c_NO
+    APL_WRITE_4_PACKETS:integer range 0 to 1 := c_NO;
+    BROADCAST_BITMASK : std_logic_vector(7 downto 0) := x"FF"
+                        --which bits must be set to accept a broadcast?
     );
 
   port(
@@ -653,7 +655,7 @@ begin
                 slave_start <= '1';
               end if;
               if INT_SLAVE_PACKET_NUM_IN = "10" then
-                if INT_SLAVE_DATA_IN = APL_MY_ADDRESS_IN or INT_SLAVE_DATA_IN = BROADCAST_ADDRESS then
+                if (INT_SLAVE_DATA_IN = APL_MY_ADDRESS_IN) or (and_all(not(not INT_SLAVE_DATA_IN and (x"FF" & BROADCAST_BITMASK))) = '1') then
                   next_state_to_apl <= sa_MY_ADDR;
                   slave_start <= '1';
                 else
index 2235e0a71e81265528b909a433b0de7f6cc1ef9b..d9a7cd5631c0b687d8118b0174269e4f7f002e31 100644 (file)
@@ -17,7 +17,8 @@ entity trb_net16_hub_base is
     HUB_CTRL_REG_ADDR_WIDTH : integer range 1 to 7 := 4;
     HUB_USED_CHANNELS       : hub_channel_config_t := (c_YES,c_YES,c_YES,c_YES);
     IBUF_SECURE_MODE        : integer range 0 to 1 := c_NO;
-    HUB_ADDRESS             : std_logic_vector(15 downto 0) := x"F003";
+    INIT_ADDRESS            : std_logic_vector(15 downto 0) := x"FFFF";
+    INIT_UNIQUE_ID          : std_logic_vector(95 downto 0) := (others => '0');
   --media interfaces
     MII_NUMBER              : integer range 2 to c_MAX_MII_PER_HUB := 4;
     MII_IBUF_DEPTH          : hub_iobuf_config_t := std_HUB_IBUF_DEPTH;
@@ -163,6 +164,7 @@ architecture trb_net16_hub_base_arch of trb_net16_hub_base is
   signal HUB_CTRL_CHANNEL             : std_logic_vector (2**(c_MUX_WIDTH-1)*16-1 downto 0);
   signal HUB_CTRL_activepoints        : std_logic_vector (2**(c_MUX_WIDTH-1)*32-1 downto 0);
   signal HUB_CTRL_GEN                 : std_logic_vector (31 downto 0);
+  signal HUB_ADDRESS                  : std_logic_vector (15 downto 0);
 
   signal IOBUF_STAT_GEN               :  std_logic_vector ((MII_NUMBER*2**(c_MUX_WIDTH-1) + API_NUMBER + TRG_NUMBER)*32-1 downto 0);
   signal IOBUF_IBUF_BUFFER            :  std_logic_vector ((MII_NUMBER*2**(c_MUX_WIDTH-1) + API_NUMBER + TRG_NUMBER)*32-1 downto 0);
@@ -397,22 +399,29 @@ end component;
     generic (
       REGISTER_WIDTH     : integer range 32 to 32 := 32;
       ADDRESS_WIDTH      : integer range 8 to 16 := 16;
-      ADDRESS_USED_WIDTH : integer range 1 to 16 := HUB_CTRL_REG_ADDR_WIDTH;
+      NUM_STAT_REGS      : integer range 0 to 6 := 3; --log2 of number of status registers
+      NUM_CTRL_REGS      : integer range 0 to 6 := 3; --log2 of number of ctrl registers
       --standard values for output registers
-      RESET_REGISTER_OUT   : std_logic_vector(2**(HUB_CTRL_REG_ADDR_WIDTH-1)*32-1 downto 0);
-      USED_REGISTER_OUT    : std_logic_vector(2**(HUB_CTRL_REG_ADDR_WIDTH-1)-1    downto 0);
-      BITMASK_REGISTER_OUT : std_logic_vector(2**(HUB_CTRL_REG_ADDR_WIDTH-1)*32-1 downto 0);
+      INIT_CTRL_REGS     : std_logic_vector(2**(3)*32-1 downto 0) :=
+              (others => '0');
+      --set to 0 for unused ctrl registers to save resources
+      USED_CTRL_REGS     : std_logic_vector(2**(3)-1 downto 0)   := "11111111";
+      --set to 0 for each unused bit in a register
+      USED_CTRL_BITMASK  : std_logic_vector(2**(3)*32-1 downto 0) :=
+              (others => '1');
       --no data / address out?
-      NO_DAT_PORT        : std_logic := '0'
+      NO_DAT_PORT        : std_logic := '0';
+      INIT_ADDRESS       : std_logic_vector(15 downto 0) := x"FFFF";
+      INIT_UNIQUE_ID     : std_logic_vector(95 downto 0) := (others => '0')
       );
     port(
+    --  Misc
       CLK    : in std_logic;
       RESET  : in std_logic;
       CLK_EN : in std_logic;
-      MY_ADDRESS             : in  std_logic_vector (15 downto 0);
-      -- Port to API
+    -- Port to API
       API_DATA_OUT           : out std_logic_vector (c_DATA_WIDTH-1 downto 0);
-      API_PACKET_NUM_OUT     : out std_logic_vector (c_NUM_WIDTH-1 downto 0);
+      API_PACKET_NUM_OUT     : out std_logic_vector (c_NUM_WIDTH-1  downto 0);
       API_WRITE_OUT          : out std_logic;
       API_FIFO_FULL_IN       : in  std_logic;
       API_SHORT_TRANSFER_OUT : out std_logic;
@@ -422,24 +431,31 @@ end component;
       API_TARGET_ADDRESS_OUT : out std_logic_vector (15 downto 0);
       -- Receiver port
       API_DATA_IN         : in  std_logic_vector (c_DATA_WIDTH-1 downto 0);
-      API_PACKET_NUM_IN   : in  std_logic_vector (c_NUM_WIDTH-1 downto 0);
+      API_PACKET_NUM_IN   : in  std_logic_vector (c_NUM_WIDTH-1  downto 0);
       API_TYP_IN          : in  std_logic_vector (2 downto 0);
       API_DATAREADY_IN    : in  std_logic;
       API_READ_OUT        : out std_logic;
       -- APL Control port
       API_RUN_IN          : in  std_logic;
-      API_MY_ADDRESS_OUT  : out std_logic_vector (15 downto 0);
       API_SEQNR_IN        : in  std_logic_vector (7 downto 0);
-      --Register in / outside
-      REGISTERS_IN        : in  std_logic_vector(REGISTER_WIDTH*2**(ADDRESS_USED_WIDTH-1)-1 downto 0);
-      REGISTERS_OUT       : out std_logic_vector(REGISTER_WIDTH*2**(ADDRESS_USED_WIDTH-1)-1 downto 0);
-      --following ports only used when no internal register is accessed
+
+      MY_ADDRESS_OUT      : out std_logic_vector(15 downto 0);
+
+    --Register in / out
+      REGISTERS_IN        : in  std_logic_vector(REGISTER_WIDTH*2**(NUM_STAT_REGS)-1 downto 0);
+      REGISTERS_OUT       : out std_logic_vector(REGISTER_WIDTH*2**(NUM_CTRL_REGS)-1 downto 0);
+
+    --following ports only used when no internal register is accessed
       DAT_ADDR_OUT        : out std_logic_vector(ADDRESS_WIDTH-1 downto 0);
       DAT_READ_ENABLE_OUT : out std_logic;
       DAT_WRITE_ENABLE_OUT: out std_logic;
       DAT_DATA_OUT        : out std_logic_vector(REGISTER_WIDTH-1 downto 0);
+      --Data input can only be used as reaction on read or write access. write operation should return data
+      --if successful
       DAT_DATA_IN         : in  std_logic_vector(REGISTER_WIDTH-1 downto 0);
-      DAT_DATAREADY_IN    : in std_logic
+      DAT_DATAREADY_IN    : in std_logic;
+      DAT_NO_MORE_DATA_IN : in std_logic
+        --To finish transmission, when reading from a fifo and it got empty
       );
   end component;
   
@@ -1085,24 +1101,25 @@ HUB_MED_CONNECTED(31 downto MII_NUMBER) <= (others => '1');
     end generate;
   end generate;
 
-
   hub_control : trb_net16_regIO
     generic map(
       REGISTER_WIDTH     => 32,
       ADDRESS_WIDTH      => 16,
-      ADDRESS_USED_WIDTH => HUB_CTRL_REG_ADDR_WIDTH,
-      RESET_REGISTER_OUT   => x"FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF" &
-                              x"00000000_00000000_00000000_00000000",
-      USED_REGISTER_OUT    =>  "11111111",
-      BITMASK_REGISTER_OUT => x"FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF" &
-                              x"FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF",
-      NO_DAT_PORT        => '1'
+      NUM_STAT_REGS      => 3,
+      NUM_CTRL_REGS      => 3,
+      INIT_CTRL_REGS     => x"FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF" &
+                            x"00000000_00000000_00000000_00000000",
+      USED_CTRL_REGS     =>  "11111111",
+      USED_CTRL_BITMASK  => x"FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF" &
+                            x"FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF",
+      NO_DAT_PORT        => '1',
+      INIT_ADDRESS       => INIT_ADDRESS,
+      INIT_UNIQUE_ID     => INIT_UNIQUE_ID
       )
     port map(
       CLK    => CLK,
       RESET  =>  RESET,
       CLK_EN => CLK_EN,
-      MY_ADDRESS          => HUB_ADDRESS,
       -- Port to API
       API_DATA_OUT        => HC_DATA_IN,
       API_PACKET_NUM_OUT  => HC_PACKET_NUM_IN,
@@ -1121,8 +1138,8 @@ HUB_MED_CONNECTED(31 downto MII_NUMBER) <= (others => '1');
       API_READ_OUT        => HC_READ_IN,
       -- HC Control port
       API_RUN_IN          => HC_RUN_OUT,
-      API_MY_ADDRESS_OUT  => HC_MY_ADDRESS_IN,
       API_SEQNR_IN        => HC_SEQNR_OUT,
+      MY_ADDRESS_OUT      => HUB_ADDRESS,
       REGISTERS_IN        => HC_STAT_REGS,
       REGISTERS_OUT       => HC_CTRL_REGS,
       DAT_ADDR_OUT        => open,
@@ -1130,9 +1147,11 @@ HUB_MED_CONNECTED(31 downto MII_NUMBER) <= (others => '1');
       DAT_WRITE_ENABLE_OUT=> open,
       DAT_DATA_OUT        => open,
       DAT_DATA_IN         => x"00000000",
-      DAT_DATAREADY_IN    => '0'
+      DAT_DATAREADY_IN    => '0',
+      DAT_NO_MORE_DATA_IN => '0'
       );
 
+
 --8x CTRL, 8x STAT
 
 
index 6dbf20f3503883449db61d20454c63fddd013fe5..dac162f59cdabf7e335d159d99d4cd2889071e17 100644 (file)
@@ -85,18 +85,19 @@ architecture trb_net16_hub_logic_arch of trb_net16_hub_logic is
       );
   end component;
 
-  component trb_net_ram is
+  component trb_net_ram_dp
     generic(
-      depth : integer := 4;
+      depth : integer := 3;
       width : integer := 16
       );
     port(
-      CLK    : in std_logic;
-      wr     : in std_logic;
-      ain    : in std_logic_vector(depth-1 downto 0);
-      din    : in std_logic_vector(width-1 downto 0);
-      aout   : in std_logic_vector(depth-1 downto 0);
-      dout   : out std_logic_vector(width-1 downto 0)
+      CLK   : in std_logic;
+      wr1   : in std_logic;
+      a1    : in std_logic_vector(depth-1 downto 0);
+      dout1 : out std_logic_vector(width-1 downto 0);
+      din1  : in std_logic_vector(width-1 downto 0);
+      a2    : in std_logic_vector(depth-1 downto 0);
+      dout2 : out std_logic_vector(width-1 downto 0)
       );
   end component;
 
@@ -396,18 +397,19 @@ STAT_ERRORBITS <= REPLY_combined_trm_F1 & REPLY_combined_trm_F2;
   current_REPLY_reading_hdr <= next_REPLY_reading_hdr or REPLY_reading_hdr;
 
   gen_saving_hdr : for i in 0 to POINT_NUMBER-1 generate
-    last_HDR_RAM : trb_net_ram
+    last_HDR_RAM : trb_net_ram_dp
       generic map(
         depth => 2,
         width => 16
         )
       port map(
-        CLK    => CLK,
-        wr     => REPLY_reading_hdr(i),
-        ain    => REPLY_PACKET_NUM_IN((i+1)*c_NUM_WIDTH-1 downto i*c_NUM_WIDTH),
-        din    => REPLY_DATA_IN((i+1)*c_DATA_WIDTH-1 downto i*c_DATA_WIDTH),
-        aout   => last_header_addr(1 downto 0),
-        dout   => last_header_data((i+1)*c_DATA_WIDTH-1 downto i*c_DATA_WIDTH)
+        CLK     => CLK,
+        wr1     => REPLY_reading_hdr(i),
+        a1      => REPLY_PACKET_NUM_IN((i+1)*c_NUM_WIDTH-1 downto i*c_NUM_WIDTH),
+        din1    => REPLY_DATA_IN((i+1)*c_DATA_WIDTH-1 downto i*c_DATA_WIDTH),
+        dout1   => open,
+        a2      => last_header_addr(1 downto 0),
+        dout2   => last_header_data((i+1)*c_DATA_WIDTH-1 downto i*c_DATA_WIDTH)
         );
   end generate;
   last_header_addr <= packet_counter;
index 9a6db0f11304172abdee3d6be2534dc23341c0e0..f2645155eaab00e3bf64bc5d248f6c93b2dc61cf 100644 (file)
@@ -120,8 +120,6 @@ architecture trb_net16_ibuf_arch of trb_net16_ibuf is
   signal tmp_INT_DATA_OUT: std_logic_vector(c_DATA_WIDTH-1 downto 0);
   signal tmp_INT_PACKET_NUM_OUT: std_logic_vector(c_NUM_WIDTH-1 downto 0);
 
-  signal reading_header : std_logic;
-  
   type ERROR_STATE is (IDLE, GOT_OVERFLOW_ERROR, GOT_UNDEFINED_ERROR);
   signal current_error_state, next_error_state : ERROR_STATE;
   signal next_rec_buffer_size_out, current_rec_buffer_size_out: std_logic_vector(3 downto 0);
@@ -313,12 +311,18 @@ begin
 
 
       fifo_read <= not fifo_empty and not (fifo_read_before and not 
-                      ((INT_INIT_READ_IN and not current_fifo_packet_type(3)) 
-                      or (INT_REPLY_READ_IN and current_fifo_packet_type(3)) or throw_away));
+                         ((sbuf_init_free and not current_fifo_packet_type(3))
+                      or (sbuf_reply_free and current_fifo_packet_type(3))
+                      or throw_away));
 
       if (fifo_read_before = '1' and (current_fifo_packet_type(2 downto 0) /= TYPE_EOB)) then
-        tmp_INT_INIT_DATAREADY_OUT <=  sbuf_init_free and not current_fifo_packet_type(3);
-        tmp_INT_REPLY_DATAREADY_OUT <=  sbuf_reply_free and current_fifo_packet_type(3);
+        if SECURE_MODE = 1 then
+          tmp_INT_INIT_DATAREADY_OUT <=  (sbuf_init_free) and not current_fifo_packet_type(3);
+          tmp_INT_REPLY_DATAREADY_OUT <=  (sbuf_reply_free ) and current_fifo_packet_type(3);
+        else
+          tmp_INT_INIT_DATAREADY_OUT <=  not current_fifo_packet_type(3);
+          tmp_INT_REPLY_DATAREADY_OUT <= current_fifo_packet_type(3);
+        end if;
       end if;
 
       if last_fifo_read = '1' then
index 6abf3102d9728cc2aede8d8a53c2581652ebad82..338f0032f5209e985029284e9410e37091c8497a 100644 (file)
@@ -18,25 +18,26 @@ entity trb_net16_regIO is
   generic (
     REGISTER_WIDTH     : integer range 32 to 32 := 32;
     ADDRESS_WIDTH      : integer range 8 to 16 := 16;
-    ADDRESS_USED_WIDTH : integer range 1 to 5 := 4;
+    NUM_STAT_REGS      : integer range 0 to 6 := 3; --log2 of number of status registers
+    NUM_CTRL_REGS      : integer range 0 to 6 := 3; --log2 of number of ctrl registers
     --standard values for output registers
-    RESET_REGISTER_OUT : std_logic_vector(2**(4-1)*32-1 downto 0) :=
-             x"00000000_00000000_00000000_00000000_00000000_00000000_00000000_00000000";
+    INIT_CTRL_REGS     : std_logic_vector(2**(3)*32-1 downto 0) :=
+            (others => '0');
     --set to 0 for unused ctrl registers to save resources
-    USED_REGISTER_OUT  : std_logic_vector(2**(4-1)-1 downto 0)   := "11111111";
+    USED_CTRL_REGS     : std_logic_vector(2**(3)-1 downto 0)   := "11111111";
     --set to 0 for each unused bit in a register
-    BITMASK_REGISTER_OUT : std_logic_vector(2**(4-1)*32-1 downto 0) :=
-             x"FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF_FFFFFFFF";
+    USED_CTRL_BITMASK  : std_logic_vector(2**(3)*32-1 downto 0) :=
+            (others => '1');
     --no data / address out?
-    NO_DAT_PORT        : std_logic := '0'
+    NO_DAT_PORT        : std_logic := '0';
+    INIT_ADDRESS       : std_logic_vector(15 downto 0) := x"FFFF";
+    INIT_UNIQUE_ID     : std_logic_vector(95 downto 0) := (others => '0')
     );
   port(
   --  Misc
     CLK    : in std_logic;
     RESET  : in std_logic;
     CLK_EN : in std_logic;
-
-    MY_ADDRESS             : in  std_logic_vector (15 downto 0);
   -- Port to API
     API_DATA_OUT           : out std_logic_vector (c_DATA_WIDTH-1 downto 0);
     API_PACKET_NUM_OUT     : out std_logic_vector (c_NUM_WIDTH-1  downto 0);
@@ -55,23 +56,25 @@ entity trb_net16_regIO is
     API_READ_OUT        : out std_logic;
     -- APL Control port
     API_RUN_IN          : in  std_logic;
-    API_MY_ADDRESS_OUT  : out std_logic_vector (15 downto 0);
     API_SEQNR_IN        : in  std_logic_vector (7 downto 0);
 
-  --Register in / outside
-    REGISTERS_IN        : in  std_logic_vector(REGISTER_WIDTH*2**(ADDRESS_USED_WIDTH-1)-1 downto 0);
-    REGISTERS_OUT       : out std_logic_vector(REGISTER_WIDTH*2**(ADDRESS_USED_WIDTH-1)-1 downto 0);
+    MY_ADDRESS_OUT      : out std_logic_vector(15 downto 0);
+
+  --Register in / out
+    REGISTERS_IN        : in  std_logic_vector(REGISTER_WIDTH*2**(NUM_STAT_REGS)-1 downto 0);
+    REGISTERS_OUT       : out std_logic_vector(REGISTER_WIDTH*2**(NUM_CTRL_REGS)-1 downto 0);
 
   --following ports only used when no internal register is accessed
     DAT_ADDR_OUT        : out std_logic_vector(ADDRESS_WIDTH-1 downto 0);
     DAT_READ_ENABLE_OUT : out std_logic;
     DAT_WRITE_ENABLE_OUT: out std_logic;
-    --Data output is only used when writing
     DAT_DATA_OUT        : out std_logic_vector(REGISTER_WIDTH-1 downto 0);
     --Data input can only be used as reaction on read or write access. write operation should return data
     --if successful
     DAT_DATA_IN         : in  std_logic_vector(REGISTER_WIDTH-1 downto 0);
-    DAT_DATAREADY_IN    : in std_logic
+    DAT_DATAREADY_IN    : in std_logic;
+    DAT_NO_MORE_DATA_IN : in std_logic
+      --To finish transmission, when reading from a fifo and it got empty
     );
 end entity;
 
@@ -79,7 +82,7 @@ architecture trb_net16_regIO_arch of trb_net16_regIO is
 
   component trb_net_pattern_gen is
     generic (
-      WIDTH : integer := ADDRESS_USED_WIDTH-1
+      WIDTH : integer := NUM_CTRL_REGS
       );
     port(
       INPUT_IN  : in  STD_LOGIC_VECTOR (WIDTH-1 downto 0);
@@ -87,9 +90,33 @@ architecture trb_net16_regIO_arch of trb_net16_regIO is
       );
   end component;
 
-  type fsm_state_t is (IDLE, HEADER_RECV, REG_READ, REG_WRITE, WAIT_FOR_INIT_TRM,
-                       SEND_REPLY_DATA_finish, SEND_REPLY_SHORT_TRANSFER, SEND_REPLY_DATA,
-                       DAT_INT, DAT_WAIT);
+  component trb_net16_addresses is
+    generic(
+      INIT_ADDRESS   : std_logic_vector(15 downto 0) := x"FFFF";
+      INIT_UNIQUE_ID : std_logic_vector(95 downto 0) := x"1000_2000_3654_4876_5bcd_6ef1"
+      );
+    port(
+      CLK    : in std_logic;
+      RESET  : in std_logic;
+      CLK_EN : in std_logic;
+      API_DATA_IN       : in  std_logic_vector(15 downto 0);
+      API_DATAREADY_IN  : in  std_logic;
+      API_READ_OUT      : out std_logic;
+      RAM_DATA_IN       : in  std_logic_vector(15 downto 0);
+      RAM_DATA_OUT      : out std_logic_vector(15 downto 0);
+      RAM_ADDR_IN       : in  std_logic_vector(2 downto 0);
+      RAM_WR_IN         : in  std_logic;
+      API_DATA_OUT      : out std_logic_vector(15 downto 0);
+      API_PACKET_NUM_OUT: out std_logic_vector(1 downto 0);
+      API_DATAREADY_OUT : out std_logic;
+      API_READ_IN       : in  std_logic;
+      ADDRESS_REJECTED  : out std_logic; 
+      ADDRESS_OUT       : out std_logic_vector(15 downto 0)
+      );
+  end component;
+
+  type fsm_state_t is (IDLE, HEADER_RECV, REG_READ, REG_WRITE, ONE_READ, ONE_WRITE, SEND_REPLY_SHORT_TRANSFER,
+                       MEM_READ, MEM_WRITE, DAT_START_READ, DAT_READ, SEND_REPLY_DATA_finish, ADDRESS_ACK, ADDRESS_RECV);
   signal current_state, next_state             : fsm_state_t;
   signal HDR_F1, HDR_F2, HDR_F3                : std_logic_vector(15 downto 0);
   signal next_HDR_F1, next_HDR_F2, next_HDR_F3 : std_logic_vector(15 downto 0);
@@ -105,35 +132,79 @@ architecture trb_net16_regIO_arch of trb_net16_regIO is
   signal buf_API_SHORT_TRANSFER_OUT, next_API_SHORT_TRANSFER_OUT : std_logic;
   signal buf_API_WRITE_OUT, next_API_WRITE_OUT        : std_logic;
 
-  signal buf_DAT_DATA_OUT, next_DAT_DATA_OUT                 : std_logic_vector(REGISTER_WIDTH-1 downto 0);
+  signal buf_DAT_DATA_OUT                 : std_logic_vector(REGISTER_WIDTH-1 downto 0);
   signal buf_DAT_READ_ENABLE_OUT, next_DAT_READ_ENABLE_OUT   : std_logic;
   signal buf_DAT_WRITE_ENABLE_OUT, next_DAT_WRITE_ENABLE_OUT : std_logic;
-  signal buf_DAT_ADDR_OUT, next_DAT_ADDR_OUT                 : std_logic_vector(ADDRESS_WIDTH-1 downto 0);
+  signal buf_DAT_ADDR_OUT                 : std_logic_vector(ADDRESS_WIDTH-1 downto 0);
 
-  signal buf_REGISTERS_OUT                     : std_logic_vector(REGISTER_WIDTH*2**(ADDRESS_USED_WIDTH-1)-1 downto 0);
-  signal REGISTERS_OUT_write_enable            : std_logic_vector(2**(ADDRESS_USED_WIDTH-1)-1 downto 0);
-  signal reg_enable_pattern                    : std_logic_vector(2**(ADDRESS_USED_WIDTH-1)-1 downto 0);
+  signal buf_REGISTERS_OUT                     : std_logic_vector(REGISTER_WIDTH*2**(NUM_CTRL_REGS)-1 downto 0);
+  signal REGISTERS_OUT_write_enable            : std_logic_vector(2**(NUM_CTRL_REGS)-1 downto 0);
+  signal next_REGISTERS_OUT_write_enable       : std_logic_vector(2**(NUM_CTRL_REGS)-1 downto 0);
+  signal reg_enable_pattern                    : std_logic_vector(2**(NUM_CTRL_REGS)-1 downto 0);
 
 
   signal state_bits                             : std_logic_vector(2 downto 0);
 
+  signal ADR_DATAREADY_IN : std_logic;
+  signal ADR_READ_OUT : std_logic;
+  signal ADR_DATA_OUT : std_logic_vector(15 downto 0);
+  signal ADR_READ_IN  : std_logic;
+  signal ADR_DATAREADY_OUT : std_logic;
+  signal RAM_DATA_IN, RAM_DATA_OUT : std_logic_vector(15 downto 0);
+  signal ADR_PACKET_NUM_OUT : std_logic_vector(1 downto 0);
+  signal RAM_ADDR_IN : std_logic_vector(2 downto 0);
+  signal RAM_WR_IN : std_logic;
+  signal ADR_REJECTED : std_logic;
+  signal next_API_ERROR_PATTERN_OUT : std_logic_vector(31 downto 0);
+  signal buf_API_ERROR_PATTERN_OUT  : std_logic_vector(31 downto 0);
+
 begin
 
   pattern_gen_inst : trb_net_pattern_gen 
     port map(
-      INPUT_IN   => address(ADDRESS_USED_WIDTH-2 downto 0), 
+      INPUT_IN   => address(NUM_CTRL_REGS-1 downto 0),
       RESULT_OUT => reg_enable_pattern
       );
 
+  addresses : trb_net16_addresses
+    generic map(
+      INIT_ADDRESS   => INIT_ADDRESS,
+      INIT_UNIQUE_ID => INIT_UNIQUE_ID
+      )
+    port map(
+      CLK    => CLK,
+      RESET  => RESET,
+      CLK_EN => CLK_EN,
+      API_DATA_IN       => API_DATA_IN,
+      API_DATAREADY_IN  => ADR_DATAREADY_IN,
+      API_READ_OUT      => ADR_READ_OUT,
+      API_DATA_OUT      => ADR_DATA_OUT,
+      API_DATAREADY_OUT => ADR_DATAREADY_OUT,
+      API_PACKET_NUM_OUT=> ADR_PACKET_NUM_OUT,
+      API_READ_IN       => ADR_READ_IN,
+      RAM_DATA_IN       => RAM_DATA_IN,
+      RAM_DATA_OUT      => RAM_DATA_OUT,
+      RAM_ADDR_IN       => RAM_ADDR_IN,
+      RAM_WR_IN         => RAM_WR_IN,
+      ADDRESS_REJECTED  => ADR_REJECTED,
+      ADDRESS_OUT       => MY_ADDRESS_OUT
+      );
+
+  RAM_DATA_IN <= (others => '0');
+  RAM_WR_IN <= '0';
+
+  buf_DAT_ADDR_OUT <= address;
+  buf_DAT_DATA_OUT <= saved_Reg_high & saved_Reg_low;
 
   fsm : process(current_state,
                 API_DATA_IN, API_PACKET_NUM_IN, API_TYP_IN, API_DATAREADY_IN, API_FIFO_FULL_IN, API_RUN_IN,
                 HDR_F1, HDR_F2, HDR_F3, address, saved_Reg_high, saved_Reg_low, saved_operation,
                 buf_API_SEND_OUT, buf_API_PACKET_NUM_OUT, buf_API_DATA_OUT, buf_API_SHORT_TRANSFER_OUT,
-                REGISTERS_IN, buf_REGISTERS_OUT, reg_enable_pattern,
-                buf_DAT_DATA_OUT, buf_DAT_ADDR_OUT, DAT_DATAREADY_IN, DAT_DATA_IN
+                REGISTERS_IN, buf_REGISTERS_OUT, reg_enable_pattern, DAT_NO_MORE_DATA_IN,
+                buf_DAT_DATA_OUT, buf_DAT_ADDR_OUT, DAT_DATAREADY_IN, DAT_DATA_IN, ADR_REJECTED,
+                ADR_READ_OUT, ADR_DATAREADY_OUT, ADR_DATA_OUT, ADR_PACKET_NUM_OUT
                 )
-    variable regnum : integer range 0 to 2**(ADDRESS_USED_WIDTH-1)-1;
+    variable regnum : integer range 0 to 2**(NUM_STAT_REGS)-1;
     begin
       next_state  <= current_state;
       next_HDR_F1 <= HDR_F1;
@@ -142,20 +213,22 @@ begin
       next_address  <= address;
       next_Reg_high <= saved_Reg_high;
       next_Reg_low  <= saved_Reg_low;
-      next_API_READ_OUT <= '1';
+--      next_API_READ_OUT <= '1';
+      ADR_DATAREADY_IN <= '0';
+      ADR_READ_IN <= '0';
+      buf_API_READ_OUT <= '1';
       next_API_SEND_OUT <= buf_API_SEND_OUT;
       next_API_WRITE_OUT <= '0';
       next_API_PACKET_NUM_OUT <= buf_API_PACKET_NUM_OUT;
       next_API_DATA_OUT <= buf_API_DATA_OUT;
       next_API_SHORT_TRANSFER_OUT <= buf_API_SHORT_TRANSFER_OUT;
       next_operation <= saved_operation;
-      REGISTERS_OUT_write_enable <= (others => '0');
-      next_DAT_DATA_OUT         <= buf_DAT_DATA_OUT;
+      next_REGISTERS_OUT_write_enable <= (others => '0');
       next_DAT_READ_ENABLE_OUT  <= '0';
       next_DAT_WRITE_ENABLE_OUT <= '0';
-      next_DAT_ADDR_OUT         <= buf_DAT_ADDR_OUT;
+      buf_API_ERROR_PATTERN_OUT(0) <= '1';
 
-      regnum := conv_integer(address(ADDRESS_USED_WIDTH-2 downto 0));
+      regnum := conv_integer(address(NUM_STAT_REGS-1 downto 0));
 
       case current_state is
         when IDLE =>
@@ -165,8 +238,7 @@ begin
             next_state <= HEADER_RECV;
           end if;
 
-      --read and save HDR, then decide what to do by dtype
-        when HEADER_RECV =>
+        when HEADER_RECV =>        --read and save HDR
           if API_DATAREADY_IN = '1' then
             if API_PACKET_NUM_IN = "01" then
               next_HDR_F1 <= API_DATA_IN;
@@ -177,57 +249,108 @@ begin
             if API_PACKET_NUM_IN = "11" then
               next_HDR_F3 <= API_DATA_IN;
               case API_DATA_IN(3 downto 0) is
-                when "1000" => next_state <= REG_READ;
-                when "1001" => next_state <= REG_WRITE;
+                when "1000" => next_state <= ONE_READ;
+                when "1001" => next_state <= ONE_WRITE;
+                when "1010" => next_state <= MEM_READ;
+                when "1011" => next_state <= MEM_WRITE;
+                when "1111" => next_state <= ADDRESS_RECV;
                 when others => next_state <= SEND_REPLY_SHORT_TRANSFER;
               end case;
               next_operation <= API_DATA_IN(3 downto 0);
             end if;
           end if;
 
-      --writing register operation
-        when REG_WRITE =>
-          if API_TYP_IN = TYPE_DAT then
-            case API_PACKET_NUM_IN is
-              when "01" =>
-                next_address <= API_DATA_IN;
-              when "10" =>
-                next_Reg_high <= API_DATA_IN;
-              when "11" =>
-                next_Reg_low <= API_DATA_IN;
-                REGISTERS_OUT_write_enable <= reg_enable_pattern;
-                next_state     <= WAIT_FOR_INIT_TRM;
-                if or_all(address(ADDRESS_WIDTH-1 downto ADDRESS_USED_WIDTH)) = '1' then
-                  if NO_DAT_PORT = '0' then
-                    next_state <= DAT_INT;
-                  else
-                    next_state <= SEND_REPLY_SHORT_TRANSFER;
-                  end if;
-                end if;
-              when others =>
-                null;
-            end case;
+        when ADDRESS_RECV =>
+          ADR_DATAREADY_IN <= API_DATAREADY_IN;
+          buf_API_READ_OUT <= ADR_READ_OUT;
+          ADR_READ_IN <= '0';
+          if ADR_REJECTED = '1' then
+            next_state <= SEND_REPLY_SHORT_TRANSFER;
+          end if;
+          if ADR_DATAREADY_OUT = '1' then
+            next_state <= ADDRESS_ACK;
           end if;
 
-        when REG_READ =>
+        when ADDRESS_ACK =>
+          ADR_READ_IN <= not API_FIFO_FULL_IN;
+          next_API_SEND_OUT <= '1';
+          next_API_WRITE_OUT <= ADR_DATAREADY_OUT;
+          next_API_DATA_OUT <= ADR_DATA_OUT;
+          next_API_PACKET_NUM_OUT <= ADR_PACKET_NUM_OUT;
+          if ADR_PACKET_NUM_OUT = "11" and not API_FIFO_FULL_IN = '1' then
+            next_state <= SEND_REPLY_DATA_finish;
+          end if;
+
+
+        when ONE_READ =>   --wait for register address
           if API_TYP_IN = TYPE_DAT and API_PACKET_NUM_IN = "01" and API_DATAREADY_IN = '1' then
             next_address <= API_DATA_IN;
-            next_state <= WAIT_FOR_INIT_TRM;
-            if or_all(API_DATA_IN(ADDRESS_WIDTH-1 downto ADDRESS_USED_WIDTH)) = '1' then
+            if or_all(API_DATA_IN(ADDRESS_WIDTH-1 downto 8)) = '1' then  --data port address
               if NO_DAT_PORT = '0' then
-                next_state <= DAT_INT;
+                next_DAT_READ_ENABLE_OUT <= '1';
+                next_state <= DAT_READ;
               else
                 next_state <= SEND_REPLY_SHORT_TRANSFER;
               end if;
+            else                              --register address
+              next_state <= REG_READ;
             end if;
           end if;
 
-        when WAIT_FOR_INIT_TRM =>
-          if API_TYP_IN = TYPE_TRM and API_PACKET_NUM_IN = "11" then
-            next_state <= SEND_REPLY_DATA;
+        when ONE_WRITE =>  --wait for register address
+          if API_TYP_IN = TYPE_DAT and API_PACKET_NUM_IN = "01" and API_DATAREADY_IN = '1' then
+            next_address <= API_DATA_IN;
+            if not (API_DATA_IN(15 downto 8)) = x"00" then  --data port address
+              if NO_DAT_PORT = '0' then
+                next_state <= REG_WRITE;
+              else
+                next_state <= SEND_REPLY_SHORT_TRANSFER;
+              end if;
+            elsif API_DATA_IN(7) = '1' then   --register address
+              if API_DATA_IN(6) = '1' then
+                if API_DATA_IN(5 downto NUM_CTRL_REGS) = 0 then
+                  next_state <= REG_WRITE;    --ctrl register
+                else
+                  next_state <= SEND_REPLY_SHORT_TRANSFER;
+                end if;                       --unused address - not valid
+              else
+                if API_DATA_IN(5 downto NUM_STAT_REGS) = 0 then
+                  next_state <= REG_READ;     --stat register - not writing
+                else
+                  next_state <= SEND_REPLY_SHORT_TRANSFER;
+                end if;                       --unused address - not valid
+              end if;
+            else                              --status ram address - not valid
+              next_state <= SEND_REPLY_SHORT_TRANSFER;
+            end if;
           end if;
 
-        when SEND_REPLY_DATA =>
+        when SEND_REPLY_DATA_finish =>
+          next_API_SEND_OUT <= '0';
+          next_state <= IDLE;
+
+        when SEND_REPLY_SHORT_TRANSFER =>
+          next_API_SHORT_TRANSFER_OUT <= '1';
+          next_API_SEND_OUT <= '1';
+          next_state <= SEND_REPLY_DATA_finish;
+
+        when REG_WRITE =>
+          case API_PACKET_NUM_IN is
+            when "10" =>
+              next_Reg_high <= API_DATA_IN;
+            when "11" =>
+              next_Reg_low <= API_DATA_IN;
+              if or_all(address(15 downto 8)) = '0' then
+                next_REGISTERS_OUT_write_enable <= reg_enable_pattern;
+                next_state   <= REG_READ;
+              else
+                next_DAT_WRITE_ENABLE_OUT <= '1';
+                next_state   <= DAT_START_READ;
+              end if;
+            when others => null;
+          end case;
+
+        when REG_READ =>
           next_API_SEND_OUT <= '1';
           if API_FIFO_FULL_IN = '1' then
             next_API_WRITE_OUT <= '0';
@@ -238,14 +361,14 @@ begin
               next_API_DATA_OUT <= address;
             elsif buf_API_PACKET_NUM_OUT = "01" then
               next_API_PACKET_NUM_OUT <= "10";
-              if address(ADDRESS_USED_WIDTH-1) = '0' then
+              if address(6) = '0' then
                 next_API_DATA_OUT <= REGISTERS_IN(regnum*REGISTER_WIDTH+31 downto regnum*REGISTER_WIDTH+16);
               else
                 next_API_DATA_OUT <= buf_REGISTERS_OUT(regnum*REGISTER_WIDTH+31 downto regnum*REGISTER_WIDTH+16);
               end if;
             elsif buf_API_PACKET_NUM_OUT = "10" then
               next_API_PACKET_NUM_OUT <= "11";
-              if address(ADDRESS_USED_WIDTH-1) = '0' then
+              if address(6) = '0' then
                 next_API_DATA_OUT <= REGISTERS_IN(regnum*REGISTER_WIDTH+15 downto regnum*REGISTER_WIDTH);
               else
                 next_API_DATA_OUT <= buf_REGISTERS_OUT(regnum*REGISTER_WIDTH+15 downto regnum*REGISTER_WIDTH);
@@ -253,30 +376,19 @@ begin
               next_state <= SEND_REPLY_DATA_finish;
             end if;
           end if;
-        when SEND_REPLY_DATA_finish =>
-          next_API_SEND_OUT <= '0';
-          next_state <= IDLE;
 
-        when SEND_REPLY_SHORT_TRANSFER =>
-          if API_TYP_IN = TYPE_TRM and API_PACKET_NUM_IN = "11" then
-            next_API_SHORT_TRANSFER_OUT <= '1';
-            next_API_SEND_OUT <= '1';
-            next_state <= SEND_REPLY_DATA_finish;
-          end if;
 
-        when DAT_INT =>
-          if API_TYP_IN = TYPE_TRM and API_PACKET_NUM_IN = "11" then
-            next_DAT_DATA_OUT <= saved_Reg_high & saved_Reg_low;
-            next_DAT_ADDR_OUT <= address;
-            if saved_operation = "1000" then
-              next_DAT_READ_ENABLE_OUT <= '1';
-            elsif saved_operation = "1001" then
-              next_DAT_WRITE_ENABLE_OUT <= '1';
-            end if;
-            next_state <= DAT_WAIT;
-          end if;
+        when MEM_READ =>
+          next_state <= SEND_REPLY_SHORT_TRANSFER;
 
-        when DAT_WAIT =>
+        when MEM_WRITE =>
+          next_state <= SEND_REPLY_SHORT_TRANSFER;
+
+        when DAT_START_READ => 
+          next_DAT_READ_ENABLE_OUT <= '1';
+          next_state <= DAT_READ;
+
+        when DAT_READ =>
           if DAT_DATAREADY_IN = '1' then
             next_API_PACKET_NUM_OUT <= "01";
             next_API_DATA_OUT <= address;
@@ -293,6 +405,10 @@ begin
             next_API_WRITE_OUT <= '1';
             next_state <= SEND_REPLY_DATA_finish;
           end if;
+
+
+
+
         when others =>
           next_state <= IDLE;
       end case;
@@ -304,30 +420,19 @@ begin
       if rising_edge(CLK) then
         if RESET = '1' then
           current_state <= IDLE;
-          HDR_F1 <= (others => '0');
-          HDR_F2 <= (others => '0');
-          HDR_F3 <= (others => '0');
-          buf_API_READ_OUT <= '0';
-          buf_API_READ_OUT <= '0';
           buf_API_SEND_OUT <= '0';
           buf_API_WRITE_OUT <= '0';
           buf_API_PACKET_NUM_OUT <= "11";
-          buf_API_DATA_OUT <= (others => '0');
-          buf_API_SHORT_TRANSFER_OUT <= '0';
-          address <= (others => '0');
-          saved_Reg_high <= (others => '0');
-          saved_Reg_low  <= (others => '0');
-          saved_operation <= (others => '0');
-          buf_DAT_DATA_OUT         <= (others => '0');
           buf_DAT_READ_ENABLE_OUT  <= '0';
           buf_DAT_WRITE_ENABLE_OUT <= '0';
-          buf_DAT_ADDR_OUT         <= (others => '0');
+          buf_API_DATA_OUT <= (others => '0');
+          buf_API_PACKET_NUM_OUT <= (others => '0');
+          saved_operation <= "0000";
         else
           current_state <= next_state;
           HDR_F1 <= next_HDR_F1;
           HDR_F2 <= next_HDR_F2;
           HDR_F3 <= next_HDR_F3;
-          buf_API_READ_OUT <= next_API_READ_OUT;
           buf_API_SEND_OUT <= next_API_SEND_OUT;
           buf_API_WRITE_OUT <= next_API_WRITE_OUT;
           buf_API_PACKET_NUM_OUT <= next_API_PACKET_NUM_OUT;
@@ -337,45 +442,45 @@ begin
           saved_Reg_high <= next_Reg_high;
           saved_Reg_low  <= next_Reg_low;
           saved_operation <= next_operation;
-          buf_DAT_DATA_OUT         <= next_DAT_DATA_OUT;
           buf_DAT_READ_ENABLE_OUT  <= next_DAT_READ_ENABLE_OUT;
           buf_DAT_WRITE_ENABLE_OUT <= next_DAT_WRITE_ENABLE_OUT;
-          buf_DAT_ADDR_OUT         <= next_DAT_ADDR_OUT;
+          REGISTERS_OUT_write_enable <= next_REGISTERS_OUT_write_enable;
         end if;
       end if;
     end process;
 
-  gen_regout : for i in 0 to 2**(ADDRESS_USED_WIDTH-1)-1 generate
+  gen_regout : for i in 0 to 2**(NUM_CTRL_REGS)-1 generate
     gen_regoutff1 : for j in i*REGISTER_WIDTH to (i+1)*REGISTER_WIDTH-1 generate
-      gen_regoutff : if USED_REGISTER_OUT(i) = '1' and BITMASK_REGISTER_OUT(j) = '1' generate
+      gen_regoutff : if USED_CTRL_REGS(i) = '1' and USED_CTRL_BITMASK(j) = '1' generate
         process(CLK)
           variable tmp : std_logic_vector(REGISTER_WIDTH-1 downto 0);
           begin
             if rising_edge(CLK) then
               if RESET = '1' then
-                buf_REGISTERS_OUT(j)  <= RESET_REGISTER_OUT(j);
+                buf_REGISTERS_OUT(j)  <= INIT_CTRL_REGS(j);
               elsif REGISTERS_OUT_write_enable(i) = '1' then
-                tmp := saved_Reg_high & API_DATA_IN;
+                tmp := saved_Reg_high & saved_Reg_low;
                 buf_REGISTERS_OUT(j) <= tmp(j-i*REGISTER_WIDTH);
               end if;
             end if;
           end process;
       end generate;
-      gen_regoutnull : if USED_REGISTER_OUT(i) = '0' or BITMASK_REGISTER_OUT(j) = '0' generate
-        buf_REGISTERS_OUT(j) <= RESET_REGISTER_OUT(j);
+      gen_regoutnull : if USED_CTRL_REGS(i) = '0' or USED_CTRL_BITMASK(j) = '0' generate
+        buf_REGISTERS_OUT(j) <= INIT_CTRL_REGS(j);
       end generate;
     end generate;
   end generate;
 
+  buf_API_ERROR_PATTERN_OUT(31 downto 1) <= (others => '0');
+
   API_READ_OUT       <= buf_API_READ_OUT;
   API_SEND_OUT       <= buf_API_SEND_OUT;
   API_WRITE_OUT      <= buf_API_WRITE_OUT;
   API_PACKET_NUM_OUT <= buf_API_PACKET_NUM_OUT;
   API_DATA_OUT       <= buf_API_DATA_OUT;
   API_SHORT_TRANSFER_OUT <= buf_API_SHORT_TRANSFER_OUT;
-  API_DTYPE_OUT          <= (others => '0');
-  API_MY_ADDRESS_OUT     <= MY_ADDRESS;
-  API_ERROR_PATTERN_OUT  <= (others => '0');
+  API_DTYPE_OUT          <= saved_operation;
+  API_ERROR_PATTERN_OUT  <= buf_API_ERROR_PATTERN_OUT;
   API_TARGET_ADDRESS_OUT <= (others => '0');
   DAT_DATA_OUT           <= buf_DAT_DATA_OUT;
   DAT_READ_ENABLE_OUT    <= buf_DAT_READ_ENABLE_OUT;
@@ -385,8 +490,6 @@ begin
 
 
 
-
-
   process(current_state)
     begin
       case current_state is
@@ -394,9 +497,9 @@ begin
         when HEADER_RECV  => state_bits <= "001";
         when REG_READ     => state_bits <= "010";
         when REG_WRITE    => state_bits <= "011";
-        when SEND_REPLY_DATA_finish   => state_bits <= "100";
+        when SEND_REPLY_DATA_finish    => state_bits <= "100";
         when SEND_REPLY_SHORT_TRANSFER => state_bits <= "101";
-        when SEND_REPLY_DATA      => state_bits <= "110";
+        when ONE_READ     => state_bits <= "110";
         when others       => state_bits <= "111";
       end case;
     end process;
index 5ee0c662de765701a6c8e639d6f3fa9999142ea3..cbc2abd454ab8c430ec91bf598ca6d7b10a5813c 100644 (file)
@@ -8,16 +8,15 @@ use work.trb_net_std.all;
 
 entity trb_net_ram is
   generic(
-    depth : integer := 3;
-    width : integer := 16
+    depth : integer := 5;
+    width : integer := 32
     );
   port(
-    CLK    : in std_logic;
-    wr     : in std_logic;
-    ain    : in std_logic_vector(depth-1 downto 0);
-    din    : in std_logic_vector(width-1 downto 0);
-    aout   : in std_logic_vector(depth-1 downto 0);
-    dout   : out std_logic_vector(width-1 downto 0)
+    CLK  : in std_logic;
+    wr   : in std_logic;
+    a    : in std_logic_vector(depth-1 downto 0);
+    dout : out std_logic_vector(width-1 downto 0);
+    din  : in std_logic_vector(width-1 downto 0)
     );
 end entity;
 
@@ -30,9 +29,9 @@ begin
     begin
       if rising_edge(CLK) then
         if wr = '1' then
-          ram(conv_integer((ain))) <= din;
+          ram(conv_integer(a)) <= din;
         end if;
-        dout <= ram(conv_integer((aout)));
+        dout <= ram(conv_integer(a));
       end if;
     end process;
 end architecture;
diff --git a/trb_net_ram_16x8_dp.vhd b/trb_net_ram_16x8_dp.vhd
new file mode 100644 (file)
index 0000000..6cc106d
--- /dev/null
@@ -0,0 +1,48 @@
+LIBRARY IEEE;
+USE IEEE.std_logic_1164.ALL;
+USE IEEE.std_logic_ARITH.ALL;
+USE IEEE.std_logic_UNSIGNED.ALL;
+
+library work;
+use work.trb_net_std.all;
+
+entity trb_net_ram_16x8_dp is
+  generic(
+    INIT0 : std_logic_vector(15 downto 0) := x"0000";
+    INIT1 : std_logic_vector(15 downto 0) := x"0000";
+    INIT2 : std_logic_vector(15 downto 0) := x"0000";
+    INIT3 : std_logic_vector(15 downto 0) := x"0000";
+    INIT4 : std_logic_vector(15 downto 0) := x"0000";
+    INIT5 : std_logic_vector(15 downto 0) := x"0000";
+    INIT6 : std_logic_vector(15 downto 0) := x"0000";
+    INIT7 : std_logic_vector(15 downto 0) := x"0000"
+    );
+  port(
+    CLK   : in  std_logic;
+    wr1   : in  std_logic;
+    a1    : in  std_logic_vector(2 downto 0);
+    dout1 : out std_logic_vector(15 downto 0);
+    din1  : in  std_logic_vector(15 downto 0);
+    a2    : in  std_logic_vector(2 downto 0);
+    dout2 : out std_logic_vector(15 downto 0)
+    );
+end entity;
+
+architecture trb_net_ram_16x8_dp_arch of trb_net_ram_16x8_dp is
+  type ram_t is array(0 to 7) of std_logic_vector(15 downto 0);
+  SIGNAL ram : ram_t := (INIT0, INIT1, INIT2, INIT3, INIT4, INIT5, INIT6, INIT7);
+begin
+
+
+  process(CLK)
+    begin
+      if rising_edge(CLK) then
+        if wr1 = '1' then
+          ram((conv_integer(a1))) <= din1;
+        end if;
+        dout1 <= ram(conv_integer(a1));
+        dout2 <= ram(conv_integer(a2));
+      end if;
+    end process;
+
+end architecture;
\ No newline at end of file
diff --git a/trb_net_ram_dp.vhd b/trb_net_ram_dp.vhd
new file mode 100644 (file)
index 0000000..c01dce1
--- /dev/null
@@ -0,0 +1,42 @@
+LIBRARY IEEE;
+USE IEEE.std_logic_1164.ALL;
+USE IEEE.std_logic_ARITH.ALL;
+USE IEEE.std_logic_UNSIGNED.ALL;
+
+library work;
+use work.trb_net_std.all;
+
+entity trb_net_ram_dp is
+  generic(
+    depth : integer := 3;
+    width : integer := 16
+    );
+  port(
+    CLK   : in  std_logic;
+    wr1   : in  std_logic;
+    a1    : in  std_logic_vector(depth-1 downto 0);
+    dout1 : out std_logic_vector(width-1 downto 0);
+    din1  : in  std_logic_vector(width-1 downto 0);
+    a2    : in  std_logic_vector(depth-1 downto 0);
+    dout2 : out std_logic_vector(width-1 downto 0)
+    );
+end entity;
+
+architecture trb_net_ram_dp_arch of trb_net_ram_dp is
+  type ram_t is array(0 to 2**depth-1) of std_logic_vector(width-1 downto 0);
+  SIGNAL ram : ram_t ;
+begin
+
+
+  process(CLK)
+    begin
+      if rising_edge(CLK) then
+        if wr1 = '1' then
+          ram((conv_integer(a1))) <= din1;
+        end if;
+        dout1 <= ram(conv_integer(a1));
+        dout2 <= ram(conv_integer(a2));
+      end if;
+    end process;
+
+end architecture;
diff --git a/trb_net_ram_true_dp.vhd b/trb_net_ram_true_dp.vhd
new file mode 100644 (file)
index 0000000..169e158
--- /dev/null
@@ -0,0 +1,44 @@
+LIBRARY IEEE;
+USE IEEE.std_logic_1164.ALL;
+USE IEEE.std_logic_ARITH.ALL;
+USE IEEE.std_logic_UNSIGNED.ALL;
+
+library work;
+use work.trb_net_std.all;
+
+entity trb_net_ram_true_dp is
+  generic(
+    depth : integer := 5;
+    width : integer := 32
+    );
+  port(
+    CLK   : in std_logic;
+    wr1   : in std_logic;
+    wr2   : in std_logic;
+    a1    : in std_logic_vector(depth-1 downto 0);
+    dout1 : out std_logic_vector(width-1 downto 0);
+    din1  : in std_logic_vector(width-1 downto 0);
+    a2    : in std_logic_vector(depth-1 downto 0);
+    din2  : in std_logic_vector(width-1 downto 0);
+    dout2 : out std_logic_vector(width-1 downto 0)
+    );
+end entity;
+
+architecture trb_net_ram_true_dp_arch of trb_net_ram_true_dp is
+  type ram_t is array(0 to 2**depth-1) of std_logic_vector(width-1 downto 0);
+  SIGNAL ram : ram_t;
+
+begin
+  process(CLK) 
+    begin
+      if rising_edge(CLK) then
+        if wr1 = '1' then
+          ram(conv_integer(a1)) <= din1;
+        elsif wr2 = '1' then
+          ram(conv_integer(a2)) <= din2;
+        end if;
+        dout1 <= ram(conv_integer(a1));
+        dout2 <= ram(conv_integer(a2));
+      end if;
+    end process;
+end architecture;
index 605c68e4078d24ac9873fbafd6cbcd9b92568430..ead1e06563a7e50c4f17e94b78fe717932b5a9e7 100644 (file)
@@ -7,7 +7,6 @@ USE IEEE.std_logic_UNSIGNED.ALL;
 package trb_net_std is
     
   type channel_config_t is array(0 to 3) of integer;
-
     
 -- some basic definitions for the whole network
 -----------------------------------------------
@@ -90,6 +89,8 @@ package trb_net_std is
 
   constant LINK_STARTUP_WORD : std_logic_vector(15 downto 0) := x"e110";
 
+  constant SET_ADDRESS : std_logic_vector(7 downto 0) := x"AD";
+  constant ACK_ADDRESS : std_logic_vector(15 downto 0) := x"5ADD";
 
   
   function and_all (arg : std_logic_vector)