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

📄 pci_mt.vhd

📁 free hardware ip core about sparcv8,a soc cpu in vhdl
💻 VHD
📖 第 1 页 / 共 2 页
字号:
    v.hreq_ack(0) := r.hreq_ack(csync); v.hreq_ack(csync) := r2.hreq_ack;    comp := '0'; mto := '0'; tad := r.ad; mad := r.ad; v.stop_req := '0';    --cbe := r.cbe;----- *** PCI TARGET *** ---------- address decoding    if (r.t_state = s_data) and ((pr.irdy or r.trdy or r.read) = '0') then      cwrite := r.csel;      if ((r.msel and r.addr(MADDR_WIDTH-1)) = '1') and (pr.cbe = "0000") then        v.page := pr.ad(31 downto MADDR_WIDTH-1);      end if;      if (pr.cbe = "0000") and  (r.addr(MADDR_WIDTH-1) = '1') then      end if;    else cwrite := '0'; end if;    cdata := (others => '0'); caddr :=  r.addr(7 downto 2);    case caddr is    when "000000" =>			-- 0x00, device & vendor id      cdata := conv_std_logic_vector(DEVICE_ID, 16) &      conv_std_logic_vector(VENDOR_ID, 16);    when "000001" =>			-- 0x04, status & command      cdata(1) := r.comm.men; cdata(2) := r.comm.msen; cdata(25) := '1';      cdata(28) := r.stat.rta; cdata(29) := r.stat.rma;    when "000010" =>			-- 0x08, class code & revision    when "000011" =>			-- 0x0c, latency & cacheline size    when "000100" =>			-- 0x10, BAR0      cdata(31 downto MADDR_WIDTH) := r.bar0;    when others =>    end case;    cwdata := pr.ad;    if pr.cbe(3) = '1' then cwdata(31 downto 24) := cdata(31 downto 24); end if;    if pr.cbe(2) = '1' then cwdata(23 downto 16) := cdata(23 downto 16); end if;    if pr.cbe(1) = '1' then cwdata(15 downto  8) := cdata(15 downto  8); end if;    if pr.cbe(0) = '1' then cwdata( 7 downto  0) := cdata( 7 downto  0); end if;    if cwrite = '1' then      case caddr is      when "000001" =>			-- 0x04, status & command        v.comm.men := cwdata(1);        v.comm.msen := cwdata(2);        v.stat.rta := r.stat.rta and not cwdata(28);        v.stat.rma := r.stat.rma and not cwdata(29);      when "000100" =>			-- 0x10, BAR0        v.bar0 := cwdata(31 downto MADDR_WIDTH);      when others =>      end case;    end if;    if (((pr.cbe = pci_config_read) or (pr.cbe = pci_config_write))    and (pr.ad(1 downto 0) = "00"))    then chit := '1'; else chit := '0'; end if;    if ((pr.cbe = pci_memory_read) or (pr.cbe = pci_memory_write))  and (r.bar0 = pr.ad(31 downto MADDR_WIDTH))  and (r.bar0 /= zero(31 downto MADDR_WIDTH))    then mhit := '1'; else mhit := '0'; end if;    hit := r.csel or r.msel;    ready := r.csel or (r.rready(0) and r.read) or (r.wready(0) and not r.read and not r.start) or   r.addr(MADDR_WIDTH-1);-- target state machine    case r.t_state is    when idle  =>      if pr.frame = '0' then v.t_state := b_busy; end if; -- !HIT ?      v.addr := pr.ad(MADDR_WIDTH-1 downto 0); -- v.cbe := pr.cbe;      v.csel := pr.idsel and chit;      v.msel := r.comm.men and mhit; v.read := not pr.cbe(0);      if (r.sync(0) and r.start and r.pwrite)  = '1' then v.start := '0'; end if;    when turn_ar =>      if pr.frame = '1' then v.t_state := idle; end if;      if pr.frame = '0' then v.t_state := b_busy; end if; -- !HIT ?      v.addr := pr.ad(MADDR_WIDTH-1 downto 0); -- v.cbe := pr.cbe;      v.csel := pr.idsel and chit;      v.msel := r.comm.men and mhit; v.read := not pr.cbe(0);      if (r.sync(0) and r.start and r.pwrite)  = '1' then v.start := '0'; end if;    when b_busy  =>      if hit = '1' then        v.t_state := s_data; v.trdy := not ready; v.stop := pr.frame and ready;        v.devsel := '0';      else        v.t_state := backoff;      end if;    when s_data  =>      v.stop := r.stop; v.devsel := '0';      v.trdy := r.trdy or not pcii.irdy;      if (pcii.frame and not pcii.irdy) = '1' then        v.t_state := turn_ar; v.stop := '1'; v.trdy := '1'; v.devsel := '1';      end if;    when backoff =>      if pr.frame = '1' then v.t_state := idle; end if;    end case;    if ((r.t_state = s_data) or (r.t_state = turn_ar)) and       (((pr.irdy or pr.trdy) = '0') or        ((not pr.irdy and not pr.stop and pr.trdy and not r.start and r.wready(0)) = '1'))    then      if (pr.trdy and r.read)= '0' then v.start := '0'; end if;      if (r.start = '0') and ((r.msel and not r.addr(MADDR_WIDTH-1)) = '1') and      (((pr.trdy and r.read and not r.rready(0)) or (not pr.trdy and not r.read)) = '1')      then        v.laddr := r.page & r.addr(MADDR_WIDTH-2 downto 0);        v.ldata := pr.ad; v.pwrite := not r.read; v.start := '1';      end if;    end if;--    if (v.t_state = s_data) and (r.read = '1') then v.oe_ad := '0'; end if;--    v.oe_par := r.oe_ad;    if r.csel = '1' then tad := cdata;    elsif r.addr(MADDR_WIDTH-1) = '1' then      tad(31 downto MADDR_WIDTH-1) := r.page;      tad(MADDR_WIDTH-2 downto 0) := (others => '0');    else tad := r2.tdata; end if;    if (v.t_state = s_data) or (r.t_state = s_data) then      v.oe_ctrl := '0';    else v.oe_ctrl := '1'; end if;----- *** PCI TARGET END*** ------------- *** PCI MASTER *** --------  if MASTER = 1 then    if r.preq(0) = '1' then          if (r.m_state = idle or r.m_state = dr_bus) and r.request = '0' and r.hreq = '0' then        v.request := '1';        v.hwrite := r2.hwrite;        v.lcbe := r2.be;        v.mdata := r2.mdata;        v.maddr :=r2.maddr;      end if;    end if;    if r.hreq_ack(0) = '1' then v.hreq := '0'; v.pabort := '0'; end if;    if r.preq(0) = '0' then v.preq_ack := '0'; end if;    comp := not(pcii.trdy or pcii.irdy);    if ((pr.irdy and not pr.frame) or (pr.devsel and r.frame and not r.oe_frame)) = '1' then -- Covers both master timeout and devsel timeout      if r.mcnt /= "000" then v.mcnt := r.mcnt - 1;      else mto := '1'; end if;    else v.mcnt := (others => '1'); end if;    -- PCI master state machine    case r.m_state is    when idle => -- Master idle      if (pr.gnt = '0' and (pr.frame and pr.irdy) = '1') then        if r.request = '1' then v.m_state := addr; v.preq_ack := '1';        else v.m_state := dr_bus; end if;      end if;    when addr => -- Always one address cycle at the beginning of an transaction      v.m_state := m_data;    when m_data => -- Master transfers data        --if (r.request and not pr.gnt and pr.frame and not pr.trdy -- Not supporting address stepping!        --and pr.stop and l_cycle and sa) = '1' then        --v.m_state <= addr;      v.hreq := comp;      if (pr.frame = '0') or ((pr.frame and pcii.trdy and pcii.stop and not mto) = '1') then        v.m_state := m_data;      elsif ((pr.frame and (mto or not pcii.stop)) = '1') then        v.m_state := s_tar;      else v.m_state := turn_ar; v.request := '0'; end if;    when turn_ar => -- Transaction complete      if (r.request and not pr.gnt) = '1' then v.m_state := addr;      elsif (r.request or pr.gnt) = '0' then v.m_state := dr_bus;      else v.m_state := idle; end if;    when s_tar => -- Stop was asserted      v.request := pr.trdy and not pr.stop and not pr.devsel;      v.stop_req := '1';      if (pr.stop or pr.devsel or pr.trdy) = '0' then -- Disconnect with data        v.m_state := turn_ar;      elsif pr.gnt = '0' then        v.pabort := not v.request;        v.m_state := dr_bus;      else v.m_state := idle; v.pabort := not v.request; end if;    when dr_bus => -- Drive bus when parked on this agent      if (r.request = '1' and (pcii.gnt or r.req) = '0') then v.m_state := addr; v.preq_ack := '1';      elsif pcii.gnt = '1' then v.m_state := idle; end if;    end case;    if v.m_state = addr then mad := r.maddr; else mad := r.mdata; end if;    if (pr.irdy or pr.trdy or r.hwrite) = '0'  then v.ldata := pr.ad; end if;    -- Target abort    if ((pr.devsel and pr.trdy and not pr.gnt and not pr.stop) = '1') then v.stat.rta := '1'; end if;    -- Master abort    if mto = '1' then v.stat.rma := '1'; end if;    -- Drive FRAME# and IRDY#    if (v.m_state = addr or v.m_state = m_data) then v.oe_frame := '0'; end if;    -- Drive CBE#    if (v.m_state = addr or v.m_state = m_data or v.m_state = dr_bus) then v.oe_cbe := '0'; end if;    -- Drive IRDY# (FRAME# delayed one pciclk)    v.oe_irdy := r.oe_frame;    -- FRAME# assert      if v.m_state = addr then v.frame := '0'; end if; -- Only single transfers valid    -- IRDY# assert    if v.m_state = m_data then v.irdy := '0'; end if;    -- REQ# assert    if (v.request = '1' and (v.m_state = idle or r.m_state = idle) and (v.stop_req or r.stop_req) = '0') then v.req := '0'; end if;    -- C/BE# assert    if v.m_state = addr then v.cbe := "011" & r.hwrite; else v.cbe := r.lcbe; end if;  end if;----- *** PCI MASTER END *** ------------- *** SHARED BUS SIGNALS *** -------    -- Drive PAR    v.oe_par := r.oe_ad; --Delayed one clock    v.par := xorv(r.ad & r.cbe); -- Default asserted by master    v.ad := mad;  -- Default asserted by master    -- Master    if (v.m_state = addr or (v.m_state = m_data and r.hwrite = '1') or v.m_state = dr_bus) then      v.oe_ad := '0';    end if;    -- Drive AD    -- Target    if r.read = '1' then      if v.t_state = s_data then        v.oe_ad := '0';        v.ad := tad;      elsif r.t_state = s_data then        v.par := xorv(r.ad & pcii.cbe);      end if;    end if;    v.oe_stop := v.oe_ctrl; v.oe_devsel := v.oe_ctrl; v.oe_trdy := v.oe_ctrl;    v.noe_ad := not v.oe_ad; v.noe_ctrl := not v.oe_ctrl;    v.noe_par := not v.oe_par; v.noe_req := not v.oe_req;    v.noe_frame := not v.oe_frame; v.noe_cbe := not v.oe_cbe;    v.noe_irdy := not v.oe_irdy;     v.noe_stop := not v.oe_ctrl; v.noe_devsel := not v.oe_ctrl;     v.noe_trdy := not v.oe_ctrl;      if oepol  = 0 then      voe_ad := (others => v.oe_ad);        oe_ad := r.oe_ad; oe_ctrl := r.oe_ctrl; oe_par := r.oe_par;      oe_req := r.oe_req; oe_frame := r.oe_frame; oe_cbe := r.oe_cbe;      oe_irdy := r.oe_irdy; oe_stop := r.oe_stop; oe_trdy := r.oe_trdy;      oe_devsel := r.oe_devsel;     else      voe_ad := (others => v.noe_ad);        oe_ad := r.noe_ad; oe_ctrl := r.noe_ctrl; oe_par := r.noe_par;      oe_req := r.noe_req; oe_frame := r.noe_frame; oe_cbe := r.noe_cbe;      oe_irdy := r.noe_irdy; oe_stop := r.noe_stop; oe_trdy := r.noe_trdy;      oe_devsel := r.noe_devsel;    end if;  ----- *** SHARED BUS SIGNALS END *** -------    if pr.rst = '0' then      v.t_state := idle; v.m_state := idle; v.comm.men := '0'; v.start := '0';      v.bar0 := (others => '0'); v.msel := '0'; v.csel := '0';      v.page := (others => '0'); v.page(31 downto 30) := "01"; v.par := '0';      v.hwrite := '0'; v.request := '0'; v.comm.msen := '0';      v.laddr := (others => '0'); v.ldata := (others => '0');      v.hreq := '0'; v.preq_ack := '0'; v.pabort := '0';      v.mcnt := (others => '1'); v.maddr := (others => '0');      v.lcbe := (others => '0'); v.mdata := (others => '0');      v.pwrite := '0'; v.stop_req := '0';      v.stat.rta := '0'; v.stat.rma := '0';    end if;    rin <= v;    rioe_ad <= voe_ad;    pcio.reqen    <= oe_req;    pcio.req      <= r.req;    pcio.frameen  <= oe_frame;    pcio.frame    <= r.frame;    pcio.irdyen   <= oe_irdy;    pcio.irdy     <= r.irdy;    pcio.cbeen    <= (others => oe_cbe);    pcio.cbe      <= r.cbe;    pcio.vaden    <= roe_ad;     pcio.aden     <= oe_ad;    pcio.ad       <= r.ad;    pcio.trdy     <= r.trdy;    pcio.ctrlen   <= oe_ctrl;    pcio.trdyen   <= oe_trdy;    pcio.devselen <= oe_devsel;    pcio.stopen   <= oe_stop;    pcio.stop     <= r.stop;    pcio.devsel   <= r.devsel;    pcio.par      <= r.par;    pcio.paren    <= oe_par;  end process;  pcir : process (pciclk, pcii.rst)  begin    if rising_edge (pciclk) then      pr.ad         <= to_x01(pcii.ad);      pr.cbe        <= to_x01(pcii.cbe);      pr.devsel     <= to_x01(pcii.devsel);      pr.frame      <= to_x01(pcii.frame);      pr.idsel      <= to_x01(pcii.idsel);      pr.irdy       <= to_x01(pcii.irdy);      pr.trdy       <= to_x01(pcii.trdy);      pr.par        <= to_x01(pcii.par);      pr.stop       <= to_x01(pcii.stop);      pr.rst        <= to_x01(pcii.rst);      pr.gnt        <= to_x01(pcii.gnt);      r <= rin;      roe_ad <= rioe_ad;     end if;    if pcii.rst = '0' then	-- asynch reset required      	r.oe_ad <= '1'; r.oe_ctrl <= '1'; r.oe_par <= '1'; r.oe_stop <= '1';	r.oe_req <= '1'; r.oe_frame <= '1'; r.oe_cbe <= '1'; r.oe_irdy <= '1';	r.oe_trdy <= '1'; r.oe_devsel <= '1';      	r.noe_ad <= '0'; r.noe_ctrl <= '0'; r.noe_par <= '0'; r.noe_req <= '0';	r.noe_frame <= '0'; r.noe_cbe <= '0'; r.noe_irdy <= '0'; r.noe_stop <= '0';	r.noe_trdy <= '0'; r.noe_devsel <= '0';	if oepol = 0 then roe_ad <= (others => '1');	else roe_ad <= (others => '0'); end if;     end if;  end process;  cpur : process (rst,clk)  begin    if rising_edge (clk) then      hr.haddr    <= ahbsi.haddr(HADDR_WIDTH - 1 downto 0);      hr.htrans   <= ahbsi.htrans;      hr.hwrite   <= ahbsi.hwrite;      hr.hsize    <= ahbsi.hsize(1 downto 0);      hr.hburst   <= ahbsi.hburst;      hr.hwdata   <= ahbsi.hwdata;      hr.hsel     <= ahbsi.hsel(hslvndx) and ahbsi.hmbsel(0);      hr.hiosel   <= ahbsi.hsel(hslvndx) and ahbsi.hmbsel(1);      hr.hready   <= ahbsi.hready;      r2 <= r2in;    end if;  end process;  oe0 : if oepol = 0 generate    pcio.perren   <= '1';    pcio.serren   <= '1';    pcio.inten    <= '1';    pcio.locken   <= '1';  end generate;  oe1 : if oepol = 1 generate    pcio.perren   <= '0';    pcio.serren   <= '0';    pcio.inten    <= '0';    pcio.locken   <= '0';  end generate;    pcio.perr     <= '1';  pcio.serr     <= '1';  pcio.int      <= '1';       msttgt : if MASTER = 1 generate    ahbmst0 : ahbmst generic map (hindex => hmstndx, devid => GAISLER_PCISBRG)	port map (rst, clk, dmai, dmao, ahbmi, ahbmo);-- pragma translate_off    bootmsg : report_version    generic map ("pci_mt" & tost(hslvndx) &	": Simple 32-bit PCI Bridge, rev " & tost(REVISION) &	", " & tost(2**abits/2**20) & " Mbyte PCI memory BAR" );-- pragma translate_on  end generate;  tgtonly : if MASTER = 0 generate    ahbmst0 : ahbmst generic map (hindex => hmstndx, devid => GAISLER_PCITRG)	port map (rst, clk, dmai, dmao, ahbmi, ahbmo);-- pragma translate_off    bootmsg : report_version    generic map ("pci_mt" & tost(hmstndx) &	": Simple 32-bit Bridge, target-only, rev " & tost(REVISION) &	", " & tost(2**abits/2**20) & " Mbyte PCI memory BAR" );-- pragma translate_on  end generate;end;

⌨️ 快捷键说明

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