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

📄 icache.vhd

📁 一个航天航空用的Sparc处理器(配美国欧洲宇航局用的R_tems嵌入式操作系统)的VHDL源代码
💻 VHD
📖 第 1 页 / 共 2 页
字号:
	(r.mds or not r.write) and 
	(r.mds or r.write or not (cacheon and hit and dvalid));
      if ((r.overrun and not v.overrun) = '1') then
        taddr := ici.fpc(TAG_HIGH downto LINE_LOW);
      end if;
      if (dco.hold and not (ici.nullify and not v.overrun)) = '1' then
	if not ((cacheon and hit and dvalid) = '1') then  
	  v.istate := 1; v.req := '1';

          v.burst := '0';
 	  if r.overrun = '1' then
	    if v.overrun = '0' then
	      if lastline /= '1' then v.burst := mcio.burst; end if;
            else
	      if (ici.branch = '0') and (xlastline /= '1') then
	        v.burst := mcio.burst; 
	      end if;
	    end if;
	  else
	    if lastline /= '1' then v.burst := mcio.burst; end if;
          end if;
--	  v.burst := mcio.burst and 
--		not ((r.overrun and ici.branch and r.mds) or lastline);
        end if;
      end if;
      if dco.icdiag.enable = '1' then
	diagen := '1';
      end if;
      if (dco.hold and cacheon and 
	 ((not ici.nullify) or ((not r.mds) and (not r.write)))) = '1' then
	v.tparerr := tparerr and cacheon and cachable;
	v.dparerr := dparerr and cacheon and cachable and hit and valid;
      end if;
      v.holdn := not v.overrun; v.branch := '0';
      if (r.overrun and v.overrun) = '0' then
        v.waddress := ici.fpc(31 downto LINE_LOW);
      else
        v.waddress := r.xaddress(31 downto LINE_LOW);
      end if;
      ddatain := dci.maddress;
    when 1 =>		-- streaming: update cache and send data to IU
      rdatasel := memory;
      v.overrun := ((r.overrun or 
	(r.write and ici.branch and (not ici.nullify) and dco.hold) or
	((not r.write) and (not ici.nullify) and dco.hold)) and r.mds)
	or (r.underrun and (not ici.nullify) and dco.hold);
      v.underrun := r.underrun or 
           (r.write and dco.hold and ici.nullify and r.mds and not v.overrun);
      if ((not r.overrun) and dco.hold and not ici.nullify) = '1' then
	v.branch := ici.branch;
      end if;
      if mcio.ready = '1' then
	v.mds := not v.overrun or (ici.branch and not r.overrun) or 
		(r.branch and r.overrun) or r.underrun; 
	v.req := r.burst; 
	v.burst := (r.burst and not (nlastline or (r.write and nnlastline)));
	if ((v.overrun and v.branch) or (v.underrun and not cacheon)) = '1' then
	  v.burst := '0';
	end if;
      end if;
      if ((not r.req) or 
	   ((v.underrun or v.overrun) and (not cacheon) and not v.req)) = '1'
      then
	v.underrun := '0';
	if (cacheon = '1') or ((r.flush and not r.flush2) = '1') then
	  v.istate := 2;
	else
          v.istate := 0; v.flush := r.flush2;
	end if;
      end if;
      taddr(TAG_HIGH downto LINE_LOW) := r.waddress(TAG_HIGH downto LINE_LOW);
      v.holdn := not v.overrun;

    when 2 => 		-- return to main witout overrun
      rdatasel := memory; 
      v.overrun := (r.overrun or 
	(r.write and ici.branch and (not ici.nullify) and dco.hold) or
	((not r.write) and (not ici.nullify) and dco.hold)) and r.mds;

      if r.overrun = '1' then
        taddr := r.xaddress(TAG_HIGH downto LINE_LOW);
      elsif ici.nullify = '0' then
        taddr := ici.fpc(TAG_HIGH downto LINE_LOW);
      else
        taddr := ici.rpc(TAG_HIGH downto LINE_LOW);
      end if;
      v.istate := 0; v.flush := r.flush2; v.mds := not v.overrun;
      v.holdn := not v.overrun;

    when others => null;
    end case;

-- Generate new valid bits write strobe

    vmaskraw := decode(r.waddress(LINE_HIGH downto LINE_LOW));
    if (r.waddress(31) = '0') and (r.waddress(30 downto 29) /= "01") then
      wcachable := '1';
    else wcachable := '0'; end if;
    if (icramo.itramout.tag = r.waddress(TAG_HIGH downto TAG_LOW)) then 
      whit := '1'; 
    else whit := '0'; end if;
    twrite := r.write;
    if (mcio.ics = "00") or (r.flush = '1') then
      twrite := '0'; vmask := (others => '0');
    elsif (mcio.ics = "01") then
      twrite := twrite and (wcachable and whit);
      vmask := icramo.itramout.valid or vmaskraw;
    else
      twrite := twrite and wcachable;
      if whit = '1' then vmask := icramo.itramout.valid or vmaskraw;
      else vmask := vmaskraw; end if;
    end if; 
    if mcio.mexc = '1' then vmask := vmask and not vmaskraw; dwrite := '0';
    else dwrite := twrite; end if;


-- diagnostic cache access

    diagdata := icramo.idramout.data;
    if diagen = '1' then -- diagnostic access
      taddr(OFFSET_HIGH downto LINE_LOW) := 
	dco.icdiag.addr(OFFSET_HIGH downto LINE_LOW);
      wtag := dco.icdiag.addr(TAG_HIGH downto TAG_LOW);
      if dco.icdiag.tag = '1' then
	twrite := not dco.icdiag.read; dwrite := '0';
        diagdata := (others => '0');
        diagdata(31) := icramo.itramout.parity;
        diagdata(8) := icramo.idramout.parity;
        diagdata(TAG_HIGH downto TAG_LOW) := icramo.itramout.tag;
        diagdata(ILINE_SIZE -1 downto 0) := icramo.itramout.valid;
      else
	dwrite := not dco.icdiag.read; twrite := '0';
      end if;
      vmask := dci.maddress(ILINE_SIZE -1 downto 0);
--      ddatain := dci.maddress;
      diagrdy := '1';
    end if;

-- select data to return on read access

    case rdatasel is
    when memory => rdata := mcio.data;
    when others => rdata := icramo.idramout.data;
    end case;

-- cache flush

    if (ici.flush or dco.icdiag.flush) = '1' then
      v.flush := '1'; v.flush2 := '1'; v.faddr := (others => '0');
    end if;

    if r.flush2 = '1' then
      twrite := '1'; vmask := (others => '0'); v.faddr := r.faddr +1; 
      taddr(OFFSET_HIGH downto OFFSET_LOW) := r.faddr;
      if (r.faddr(IOFFSET_BITS -1) and not v.faddr(IOFFSET_BITS -1)) = '1' then
	v.flush2 := '0';
      end if;
    end if;

-- parity generation

    tparin := '0';
    v.tapar := '0';
    if ITAGPAR then
      v.tapar := xorv(taddr(OFFSET_HIGH downto OFFSET_LOW)) and ITAGAPAR;
      tparin := xorv(wtag & vmask & v.tapar & (diagen and dco.icdiag.addr(31)));
    end if;

    dparin := '0';
    v.dapar := '0';
    if DDATPAR then
      v.dapar := xorv(taddr(OFFSET_HIGH downto LINE_LOW)) and IDATAPAR;
      dparin := xorv(ddatain & v.dapar & (diagen and dco.icdiag.addr(31)));
    else
      dparin := '0';
    end if;

-- reset

    if rst = '0' then 
      v.istate := 0; v.req := '0'; v.burst := '0'; v.holdn := '1';
      v.flush := '0'; v.flush2 := '0';
      v.overrun := '0'; v.branch := '0'; v.underrun := '0';
    end if;

-- Drive signals

    c <= v;	-- register inputs

    -- tag ram inputs
    icrami.itramin.valid    <= vmask;
    icrami.itramin.tag      <= wtag;
    icrami.itramin.enable   <= enable;
    icrami.itramin.write    <= twrite;
    icrami.itramin.parity   <= tparin;

    -- data ram inputs
    icrami.idramin.enable   <= enable;
    icrami.idramin.address  <= taddr(OFFSET_HIGH downto LINE_LOW);
    icrami.idramin.data     <= ddatain;
    icrami.idramin.write    <= dwrite;
    icrami.idramin.parity   <= dparin;

    -- memory controller inputs
    mcii.address(31 downto LINE_LOW)  <= r.waddress;
    mcii.address(1 downto 0)  <= "00";
    mcii.su       <= r.su;
    mcii.burst    <= r.burst;
    mcii.req      <= r.req;
    mcii.tparerr  <= r.tparerr;
    mcii.dparerr  <= r.dparerr;
    mcii.flush    <= r.flush;

    -- IU data cache inputs
    ico.data      <= rdata;
    ico.exception <= mcio.mexc or error;
    ico.hold      <= r.holdn;
    ico.mds       <= r.mds;
    ico.flush     <= r.flush;
    ico.diagdata  <= diagdata;
    ico.diagrdy   <= diagrdy;

  end process;

-- Local registers

  dlat : process(clk)
  begin
    if clk'event and (clk='1') then
      r <= c;
    end if;
  end process;

end ;

⌨️ 快捷键说明

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