OpenCores
URL https://opencores.org/ocsvn/System09/System09/trunk

Subversion Repositories System09

[/] [System09/] [trunk/] [rtl/] [System09_Xess_XSA-3S1000/] [sdramcntl.vhd] - Diff between revs 66 and 115

Show entire file | Details | Blame | View Log

Rev 66 Rev 115
Line 22... Line 22...
      clk                  : in  std_logic;  -- master clock
      clk                  : in  std_logic;  -- master clock
      lock                 : in  std_logic;  -- true if clock is stable
      lock                 : in  std_logic;  -- true if clock is stable
      rst                  : in  std_logic;  -- reset
      rst                  : in  std_logic;  -- reset
      rd                   : in  std_logic;  -- initiate read operation
      rd                   : in  std_logic;  -- initiate read operation
      wr                   : in  std_logic;  -- initiate write operation
      wr                   : in  std_logic;  -- initiate write operation
 
      uds                  : in  std_logic;  -- upper byte data strobe
 
      lds                  : in  std_logic;  -- lower byte data strobe
      earlyOpBegun         : out std_logic;  -- read/write/self-refresh op has begun (async)
      earlyOpBegun         : out std_logic;  -- read/write/self-refresh op has begun (async)
      opBegun              : out std_logic;  -- read/write/self-refresh op has begun (clocked)
      opBegun              : out std_logic;  -- read/write/self-refresh op has begun (clocked)
      rdPending            : out std_logic;  -- true if read operation(s) are still in the pipeline
      rdPending            : out std_logic;  -- true if read operation(s) are still in the pipeline
      done                 : out std_logic;  -- read or write operation is done
      done                 : out std_logic;  -- read or write operation is done
      rdDone               : out std_logic;  -- read operation is done and data is available
      rdDone               : out std_logic;  -- read operation is done and data is available
Line 39... Line 41...
      ras_n                : out std_logic;  -- SDRAM row address strobe
      ras_n                : out std_logic;  -- SDRAM row address strobe
      cas_n                : out std_logic;  -- SDRAM column address strobe
      cas_n                : out std_logic;  -- SDRAM column address strobe
      we_n                 : out std_logic;  -- SDRAM write enable
      we_n                 : out std_logic;  -- SDRAM write enable
      ba                   : out std_logic_vector(1 downto 0);  -- SDRAM bank address
      ba                   : out std_logic_vector(1 downto 0);  -- SDRAM bank address
      sAddr                : out std_logic_vector(SADDR_WIDTH-1 downto 0);  -- SDRAM row/column address
      sAddr                : out std_logic_vector(SADDR_WIDTH-1 downto 0);  -- SDRAM row/column address
      sDIn                 : in  std_logic_vector(DATA_WIDTH-1 downto 0);  -- data from SDRAM
      sDIn                 : in  std_logic_vector(DATA_WIDTH-1 downto 0);  -- data to SDRAM
      sDOut                : out std_logic_vector(DATA_WIDTH-1 downto 0);  -- data to SDRAM
      sDOut                : out std_logic_vector(DATA_WIDTH-1 downto 0);  -- data from SDRAM
      sDOutEn              : out std_logic;  -- true if data is output to SDRAM on sDOut
      sDOutEn              : out std_logic;  -- true if data is output to SDRAM on sDOut
      dqmh                 : out std_logic;  -- enable upper-byte of SDRAM databus if true
      dqmh                 : out std_logic;  -- enable upper-byte of SDRAM databus if true
      dqml                 : out std_logic  -- enable lower-byte of SDRAM databus if true
      dqml                 : out std_logic  -- enable lower-byte of SDRAM databus if true
      );
      );
  end component;
  end component;
Line 62... Line 64...
 
 
      -- host-side port 0
      -- host-side port 0
      rst0          : in  std_logic;    -- reset
      rst0          : in  std_logic;    -- reset
      rd0           : in  std_logic;    -- initiate read operation
      rd0           : in  std_logic;    -- initiate read operation
      wr0           : in  std_logic;    -- initiate write operation
      wr0           : in  std_logic;    -- initiate write operation
 
      uds0          : in  std_logic;     -- upper data strobe
 
      lds0          : in  std_logic;     -- lower data strobe
      earlyOpBegun0 : out std_logic;    -- read/write op has begun (async)
      earlyOpBegun0 : out std_logic;    -- read/write op has begun (async)
      opBegun0      : out std_logic;    -- read/write op has begun (clocked)
      opBegun0      : out std_logic;    -- read/write op has begun (clocked)
      rdPending0    : out std_logic;    -- true if read operation(s) are still in the pipeline
      rdPending0    : out std_logic;    -- true if read operation(s) are still in the pipeline
      done0         : out std_logic;    -- read or write operation is done
      done0         : out std_logic;    -- read or write operation is done
      rdDone0       : out std_logic;    -- read operation is done and data is available
      rdDone0       : out std_logic;    -- read operation is done and data is available
Line 76... Line 80...
 
 
      -- host-side port 1
      -- host-side port 1
      rst1          : in  std_logic;
      rst1          : in  std_logic;
      rd1           : in  std_logic;
      rd1           : in  std_logic;
      wr1           : in  std_logic;
      wr1           : in  std_logic;
 
      uds1          : in  std_logic;
 
      lds1          : in  std_logic;
      earlyOpBegun1 : out std_logic;
      earlyOpBegun1 : out std_logic;
      opBegun1      : out std_logic;
      opBegun1      : out std_logic;
      rdPending1    : out std_logic;
      rdPending1    : out std_logic;
      done1         : out std_logic;
      done1         : out std_logic;
      rdDone1       : out std_logic;
      rdDone1       : out std_logic;
Line 118... Line 124...
--
--
-- Description:
-- Description:
-- SDRAM controller
-- SDRAM controller
--
--
-- Revision:
-- Revision:
-- 1.4.0
-- 1.5.0
--
--
-- Additional Comments:
-- Additional Comments:
 
-- 1.5.0:
 
-- John Kent 2008-03-28
 
-- added upper and lower data strobes.
-- 1.4.0:
-- 1.4.0:
-- Added generic parameter to enable/disable independent active rows in each bank.
-- Added generic parameter to enable/disable independent active rows in each bank.
-- 1.3.0:
-- 1.3.0:
-- Modified to allow independently active rows in each bank.
-- Modified to allow independently active rows in each bank.
-- 1.2.0:
-- 1.2.0:
Line 161... Line 170...
    clk                  : in  std_logic;  -- master clock
    clk                  : in  std_logic;  -- master clock
    lock                 : in  std_logic;  -- true if clock is stable
    lock                 : in  std_logic;  -- true if clock is stable
    rst                  : in  std_logic;  -- reset
    rst                  : in  std_logic;  -- reset
    rd                   : in  std_logic;  -- initiate read operation
    rd                   : in  std_logic;  -- initiate read operation
    wr                   : in  std_logic;  -- initiate write operation
    wr                   : in  std_logic;  -- initiate write operation
 
    uds                  : in  std_logic;  -- upper data strobe
 
    lds                  : in  std_logic;  -- lower data strobe
    earlyOpBegun         : out std_logic;  -- read/write/self-refresh op has begun (async)
    earlyOpBegun         : out std_logic;  -- read/write/self-refresh op has begun (async)
    opBegun              : out std_logic;  -- read/write/self-refresh op has begun (clocked)
    opBegun              : out std_logic;  -- read/write/self-refresh op has begun (clocked)
    rdPending            : out std_logic;  -- true if read operation(s) are still in the pipeline
    rdPending            : out std_logic;  -- true if read operation(s) are still in the pipeline
    done                 : out std_logic;  -- read or write operation is done
    done                 : out std_logic;  -- read or write operation is done
    rdDone               : out std_logic;  -- read operation is done and data is available
    rdDone               : out std_logic;  -- read operation is done and data is available
Line 246... Line 257...
    );
    );
  signal state_r, state_x : cntlState;  -- state register and next state
  signal state_r, state_x : cntlState;  -- state register and next state
 
 
  -- commands that are sent to the SDRAM to make it perform certain operations
  -- commands that are sent to the SDRAM to make it perform certain operations
  -- commands use these SDRAM input pins (ce_n,ras_n,cas_n,we_n,dqmh,dqml)
  -- commands use these SDRAM input pins (ce_n,ras_n,cas_n,we_n,dqmh,dqml)
  subtype sdramCmd is unsigned(5 downto 0);
--  subtype sdramCmd is unsigned(5 downto 0);
  constant NOP_CMD    : sdramCmd := "011100";
--  constant NOP_CMD    : sdramCmd := "011100";
  constant ACTIVE_CMD : sdramCmd := "001100";
--  constant ACTIVE_CMD : sdramCmd := "001100";
  constant READ_CMD   : sdramCmd := "010100";
--  constant READ_CMD   : sdramCmd := "010100";
  constant WRITE_CMD  : sdramCmd := "010000";
--  constant WRITE_CMD  : sdramCmd := "010000";
  constant PCHG_CMD   : sdramCmd := "001011";
--  constant PCHG_CMD   : sdramCmd := "001011";
  constant MODE_CMD   : sdramCmd := "000011";
--  constant MODE_CMD   : sdramCmd := "000011";
  constant RFSH_CMD   : sdramCmd := "000111";
--  constant RFSH_CMD   : sdramCmd := "000111";
 
 
 
  -- commands that are sent to the SDRAM to make it perform certain operations
 
  -- commands use these SDRAM input pins (ce_n,ras_n,cas_n,we_n)
 
  subtype sdramCmd is unsigned(3 downto 0);
 
  constant NOP_CMD    : sdramCmd := "0111";
 
  constant ACTIVE_CMD : sdramCmd := "0011";
 
  constant READ_CMD   : sdramCmd := "0101";
 
  constant WRITE_CMD  : sdramCmd := "0100";
 
  constant PCHG_CMD   : sdramCmd := "0010";
 
  constant MODE_CMD   : sdramCmd := "0000";
 
  constant RFSH_CMD   : sdramCmd := "0001";
 
 
  -- SDRAM mode register
  -- SDRAM mode register
  -- the SDRAM is placed in a non-burst mode (burst length = 1) with a 3-cycle CAS
  -- the SDRAM is placed in a non-burst mode (burst length = 1) with a 3-cycle CAS
  subtype sdramMode is std_logic_vector(12 downto 0);
  subtype sdramMode is std_logic_vector(12 downto 0);
  constant MODE : sdramMode := "000" & "0" & "00" & "011" & "0" & "000";
  constant MODE : sdramMode := "000" & "0" & "00" & "011" & "0" & "000";
Line 303... Line 325...
  signal cke_r, cke_x           : std_logic;  -- clock enable 
  signal cke_r, cke_x           : std_logic;  -- clock enable 
  signal cmd_r, cmd_x           : sdramCmd;  -- SDRAM command bits
  signal cmd_r, cmd_x           : sdramCmd;  -- SDRAM command bits
  signal ba_r, ba_x             : std_logic_vector(ba'range);  -- SDRAM bank address bits
  signal ba_r, ba_x             : std_logic_vector(ba'range);  -- SDRAM bank address bits
  signal sAddr_r, sAddr_x       : std_logic_vector(sAddr'range);  -- SDRAM row/column address
  signal sAddr_r, sAddr_x       : std_logic_vector(sAddr'range);  -- SDRAM row/column address
  signal sData_r, sData_x       : std_logic_vector(sDOut'range);  -- SDRAM out databus
  signal sData_r, sData_x       : std_logic_vector(sDOut'range);  -- SDRAM out databus
 
  signal dqmh_r, dqmh_x         : std_logic;  -- SDRAM upper data mask
 
  signal dqml_r, dqml_x         : std_logic;  -- SDRAM lower data mask
  signal sDataDir_r, sDataDir_x : std_logic;  -- SDRAM databus direction control bit
  signal sDataDir_r, sDataDir_x : std_logic;  -- SDRAM databus direction control bit
 
 
begin
begin
 
 
 
assign_single_port : process( cmd_r, dqmh_r, dqml_r, cke_r,
 
                              ba_r, sAddr_r,
 
                                                                 sData_r, sDataDir_r,
 
                              hDOut_r, opBegun_r )
 
begin
  -----------------------------------------------------------
  -----------------------------------------------------------
  -- attach some internal signals to the I/O ports 
  -- attach some internal signals to the I/O ports 
  -----------------------------------------------------------
  -----------------------------------------------------------
 
 
  -- attach registered SDRAM control signals to SDRAM input pins
  -- attach registered SDRAM control signals to SDRAM input pins
  (ce_n, ras_n, cas_n, we_n, dqmh, dqml) <= cmd_r;  -- SDRAM operation control bits
  (ce_n, ras_n, cas_n, we_n) <= cmd_r;  -- SDRAM operation control bits
 
  dqmh                                     <= dqmh_r;
 
  dqml                       <= dqml_r;
  cke                                    <= cke_r;  -- SDRAM clock enable
  cke                                    <= cke_r;  -- SDRAM clock enable
  ba                                     <= ba_r;  -- SDRAM bank address
  ba                                     <= ba_r;  -- SDRAM bank address
  sAddr                                  <= sAddr_r;  -- SDRAM address
  sAddr                                  <= sAddr_r;  -- SDRAM address
  sDOut                                  <= sData_r;  -- SDRAM output data bus
  sDOut                                  <= sData_r;  -- SDRAM output data bus
  sDOutEn                                <= YES when sDataDir_r = OUTPUT else NO;  -- output databus enable
  if sDataDir_r = OUTPUT then
 
     sDOutEn                 <= YES;
 
  else
 
     sDOutEn                 <= NO;  -- output databus enable
 
  end if;
  -- attach some port signals
  -- attach some port signals
  hDOut   <= hDOut_r;                   -- data back to host
  hDOut   <= hDOut_r;                   -- data back to host
  opBegun <= opBegun_r;                 -- true if requested operation has begun
  opBegun <= opBegun_r;                 -- true if requested operation has begun
 
end process;
 
 
 
 
  -----------------------------------------------------------
  -----------------------------------------------------------
  -- compute the next state and outputs 
  -- compute the next state and outputs 
  -----------------------------------------------------------
  -----------------------------------------------------------
 
 
  combinatorial : process(rd, wr, hAddr, hDIn, hDOut_r, sDIn, state_r, opBegun_x,
  combinatorial : process(rd, wr, hAddr, hDIn, hDOut_r, sDIn, state_r, opBegun_x,
                          activeFlag_r, activeRow_r, rdPipeline_r, wrPipeline_r,
                          activeFlag_r, activeRow_r, rdPipeline_r, wrPipeline_r,
                          hDOutOppPhase_r, nopCntr_r, lock, rfshCntr_r, timer_r, rasTimer_r,
                          hDOutOppPhase_r, nopCntr_r, lock, rfshCntr_r, timer_r, rasTimer_r,
                          wrTimer_r, refTimer_r, cmd_r, cke_r, activeBank_r, ba_r )
                          wrTimer_r, refTimer_r, cmd_r, uds, lds, cke_r, activeBank_r, ba_r )
  begin
  begin
 
 
    -----------------------------------------------------------
    -----------------------------------------------------------
    -- setup default values for signals 
    -- setup default values for signals 
    -----------------------------------------------------------
    -----------------------------------------------------------
 
 
    opBegun_x    <= NO;                 -- no operations have begun
    opBegun_x    <= NO;                 -- no operations have begun
    earlyOpBegun <= opBegun_x;
    earlyOpBegun <= opBegun_x;
    cke_x        <= YES;                -- enable SDRAM clock
    cke_x        <= YES;                -- enable SDRAM clock
    cmd_x        <= NOP_CMD;            -- set SDRAM command to no-operation
    cmd_x        <= NOP_CMD;            -- set SDRAM command to no-operation
 
    dqmh_x       <= '0';
 
         dqml_x       <= '0';
    sDataDir_x   <= INPUT;              -- accept data from the SDRAM
    sDataDir_x   <= INPUT;              -- accept data from the SDRAM
    sData_x      <= hDIn(sData_x'range);  -- output data from host to SDRAM
    sData_x      <= hDIn(sData_x'range);  -- output data from host to SDRAM
    state_x      <= state_r;            -- reload these registers and flags
    state_x      <= state_r;            -- reload these registers and flags
    activeFlag_x <= activeFlag_r;       --              with their existing values
    activeFlag_x <= activeFlag_r;       --              with their existing values
    activeRow_x  <= activeRow_r;
    activeRow_x  <= activeRow_r;
Line 370... Line 407...
    -- extend column (if needed) until it is as large as the (SDRAM address bus - 1)
    -- extend column (if needed) until it is as large as the (SDRAM address bus - 1)
    col                     <= (others => '0');  -- set it to all zeroes
    col                     <= (others => '0');  -- set it to all zeroes
    col(COL_LEN-1 downto 0) <= hAddr(COL_LEN-1 downto 0);
    col(COL_LEN-1 downto 0) <= hAddr(COL_LEN-1 downto 0);
    -- by default, set SDRAM address to the column address with interspersed
    -- by default, set SDRAM address to the column address with interspersed
    -- command bit set to disable auto-precharge
    -- command bit set to disable auto-precharge
    sAddr_x                 <= col(col'high-1 downto CMDBIT_POS) & AUTO_PCHG_OFF
    sAddr_x                 <= col(col'high downto CMDBIT_POS+1) & AUTO_PCHG_OFF
                               & col(CMDBIT_POS-1 downto 0);
                               & col(CMDBIT_POS-1 downto 0);
 
 
    -----------------------------------------------------------
    -----------------------------------------------------------
    -- manage the read and write operation pipelines
    -- manage the read and write operation pipelines
    -----------------------------------------------------------
    -----------------------------------------------------------
Line 517... Line 554...
          -----------------------------------------------------------
          -----------------------------------------------------------
          -- precharge all SDRAM banks after power-on initialization 
          -- precharge all SDRAM banks after power-on initialization 
          -----------------------------------------------------------
          -----------------------------------------------------------
        when INITPCHG =>
        when INITPCHG =>
          cmd_x               <= PCHG_CMD;
          cmd_x               <= PCHG_CMD;
 
                         dqmh_x              <= '1';
 
                         dqml_x              <= '1';
          sAddr_x(CMDBIT_POS) <= ALL_BANKS;  -- precharge all banks
          sAddr_x(CMDBIT_POS) <= ALL_BANKS;  -- precharge all banks
          timer_x             <= RP_CYCLES;  -- set timer for precharge operation duration
          timer_x             <= RP_CYCLES;  -- set timer for precharge operation duration
          rfshCntr_x          <= RFSH_OPS;  -- set counter for refresh ops needed after precharge
          rfshCntr_x          <= RFSH_OPS;  -- set counter for refresh ops needed after precharge
          state_x             <= INITRFSH;
          state_x             <= INITRFSH;
          status              <= "0010";
          status              <= "0010";
Line 528... Line 567...
          -----------------------------------------------------------
          -----------------------------------------------------------
          -- refresh the SDRAM a number of times after initial precharge 
          -- refresh the SDRAM a number of times after initial precharge 
          -----------------------------------------------------------
          -----------------------------------------------------------
        when INITRFSH =>
        when INITRFSH =>
          cmd_x      <= RFSH_CMD;
          cmd_x      <= RFSH_CMD;
 
                         dqmh_x     <= '1';
 
                         dqml_x     <= '1';
          timer_x    <= RFC_CYCLES;     -- set timer to refresh operation duration
          timer_x    <= RFC_CYCLES;     -- set timer to refresh operation duration
          rfshCntr_x <= rfshCntr_r - 1;  -- decrement refresh operation counter
          rfshCntr_x <= rfshCntr_r - 1;  -- decrement refresh operation counter
          if rfshCntr_r = 1 then
          if rfshCntr_r = 1 then
            state_x  <= INITSETMODE;    -- set the SDRAM mode once all refresh ops are done
            state_x  <= INITSETMODE;    -- set the SDRAM mode once all refresh ops are done
          end if;
          end if;
Line 540... Line 581...
          -----------------------------------------------------------
          -----------------------------------------------------------
          -- set the mode register of the SDRAM 
          -- set the mode register of the SDRAM 
          -----------------------------------------------------------
          -----------------------------------------------------------
        when INITSETMODE =>
        when INITSETMODE =>
          cmd_x   <= MODE_CMD;
          cmd_x   <= MODE_CMD;
 
                         dqmh_x  <= '1';
 
                         dqml_x  <= '1';
          sAddr_x <= MODE;              -- output mode register bits on the SDRAM address bits
          sAddr_x <= MODE;              -- output mode register bits on the SDRAM address bits
          timer_x <= MODE_CYCLES;       -- set timer for mode setting operation duration
          timer_x <= MODE_CYCLES;       -- set timer for mode setting operation duration
          state_x <= RW;
          state_x <= RW;
          status  <= "0100";
          status  <= "0100";
 
 
Line 557... Line 600...
          -----------------------------------------------------------
          -----------------------------------------------------------
          if rfshCntr_r /= 0 then
          if rfshCntr_r /= 0 then
                                        -- wait for any row activations, writes or reads to finish before doing a precharge
                                        -- wait for any row activations, writes or reads to finish before doing a precharge
            if (activateInProgress = NO) and (wrInProgress = NO) and (rdInProgress = NO) then
            if (activateInProgress = NO) and (wrInProgress = NO) and (rdInProgress = NO) then
              cmd_x                       <= PCHG_CMD;  -- initiate precharge of the SDRAM
              cmd_x                       <= PCHG_CMD;  -- initiate precharge of the SDRAM
 
              dqmh_x                      <= '1';
 
              dqml_x                      <= '1';
              sAddr_x(CMDBIT_POS)         <= ALL_BANKS;  -- precharge all banks
              sAddr_x(CMDBIT_POS)         <= ALL_BANKS;  -- precharge all banks
              timer_x                     <= RP_CYCLES;  -- set timer for this operation
              timer_x                     <= RP_CYCLES;  -- set timer for this operation
              activeFlag_x                <= (others => NO);  -- all rows are inactive after a precharge operation
              activeFlag_x                <= (others => NO);  -- all rows are inactive after a precharge operation
              state_x                     <= REFRESHROW;  -- refresh the SDRAM after the precharge
              state_x                     <= REFRESHROW;  -- refresh the SDRAM after the precharge
            end if;
            end if;
Line 575... Line 620...
                                        -- activate a new row if the current read is outside the active row or bank
                                        -- activate a new row if the current read is outside the active row or bank
              if doActivate = YES then
              if doActivate = YES then
                                        -- activate new row only if all previous activations, writes, reads are done
                                        -- activate new row only if all previous activations, writes, reads are done
                if (activateInProgress = NO) and (wrInProgress = NO) and (rdInProgress = NO) then
                if (activateInProgress = NO) and (wrInProgress = NO) and (rdInProgress = NO) then
                  cmd_x                   <= PCHG_CMD;  -- initiate precharge of the SDRAM
                  cmd_x                   <= PCHG_CMD;  -- initiate precharge of the SDRAM
 
                  dqmh_x                  <= '1';
 
                  dqml_x                  <= '1';
                  sAddr_x(CMDBIT_POS)     <= ONE_BANK;  -- precharge this bank
                  sAddr_x(CMDBIT_POS)     <= ONE_BANK;  -- precharge this bank
                  timer_x                 <= RP_CYCLES;  -- set timer for this operation
                  timer_x                 <= RP_CYCLES;  -- set timer for this operation
                  activeFlag_x(bankIndex) <= NO;  -- rows in this bank are inactive after a precharge operation
                  activeFlag_x(bankIndex) <= NO;  -- rows in this bank are inactive after a precharge operation
                  state_x                 <= ACTIVATE;  -- activate the new row after the precharge is done
                  state_x                 <= ACTIVATE;  -- activate the new row after the precharge is done
                end if;
                end if;
Line 587... Line 634...
                                        -- we can always initiate a read even if a write is already in progress
                                        -- we can always initiate a read even if a write is already in progress
              elsif (rdInProgress = NO) or PIPE_EN then
              elsif (rdInProgress = NO) or PIPE_EN then
                cmd_x                     <= READ_CMD;  -- initiate a read of the SDRAM
                cmd_x                     <= READ_CMD;  -- initiate a read of the SDRAM
                                        -- insert a flag into the pipeline shift register that will exit the end
                                        -- insert a flag into the pipeline shift register that will exit the end
                                        -- of the shift register when the data from the SDRAM is available
                                        -- of the shift register when the data from the SDRAM is available
 
                dqmh_x                    <= not uds;
 
                dqml_x                    <= not lds;
                rdPipeline_x              <= READ & rdPipeline_r(rdPipeline_r'high downto 1);
                rdPipeline_x              <= READ & rdPipeline_r(rdPipeline_r'high downto 1);
                opBegun_x                 <= YES;  -- tell the host the requested operation has begun
                opBegun_x                 <= YES;  -- tell the host the requested operation has begun
              end if;
              end if;
            end if;
            end if;
            status                        <= "0110";
            status                        <= "0110";
Line 604... Line 653...
                                        -- activate a new row if the current write is outside the active row or bank
                                        -- activate a new row if the current write is outside the active row or bank
              if doActivate = YES then
              if doActivate = YES then
                                        -- activate new row only if all previous activations, writes, reads are done
                                        -- activate new row only if all previous activations, writes, reads are done
                if (activateInProgress = NO) and (wrInProgress = NO) and (rdInProgress = NO) then
                if (activateInProgress = NO) and (wrInProgress = NO) and (rdInProgress = NO) then
                  cmd_x                   <= PCHG_CMD;  -- initiate precharge of the SDRAM
                  cmd_x                   <= PCHG_CMD;  -- initiate precharge of the SDRAM
 
                  dqmh_x                  <= '1';
 
                  dqml_x                  <= '1';
                  sAddr_x(CMDBIT_POS)     <= ONE_BANK;  -- precharge this bank
                  sAddr_x(CMDBIT_POS)     <= ONE_BANK;  -- precharge this bank
                  timer_x                 <= RP_CYCLES;  -- set timer for this operation
                  timer_x                 <= RP_CYCLES;  -- set timer for this operation
                  activeFlag_x(bankIndex) <= NO;  -- rows in this bank are inactive after a precharge operation
                  activeFlag_x(bankIndex) <= NO;  -- rows in this bank are inactive after a precharge operation
                  state_x                 <= ACTIVATE;  -- activate the new row after the precharge is done
                  state_x                 <= ACTIVATE;  -- activate the new row after the precharge is done
                end if;
                end if;
                                        -- write to the currently active row if no previous read operations are in progress
                                        -- write to the currently active row if no previous read operations are in progress
              elsif rdInProgress = NO then
              elsif rdInProgress = NO then
                cmd_x                     <= WRITE_CMD;  -- initiate the write operation
                cmd_x                     <= WRITE_CMD;  -- initiate the write operation
 
                dqmh_x                    <= not uds;
 
                dqml_x                    <= not lds;
                sDataDir_x                <= OUTPUT;  -- turn on drivers to send data to SDRAM
                sDataDir_x                <= OUTPUT;  -- turn on drivers to send data to SDRAM
                                        -- set timer so precharge doesn't occur too soon after write operation
                                        -- set timer so precharge doesn't occur too soon after write operation
                wrTimer_x                 <= WR_CYCLES;
                wrTimer_x                 <= WR_CYCLES;
                                        -- insert a flag into the 1-bit pipeline shift register that will exit on the
                                        -- insert a flag into the 1-bit pipeline shift register that will exit on the
                                        -- next cycle.  The write into SDRAM is not actually done by that time, but
                                        -- next cycle.  The write into SDRAM is not actually done by that time, but
Line 630... Line 683...
            -----------------------------------------------------------
            -----------------------------------------------------------
          elsif doSelfRfsh = YES then
          elsif doSelfRfsh = YES then
                                        -- wait until all previous activations, writes, reads are done
                                        -- wait until all previous activations, writes, reads are done
            if (activateInProgress = NO) and (wrInProgress = NO) and (rdInProgress = NO) then
            if (activateInProgress = NO) and (wrInProgress = NO) and (rdInProgress = NO) then
              cmd_x                       <= PCHG_CMD;  -- initiate precharge of the SDRAM
              cmd_x                       <= PCHG_CMD;  -- initiate precharge of the SDRAM
 
              dqmh_x                       <= '1';
 
              dqml_x                       <= '1';
              sAddr_x(CMDBIT_POS)         <= ALL_BANKS;  -- precharge all banks
              sAddr_x(CMDBIT_POS)         <= ALL_BANKS;  -- precharge all banks
              timer_x                     <= RP_CYCLES;  -- set timer for this operation
              timer_x                     <= RP_CYCLES;  -- set timer for this operation
              activeFlag_x                <= (others => NO);  -- all rows are inactive after a precharge operation
              activeFlag_x                <= (others => NO);  -- all rows are inactive after a precharge operation
              state_x                     <= SELFREFRESH;  -- self-refresh the SDRAM after the precharge
              state_x                     <= SELFREFRESH;  -- self-refresh the SDRAM after the precharge
            end if;
            end if;
Line 649... Line 704...
          -----------------------------------------------------------
          -----------------------------------------------------------
          -- activate a row of the SDRAM 
          -- activate a row of the SDRAM 
          -----------------------------------------------------------
          -----------------------------------------------------------
        when ACTIVATE                        =>
        when ACTIVATE                        =>
          cmd_x                   <= ACTIVE_CMD;
          cmd_x                   <= ACTIVE_CMD;
 
          dqmh_x                  <= '0';
 
          dqml_x                  <= '0';
          sAddr_x                 <= (others => '0');  -- output the address for the row to be activated
          sAddr_x                 <= (others => '0');  -- output the address for the row to be activated
          sAddr_x(row'range)      <= row;
          sAddr_x(row'range)      <= row;
          activeBank_x            <= bank;
          activeBank_x            <= bank;
          activeRow_x(bankIndex)  <= row;  -- store the new active SDRAM row address
          activeRow_x(bankIndex)  <= row;  -- store the new active SDRAM row address
          activeFlag_x(bankIndex) <= YES;  -- the SDRAM is now active
          activeFlag_x(bankIndex) <= YES;  -- the SDRAM is now active
Line 664... Line 721...
          -----------------------------------------------------------
          -----------------------------------------------------------
          -- refresh a row of the SDRAM         
          -- refresh a row of the SDRAM         
          -----------------------------------------------------------
          -----------------------------------------------------------
        when REFRESHROW =>
        when REFRESHROW =>
          cmd_x      <= RFSH_CMD;
          cmd_x      <= RFSH_CMD;
 
          dqmh_x     <= '1';
 
          dqml_x     <= '1';
          timer_x    <= RFC_CYCLES;     -- refresh operation interval
          timer_x    <= RFC_CYCLES;     -- refresh operation interval
          rfshCntr_x <= rfshCntr_r - 1;  -- decrement the number of needed row refreshes
          rfshCntr_x <= rfshCntr_r - 1;  -- decrement the number of needed row refreshes
          state_x    <= RW;             -- process more SDRAM operations after refresh is done
          state_x    <= RW;             -- process more SDRAM operations after refresh is done
          status     <= "1011";
          status     <= "1011";
 
 
Line 676... Line 735...
          -----------------------------------------------------------
          -----------------------------------------------------------
        when SELFREFRESH            =>
        when SELFREFRESH            =>
          if (doSelfRfsh = YES) or (lock = NO) then
          if (doSelfRfsh = YES) or (lock = NO) then
                                        -- keep the SDRAM in self-refresh mode as long as requested and until there is a stable clock
                                        -- keep the SDRAM in self-refresh mode as long as requested and until there is a stable clock
            cmd_x        <= RFSH_CMD;   -- output the refresh command; this is only needed on the first clock cycle
            cmd_x        <= RFSH_CMD;   -- output the refresh command; this is only needed on the first clock cycle
 
            dqmh_x       <= '1';
 
            dqml_x       <= '1';
            cke_x        <= NO;         -- disable the SDRAM clock
            cke_x        <= NO;         -- disable the SDRAM clock
          else
          else
                                        -- else exit self-refresh mode and start processing read and write operations
                                        -- else exit self-refresh mode and start processing read and write operations
            cke_x        <= YES;        -- restart the SDRAM clock
            cke_x        <= YES;        -- restart the SDRAM clock
            rfshCntr_x   <= 0;          -- no refreshes are needed immediately after leaving self-refresh
            rfshCntr_x   <= 0;          -- no refreshes are needed immediately after leaving self-refresh
Line 721... Line 782...
      opBegun_r    <= NO;
      opBegun_r    <= NO;
      rdPipeline_r <= (others => '0');
      rdPipeline_r <= (others => '0');
      wrPipeline_r <= (others => '0');
      wrPipeline_r <= (others => '0');
      cke_r        <= NO;
      cke_r        <= NO;
      cmd_r        <= NOP_CMD;
      cmd_r        <= NOP_CMD;
 
                dqmh_r       <= '1';
 
                dqml_r       <= '1';
      ba_r         <= (others => '0');
      ba_r         <= (others => '0');
      sAddr_r      <= (others => '0');
      sAddr_r      <= (others => '0');
      sData_r      <= (others => '0');
      sData_r      <= (others => '0');
      sDataDir_r   <= INPUT;
      sDataDir_r   <= INPUT;
      hDOut_r      <= (others => '0');
      hDOut_r      <= (others => '0');
Line 742... Line 805...
      opBegun_r    <= opBegun_x;
      opBegun_r    <= opBegun_x;
      rdPipeline_r <= rdPipeline_x;
      rdPipeline_r <= rdPipeline_x;
      wrPipeline_r <= wrPipeline_x;
      wrPipeline_r <= wrPipeline_x;
      cke_r        <= cke_x;
      cke_r        <= cke_x;
      cmd_r        <= cmd_x;
      cmd_r        <= cmd_x;
 
                dqmh_r       <= dqmh_x;
 
                dqml_r       <= dqml_x;
      ba_r         <= ba_x;
      ba_r         <= ba_x;
      sAddr_r      <= sAddr_x;
      sAddr_r      <= sAddr_x;
      sData_r      <= sData_x;
      sData_r      <= sData_x;
      sDataDir_r   <= sDataDir_x;
      sDataDir_r   <= sDataDir_x;
      hDOut_r      <= hDOut_x;
      hDOut_r      <= hDOut_x;
Line 776... Line 841...
-- Description:
-- Description:
-- Dual-port front-end for SDRAM controller. Supports two
-- Dual-port front-end for SDRAM controller. Supports two
-- independent I/O ports to the SDRAM.
-- independent I/O ports to the SDRAM.
--
--
-- Revision:
-- Revision:
 
-- 1.2.0:
 
--     added upper and lower data strobe
 
--     John Kent - 2008-03-23
 
--
-- 1.0.0
-- 1.0.0
 
--     Dave Vanden Bout - 2005-01-06
--
--
-- Additional Comments:
-- Additional Comments:
--
--
-- License:
-- License:
-- This code can be freely distributed and modified as long as
-- This code can be freely distributed and modified as long as
Line 805... Line 875...
 
 
    -- host-side port 0
    -- host-side port 0
    rst0          : in  std_logic;      -- reset
    rst0          : in  std_logic;      -- reset
    rd0           : in  std_logic;      -- initiate read operation
    rd0           : in  std_logic;      -- initiate read operation
    wr0           : in  std_logic;      -- initiate write operation
    wr0           : in  std_logic;      -- initiate write operation
 
    uds0          : in  std_logic;      -- upper data strobe
 
    lds0          : in  std_logic;      -- lower data strobe
    earlyOpBegun0 : out std_logic;      -- read/write op has begun (async)
    earlyOpBegun0 : out std_logic;      -- read/write op has begun (async)
    opBegun0      : out std_logic;      -- read/write op has begun (clocked)
    opBegun0      : out std_logic;      -- read/write op has begun (clocked)
    rdPending0    : out std_logic;      -- true if read operation(s) are still in the pipeline
    rdPending0    : out std_logic;      -- true if read operation(s) are still in the pipeline
    done0         : out std_logic;      -- read or write operation is done
    done0         : out std_logic;      -- read or write operation is done
    rdDone0       : out std_logic;      -- read operation is done and data is available
    rdDone0       : out std_logic;      -- read operation is done and data is available
Line 819... Line 891...
 
 
    -- host-side port 1
    -- host-side port 1
    rst1          : in  std_logic;
    rst1          : in  std_logic;
    rd1           : in  std_logic;
    rd1           : in  std_logic;
    wr1           : in  std_logic;
    wr1           : in  std_logic;
 
    uds1          : in  std_logic;      -- upper data strobe
 
    lds1          : in  std_logic;      -- lower data strobe
    earlyOpBegun1 : out std_logic;
    earlyOpBegun1 : out std_logic;
    opBegun1      : out std_logic;
    opBegun1      : out std_logic;
    rdPending1    : out std_logic;
    rdPending1    : out std_logic;
    done1         : out std_logic;
    done1         : out std_logic;
    rdDone1       : out std_logic;
    rdDone1       : out std_logic;
Line 833... Line 907...
 
 
    -- SDRAM controller port
    -- SDRAM controller port
    rst          : out std_logic;
    rst          : out std_logic;
    rd           : out std_logic;
    rd           : out std_logic;
    wr           : out std_logic;
    wr           : out std_logic;
 
    uds          : out std_logic;      -- upper data strobe
 
    lds          : out std_logic;      -- lower data strobe
    earlyOpBegun : in  std_logic;
    earlyOpBegun : in  std_logic;
    opBegun      : in  std_logic;
    opBegun      : in  std_logic;
    rdPending    : in  std_logic;
    rdPending    : in  std_logic;
    done         : in  std_logic;
    done         : in  std_logic;
    rdDone       : in  std_logic;
    rdDone       : in  std_logic;
Line 865... Line 941...
  signal wr_i                             : std_logic;  -- write signal to the SDRAM controller (internal copy)
  signal wr_i                             : std_logic;  -- write signal to the SDRAM controller (internal copy)
  signal earlyOpBegun0_i, earlyOpBegun1_i : std_logic;  -- (internal copies)
  signal earlyOpBegun0_i, earlyOpBegun1_i : std_logic;  -- (internal copies)
  signal slot_r, slot_x                   : std_logic_vector(PORT_TIME_SLOTS'range);  -- time-slot allocation shift-register
  signal slot_r, slot_x                   : std_logic_vector(PORT_TIME_SLOTS'range);  -- time-slot allocation shift-register
begin
begin
 
 
 
assign_dual_ports : process( port_r, hAddr0, hAddr1, hDIn0, hDIn1, uds0, uds1, lds0, lds1,
 
                             hDout, status, rst0, rst1, rd0, rd1, wr0, wr1, door_r,
 
                             earlyOpBegun, earlyOpBegun0_i, earlyOpBegun1_i,
 
                             rdPending, Done, rdDone, rd_i, wr_i, slot_r )
 
begin
  ----------------------------------------------------------------------------
  ----------------------------------------------------------------------------
  -- multiplex the SDRAM controller port signals to/from the dual host-side ports  
  -- multiplex the SDRAM controller port signals to/from the dual host-side ports  
  ----------------------------------------------------------------------------
  ----------------------------------------------------------------------------
 
 
  -- send the SDRAM controller the address and data from the currently active port
  -- send the SDRAM controller the address and data from the currently active port
  hAddr <= hAddr0 when port_r = PORT0 else hAddr1;
  if port_r = PORT0 then
  hDIn  <= hDIn0  when port_r = PORT0 else hDIn1;
    hAddr   <= hAddr0;
 
    hDIn    <= hDIn0;
 
    uds     <= uds0;
 
    lds     <= lds0;
 
  -- send the SDRAM controller status to the active port and give the inactive port an inactive status code
 
    status0 <= status;
 
         status1 <= "1111";
 
  -- apply the read and write signals from the active port to the SDRAM controller only if the door is open.
 
         if door_r = OPENED then
 
           rd_i <= rd0;
 
                wr_i <= wr0;
 
         else
 
           rd_i <= NO;
 
                wr_i <= NO;
 
    end if;
 
    earlyOpBegun0_i <= earlyOpBegun;
 
    earlyOpBegun1_i <= NO;
 
    rdPending0      <= rdPending;
 
    rdPending1      <= NO;
 
    done0           <= done;
 
    done1           <= NO;
 
    rdDone0         <= rdDone;
 
    rdDone1         <= NO;
 
  else
 
    hAddr   <= hAddr1;
 
    hDIn    <= hDIn1;
 
    uds     <= uds1;
 
    lds     <= lds1;
 
  -- send the SDRAM controller status to the active port and give the inactive port an inactive status code
 
         status0 <= "1111";
 
    status1 <= status;
 
  -- apply the read and write signals from the active port to the SDRAM controller only if the door is open.
 
         if door_r = OPENED then
 
           rd_i <= rd1;
 
           wr_i <= wr1;
 
         else
 
           rd_i <= NO;
 
           wr_i <= NO;
 
    end if;
 
    earlyOpBegun0_i <= NO;
 
    earlyOpBegun1_i <= earlyOpBegun;
 
    rdPending0      <= NO;
 
    rdPending1      <= rdPending;
 
    done0           <= NO;
 
    done1           <= done;
 
    rdDone0         <= NO;
 
    rdDone1         <= rdDone;
 
 end if;
 
 
  -- both ports get the data from the SDRAM but only the active port will use it
  -- both ports get the data from the SDRAM but only the active port will use it
  hDOut0 <= hDOut;
  hDOut0 <= hDOut;
  hDOut1 <= hDOut;
  hDOut1 <= hDOut;
 
 
  -- send the SDRAM controller status to the active port and give the inactive port an inactive status code
 
  status0 <= status when port_r = PORT0 else "1111";
 
  status1 <= status when port_r = PORT1 else "1111";
 
 
 
  -- either port can reset the SDRAM controller
  -- either port can reset the SDRAM controller
  rst <= rst0 or rst1;
  rst <= rst0 or rst1;
 
 
  -- apply the read signal from the active port to the SDRAM controller only if the door is open.
 
  rd_i <= rd0 when (port_r = PORT0) and (door_r = OPENED) else
 
          rd1 when (port_r = PORT1) and (door_r = OPENED) else
 
          NO;
 
  rd   <= rd_i;
  rd   <= rd_i;
 
 
  -- apply the write signal from the active port to the SDRAM controller only if the door is open.
 
  wr_i <= wr0 when (port_r = PORT0) and (door_r = OPENED) else
 
          wr1 when (port_r = PORT1) and (door_r = OPENED) else
 
          NO;
 
  wr   <= wr_i;
  wr   <= wr_i;
 
 
  -- send the status signals for various SDRAM controller operations back to the active port
 
  earlyOpBegun0_i <= earlyOpBegun when port_r = PORT0 else NO;
 
  earlyOpBegun0   <= earlyOpBegun0_i;
 
  earlyOpBegun1_i <= earlyOpBegun when port_r = PORT1 else NO;
 
  earlyOpBegun1   <= earlyOpBegun1_i;
 
  rdPending0      <= rdPending    when port_r = PORT0 else NO;
 
  rdPending1      <= rdPending    when port_r = PORT1 else NO;
 
  done0           <= done         when port_r = PORT0 else NO;
 
  done1           <= done         when port_r = PORT1 else NO;
 
  rdDone0         <= rdDone       when port_r = PORT0 else NO;
 
  rdDone1         <= rdDone       when port_r = PORT1 else NO;
 
 
 
  ----------------------------------------------------------------------------
  ----------------------------------------------------------------------------
  -- Indicate when the active port needs to be switched.  A switch occurs if
  -- Indicate when the active port needs to be switched.  A switch occurs if
  -- a read or write operation is requested on the port that is not currently active and:
  -- a read or write operation is requested on the port that is not currently active and:
  -- 1) no R/W operation is being performed on the active port or 
  -- 1) no R/W operation is being performed on the active port or 
  -- 2) a R/W operation is in progress on the active port, but the time-slot allocation 
  -- 2) a R/W operation is in progress on the active port, but the time-slot allocation 
  --    register is giving precedence to the inactive port.  (The R/W operation on the
  --    register is giving precedence to the inactive port.  (The R/W operation on the
  --    active port will be completed before the switch is made.)
  --    active port will be completed before the switch is made.)
  -- This rule keeps the active port from hogging all the bandwidth.
  -- This rule keeps the active port from hogging all the bandwidth.
  ----------------------------------------------------------------------------
  ----------------------------------------------------------------------------
  switch <= (rd0 or wr0) when (port_r = PORT1) and (((rd1 = NO) and (wr1 = NO)) or (slot_r(0) = '0')) else
 
            (rd1 or wr1) when (port_r = PORT0) and (((rd0 = NO) and (wr0 = NO)) or (slot_r(0) = '1')) else
  if port_r = PORT0 then
            NO;
    if (((rd0 = NO) and (wr0 = NO)) or (slot_r(0) = '1')) then
 
      switch <= (rd1 or wr1);
 
    else
 
      switch <= NO;
 
    end if;
 
  else
 
    if (((rd1 = NO) and (wr1 = NO)) or (slot_r(0) = '0')) then
 
      switch <= (rd0 or wr0);
 
    else
 
           switch  <= NO;
 
    end if;
 
  end if;
 
 
 
  -- send the status signals for various SDRAM controller operations back to the active port
 
  earlyOpBegun0   <= earlyOpBegun0_i;
 
  earlyOpBegun1   <= earlyOpBegun1_i;
 
 
  ----------------------------------------------------------------------------
  ----------------------------------------------------------------------------
  -- Indicate when an operation on the active port is in-progress and
  -- Indicate when an operation on the active port is in-progress and
  -- can't be interrupted by a switch to the other port.  (Only read operations
  -- can't be interrupted by a switch to the other port.  (Only read operations
  -- are looked at since write operations always complete in one cycle once they
  -- are looked at since write operations always complete in one cycle once they
Line 939... Line 1058...
  -- 3) the currently active port matches the port that currently has priority.
  -- 3) the currently active port matches the port that currently has priority.
  -- Under these conditions, the current time slot port allocation has been used so
  -- Under these conditions, the current time slot port allocation has been used so
  -- the shift register is rotated right to bring the next port time-slot allocation
  -- the shift register is rotated right to bring the next port time-slot allocation
  -- bit into play.
  -- bit into play.
  ----------------------------------------------------------------------------
  ----------------------------------------------------------------------------
  slot_x <= slot_r(0) & slot_r(slot_r'high downto 1) when (earlyOpBegun = YES) and
  if (earlyOpBegun = YES) and
            ( ((rd0 = YES) or (wr0 = YES)) and ((rd1 = YES) or (wr1 = YES)) ) and
            ( ((rd0 = YES) or (wr0 = YES)) and ((rd1 = YES) or (wr1 = YES)) ) and
            ( ((port_r = PORT0) and (slot_r(0) = '0')) or ((port_r = PORT1) and (slot_r(0) = '1')) )
     ( ((port_r = PORT0) and (slot_r(0) = '0')) or ((port_r = PORT1) and (slot_r(0) = '1')) ) then
            else slot_r;
    slot_x <= slot_r(0) & slot_r(slot_r'high downto 1);
 
  else
 
    slot_x <= slot_r;
 
  end if;
 
 
 
end process;
 
 
  ----------------------------------------------------------------------------
  ----------------------------------------------------------------------------
  -- Determine which port will be active on the next cycle.  The active port is switched if:
  -- Determine which port will be active on the next cycle.  The active port is switched if:
  -- 1) the currently active port has finished its current R/W operation, and
  -- 1) the currently active port has finished its current R/W operation, and
  -- 2) there are no pending operations in progress, and
  -- 2) there are no pending operations in progress, and

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.