⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mmuconfig.vhd

📁 sparc org, vhdl rtl code
💻 VHD
📖 第 1 页 / 共 2 页
字号:

constant FS_FT_U : integer := 4;
constant FS_FT_D : integer := 2;
constant FS_FT_NONE : std_logic_vector(2 downto 0) := "000";
constant FS_FT_INV : std_logic_vector(2 downto 0)  := "001";
constant FS_FT_PRO : std_logic_vector(2 downto 0)  := "010";
constant FS_FT_PRI : std_logic_vector(2 downto 0)  := "011";
constant FS_FT_TRANS : std_logic_vector(2 downto 0):= "110";
constant FS_FT_BUS : std_logic_vector(2 downto 0)  := "101";
constant FS_FT_INT : std_logic_vector(2 downto 0)  := "110";
constant FS_FT_RVD : std_logic_vector(2 downto 0)  := "111";

constant FS_FAV : natural := 1;
constant FS_OW : natural := 0;

--# mmu ctrl reg
type mmctrl_type1 is record
  e       : std_logic;				        -- enable
  nf      : std_logic;				        -- no fault
  pso     : std_logic;				        -- partial store order
--  pre     : std_logic;                            -- pretranslation source
--  pri     : std_logic;                            -- i/d priority 
  ctx     : std_logic_vector(M_CTX_SZ-1 downto 0);-- context nr
  ctxp    : std_logic_vector(MMCTRL_CTXP_SZ-1 downto 0);  -- context table pointer
  tlbdis  : std_logic;                            -- tlb disabled
  bar     : std_logic_vector(1 downto 0);         -- preplace barrier
end record;

--# fault status reg
type mmctrl_fs_type is record
  ow    : std_logic;				  
  fav   : std_logic;				  
  ft    : std_logic_vector(2 downto 0);	          -- fault type
  at_ls : std_logic;                              -- access type, load/store
  at_id : std_logic;                              -- access type, i/dcache
  at_su : std_logic;                              -- access type, su/user
  l     : std_logic_vector(1 downto 0);           -- level 
  ebe   : std_logic_vector(7 downto 0);            
end record;

type mmctrl_type2 is record
  fs    : mmctrl_fs_type;
  valid : std_logic;
  fa    : std_logic_vector(VA_I_SZ-1 downto 0);   -- fault address register
end record;

-- ##############################################################
--     6. Virtual Flush/Probe address [sparc V8: p.249,Appx.H,Figure H-9]
--     +---------------------------------------+--------+-------+
--     |   VIRTUAL FLUSH&Probe Address (VFPA)  |  type  |  rvd  |      
--     +---------------------------------------+--------+-------+  
--      31                                   12 11     8 7      0         
--     
--
subtype FPA is natural range  31 downto 12;
constant FPA_I1_U : integer := 31;
constant FPA_I1_D : integer := 24;
constant FPA_I2_U : integer := 23;
constant FPA_I2_D : integer := 18;
constant FPA_I3_U : integer := 17;
constant FPA_I3_D : integer := 12;
constant FPTY_U : integer := 10;        -- only 3 bits
constant FPTY_D : integer := 8;

-- ##############################################################
--     7. control register virtual address [sparc V8: p.253,Appx.H,Table H-5] 
--     +---------------------------------+-----+--------+
--     |                                 | CNR |  rsvd  |      
--     +---------------------------------+-----+--------+  
--      31                                10  8 7      0
      
constant CNR_U        : integer := 10;
constant CNR_D        : integer := 8;    
constant CNR_CTRL     : std_logic_vector(2 downto 0) := "000";
constant CNR_CTXP     : std_logic_vector(2 downto 0) := "001";
constant CNR_CTX      : std_logic_vector(2 downto 0) := "010";
constant CNR_F        : std_logic_vector(2 downto 0) := "011";
constant CNR_FADDR    : std_logic_vector(2 downto 0) := "100";

-- ##############################################################
--     8. Precise flush (ASI 0x10-14) [sparc V8: p.266,Appx.I]
--        supported: ASI_FLUSH_PAGE
--                   ASI_FLUSH_CTX
                     
constant PFLUSH_PAGE : std_logic := '0';
constant PFLUSH_CTX  : std_logic := '1';

-- ##############################################################
--     9. Diagnostic access
--        
constant DIAGF_LVL_U : integer := 1;
constant DIAGF_LVL_D : integer := 0;
constant DIAGF_WR    : integer := 3;
constant DIAGF_HIT   : integer := 4;
constant DIAGF_CTX_U : integer := 12;
constant DIAGF_CTX_D : integer := 5;
constant DIAGF_VALID : integer := 13;
end mmuconfig;                          



-- Konrad Eisele<eiselekd@web.de> ,2002  

library ieee;
use ieee.std_logic_1164.all;
use IEEE.std_logic_arith.all;
use work.mmuconfig.all;

package mmulib is
  
  function TLB_CreateCamWrite( two_data  : std_logic_vector(31 downto 0);
                               read      : std_logic;
                               lvl       : std_logic_vector(1 downto 0);
                               ctx       : std_logic_vector(M_CTX_SZ-1 downto 0);
                               vaddr     : std_logic_vector(31 downto 0)
                               ) return tlbcam_reg;
  
  procedure TLB_CheckFault( ACC        : in  std_logic_vector(2 downto 0);
                            isid       : in  mmu_idcache;
                            su         : in  std_logic;
                            read       : in  std_logic;
                            fault_pro  : out std_logic;
                            fault_pri  : out std_logic );

  procedure TLB_MergeData( LVL         : in  std_logic_vector(1 downto 0);
                           PTE         : in  std_logic_vector(31 downto 0);
                           data        : in  std_logic_vector(31 downto 0);
                           transdata   : out std_logic_vector(31 downto 0));

  function TLB_CreateCamTrans( vaddr     : std_logic_vector(31 downto 0);
                               read      : std_logic;
                               ctx       : std_logic_vector(M_CTX_SZ-1 downto 0)
                             ) return tlbcam_tfp;

  function TLB_CreateCamFlush( data      : std_logic_vector(31 downto 0);
                               ctx       : std_logic_vector(M_CTX_SZ-1 downto 0)
                             ) return tlbcam_tfp;
  
end;

package body mmulib is

procedure TLB_CheckFault( ACC        : in  std_logic_vector(2 downto 0);
                          isid       : in  mmu_idcache;
                          su         : in  std_logic;
                          read       : in  std_logic;
                          fault_pro  : out std_logic;
                          fault_pri  : out std_logic ) is
variable c_isd    : std_logic;
begin
  fault_pro := '0';
  fault_pri := '0';
  
  -- use '0' == icache '1' == dcache
  if isid = id_icache then
    c_isd := '0';
  else
    c_isd := '1';
  end if;
  --# fault, todo: should we flush on a fault?
  case ACC is
    when "000" => fault_pro := (not c_isd) or (not read);    
    when "001" => fault_pro := (not c_isd);
    when "010" => fault_pro := (not read);
    when "011" => null;
    when "100" => fault_pro := (c_isd);
    when "101" => fault_pro := (not c_isd) or ((not read) and (not su));
    when "110" => fault_pri := (not su);
                  fault_pro := (not read);
    when "111" => fault_pri := (not su);
    when others => null;
  end case;
end;
 
procedure TLB_MergeData( LVL         : in  std_logic_vector(1 downto 0);
                         PTE         : in  std_logic_vector(31 downto 0);
                         data        : in  std_logic_vector(31 downto 0);
                         transdata   : out std_logic_vector(31 downto 0) ) is
begin 

  --# merge data
  transdata := (others => '0');
  case LVL is
    when LVL_PAGE    => transdata := PTE(PTE_PPN32PAG_U downto PTE_PPN32PAG_D) & data(VA_OFFPAG_U downto VA_OFFPAG_D);
    when LVL_SEGMENT => transdata := PTE(PTE_PPN32SEG_U downto PTE_PPN32SEG_D) & data(VA_OFFSEG_U downto VA_OFFSEG_D);
    when LVL_REGION  => transdata := PTE(PTE_PPN32REG_U downto PTE_PPN32REG_D) & data(VA_OFFREG_U downto VA_OFFREG_D);
    when LVL_CTX     => transdata :=                                             data(VA_OFFCTX_U downto VA_OFFCTX_D);
    when others      => transdata := (others => 'X');
  end case;
end;

function TLB_CreateCamWrite( two_data  : std_logic_vector(31 downto 0);
                             read      : std_logic;
                             lvl       : std_logic_vector(1 downto 0);
                             ctx       : std_logic_vector(M_CTX_SZ-1 downto 0);
                             vaddr     : std_logic_vector(31 downto 0)
                             ) return tlbcam_reg is
variable tlbcam_tagwrite      : tlbcam_reg;
begin

    tlbcam_tagwrite.ET    := two_data(PT_ET_U downto PT_ET_D);
    tlbcam_tagwrite.ACC   := two_data(PTE_ACC_U downto PTE_ACC_D);
    tlbcam_tagwrite.M     := two_data(PTE_M) or (not read); -- tw : p-update modified
    tlbcam_tagwrite.R     := '1';                         
    case tlbcam_tagwrite.ACC is      -- tw : p-su ACC >= 6
      when "110" | "111" => tlbcam_tagwrite.SU := '1';
      when others =>        tlbcam_tagwrite.SU := '0';
    end case;
    tlbcam_tagwrite.VALID := '1';
    tlbcam_tagwrite.LVL   := lvl;
    tlbcam_tagwrite.I1    := vaddr(VA_I1_U downto VA_I1_D);
    tlbcam_tagwrite.I2    := vaddr(VA_I2_U downto VA_I2_D);
    tlbcam_tagwrite.I3    := vaddr(VA_I3_U downto VA_I3_D);
    tlbcam_tagwrite.CTX   := ctx;
    tlbcam_tagwrite.PPN   := two_data(PTE_PPN_U downto PTE_PPN_D);
    tlbcam_tagwrite.C     := two_data(PTE_C);
    return tlbcam_tagwrite;
end;

function TLB_CreateCamTrans( vaddr     : std_logic_vector(31 downto 0);
                             read      : std_logic;
                             ctx       : std_logic_vector(M_CTX_SZ-1 downto 0)
                             ) return tlbcam_tfp is
variable mtag            : tlbcam_tfp;
begin
    mtag.TYP := (others => '0');
    mtag.I1 := vaddr(VA_I1_U downto VA_I1_D);
    mtag.I2 := vaddr(VA_I2_U downto VA_I2_D);
    mtag.I3 := vaddr(VA_I3_U downto VA_I3_D);
    mtag.CTX :=  ctx;
    mtag.M :=  not (read);
    return mtag;
end;

function TLB_CreateCamFlush( data      : std_logic_vector(31 downto 0);
                             ctx       : std_logic_vector(M_CTX_SZ-1 downto 0)
                             ) return tlbcam_tfp is
variable ftag            : tlbcam_tfp;
begin
    ftag.TYP := data(FPTY_U downto FPTY_D);
    ftag.I1  := data(FPA_I1_U downto FPA_I1_D);
    ftag.I2  := data(FPA_I2_U downto FPA_I2_D);
    ftag.I3  := data(FPA_I3_U downto FPA_I3_D);
    ftag.CTX :=  ctx;
    ftag.M   := '0';
    return ftag;
end;

end;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -