ctrlunit.vhd

来自「The GRLIB IP Library is an integrated se」· VHDL 代码 · 共 844 行 · 第 1/3 页

VHD
844
字号
      v.dmao.address:=r.baseadr(31 downto 6) & "011110";        v.dmao.write := '1';  v.dmao.size := "01";        v.dmao.wdata(15 downto 0) := r.readbuf2(15 downto 0);      v.ipchksum := r.ipchksum + r.readbuf2(15 downto 0);     when 4 =>        v.dmao.address := r.baseadr(31 downto 6) & "011100";       v.dmao.write := '0'; v.dmao.size := "01";     when 5 =>       v.dmao.address := r.baseadr(31 downto 6) & "100000";       v.dmao.write := '1'; v.dmao.size := "01";       v.dmao.wdata(31 downto 16) := r.readbuf2(31 downto 16);       v.ipchksum := r.ipchksum + r.readbuf2(31 downto 16);    when 6 =>        v.dmao.address := r.baseadr(31 downto 6) & "010110";        v.dmao.write := '0'; v.dmao.size := "01";      when 7 =>        v.ipchksum := r.ipchksum + r.readbuf2(15 downto 0);    when 8 =>        v.dmao.address := r.baseadr(31 downto 6) & "011010";       v.dmao.write := '1';  v.dmao.size := "01";        v.dmao.wdata(15 downto 0) := ip_adr(31 downto 16);      v.ipchksum := "0000" & r.ipchksum(15 downto 0) + r.ipchksum(19 downto 16);                                                              when 9 =>        v.dmao.address := r.baseadr(31 downto 6) & "011100";        v.dmao.write := '1'; v.dmao.size := "01";  v.dmao.wdata(31 downto 16) := ip_adr(15 downto 0);      v.ipchksum := "0000" & not (r.ipchksum(15 downto 0) + r.ipchksum(16));    when 10 =>       v.dmao.address := r.baseadr(31 downto 6) & "011000";        v.dmao.write := '1';  v.dmao.size := "01";        v.dmao.wdata(31 downto 16) := r.ipchksum(15 downto 0);    when others => null;    end case;   when finished =>  if r.main_state /= ip then v.ip_state := idle; end if;   when others => v.ip_state := idle;  end case;--------------------------------------------------------------------------------    --ARP FSM--------------------------------------------------------------------------------      case r.arp_state is  when idle =>     if v.main_state = arp then       v.arp_state := arp_1; v.dmao.address := r.baseadr(31 downto 6) & "100110";      v.dmao.write := '0'; v.dmao.size := "01"; end if;  when arp_1 =>    case r.counter2 is     when 0 => start := '1';      if dmain.ready = '1' then         start := '0';  v.readbuf2(31 downto 16) := dmain.rdata(15 downto 0);        v.counter2 := r.counter2 + 1;          v.dmao.address := r.baseadr(31 downto 6) & "101000";        v.dmao.write := '0'; v.dmao.size := "01";       end if;     when 1 =>      start := '1';             if dmain.ready = '1' then      	start := '0';  v.readbuf2(15 downto 0) := dmain.rdata(31 downto 16);        v.counter2 := r.counter2 + 1;        end if;    when 2 =>      if r.readbuf2 = ip_adr then  v.arp_state := arp_2;       else v.arp_state := finished; v.arp_bad_ip := '1'; end if;      v.counter2 := 0;    when others =>  null;    end case;  when arp_2 =>    case r.counter2 is    when 0 =>        v.dmao.address := r.baseadr(31 downto 6) & "010100";        v.dmao.write := '1';  v.dmao.size := "01";  v.dmao.wdata(31 downto 16) := X"0002";    when 1 =>        v.dmao.address := r.baseadr(31 downto 6) & "010110";        v.dmao.write := '0';  v.dmao.size := "01";                                                              when 2 =>      v.dmao.address := r.baseadr(31 downto 6) & "100000";      v.dmao.write := '1';  v.dmao.size := "01";        v.dmao.wdata(31 downto 16) := r.readbuf2(15 downto 0);    when 3 =>        v.dmao.address := r.baseadr(31 downto 6) & "011000";       v.dmao.write := '0';  v.dmao.size := "10";    when 4 =>        v.dmao.address := r.baseadr(31 downto 6) & "100010";        v.dmao.write := '1';  v.dmao.size := "01";        v.dmao.wdata(15 downto 0) := r.readbuf2(31 downto 16);    when 5 =>        v.dmao.address := r.baseadr(31 downto 6) & "100100";       v.dmao.write := '1';  v.dmao.size := "01";       v.dmao.wdata(31 downto 16) := r.readbuf2(15 downto 0);     when 6 =>        v.dmao.address := r.baseadr(31 downto 6) & "011100";        v.dmao.write := '0';  v.dmao.size := "10";    when 7 =>       v.dmao.address := r.baseadr(31 downto 6) & "100110";       v.dmao.write := '1';  v.dmao.size := "01";       v.dmao.wdata(15 downto 0) := r.readbuf2(31 downto 16);    when 8 =>       v.dmao.address := r.baseadr(31 downto 6) & "101000";       v.dmao.write := '1';  v.dmao.size := "01";        v.dmao.wdata(31 downto 16) := r.readbuf2(15 downto 0);     when 9 =>        v.dmao.address := r.baseadr(31 downto 6) & "011100";       v.dmao.write := '1';  v.dmao.size := "10";  v.dmao.wdata := ip_adr;                                   when 10 =>      v.dmao.address := r.baseadr(31 downto 6) & "011000";       v.dmao.write := '1';  v.dmao.size := "10";  v.dmao.wdata := eth_adr(31 downto 0);    when 11 =>      v.dmao.address := r.baseadr(31 downto 6) & "010110";        v.dmao.write := '1';  v.dmao.size := "01";        v.dmao.wdata(15 downto 0):=eth_adr(47 downto 32);        when others => null;       end case;    if r.counter2 < 12 then  v.counter2 := r.counter2 + 1;  v.arp_state := arp_3;         else  v.counter2 := 0;  v.arp_state := finished;  end if;  when arp_3 =>    start := '1';    if dmain.ready = '1' then      start := '0';  v.arp_state := arp_2;      if r.dmao.write = '0' then v.readbuf2 := dmain.rdata; end if;    end if;     when finished => if r.main_state /= arp then v.arp_state := idle; end if;         end case; --------------------------------------------------------------------------------   --MAC INITIALIZATION--------------------------------------------------------------------------------           case r.initmacstate is    when idle =>       if mdioenabled = 0 and autoneg = 1 then         v.initmacstate := addrSel; v.dmao.size := "10"; v.dmao.write := '1';        v.dmao.address := X"FFF01018";          v.dmao.wdata := X"0040" & conv_std_logic_vector(block_size, 16);      else         v.initmacstate := waitphy;	-- pragma translate_off	if sim = 1 then v.initmacstate := setphy; end if; 	-- pragma translate_on      end if;                             when waitphy =>       if unsigned(r.resetcounter) < phyrstcls then         v.resetcounter := r.resetcounter + 1;      else         v.resetcounter := (others => '0');         v.initmacstate := setphy;       end if;    when setphy =>       if autoneg = 1 then        case r.counter2 is        when 0 =>          v.dmao.address := X"FFF01030"; v.dmao.size := "10"; v.dmao.write := '1';          v.dmao.wdata := X"000000" & conv_std_logic_vector(phyadr,8);              v.initmacstate := setphy2;        when 1 =>               v.dmao.address := X"FFF0102C"; v.dmao.size := "10"; v.dmao.write := '1';          v.dmao.wdata := X"00000002"; v.initmacstate := setphy2;        when 2 =>           v.dmao.address := X"FFF0103C"; v.dmao.size := "10"; v.dmao.write := '0';           v.initmacstate := pollstat; v.counter2 := 0;        when others => null;        end case;      else         case r.counter2 is        when 0 =>          v.dmao.address := X"FFF01030"; v.dmao.size := "10"; v.dmao.write := '1';          v.dmao.wdata := X"000000" & conv_std_logic_vector(phyadr,8);              v.initmacstate := setphy2;        when 1 =>           v.dmao.address := X"FFF01034"; v.dmao.size := "10"; v.dmao.write := '1';           v.initmacstate := setphy2;           if speed = 1 and fullduplex = 1 then v.dmao.wdata := X"00002100";           elsif speed = 1 and fullduplex = 0 then v.dmao.wdata := X"00002000";          elsif speed = 0 and fullduplex = 1 then v.dmao.wdata := X"00000100";          else v.dmao.wdata := X"00000000"; end if;        when 2 =>               v.dmao.address := X"FFF0102C"; v.dmao.size := "10"; v.dmao.write := '1';          v.dmao.wdata := X"00000004"; v.initmacstate := setphy2;        when 3 =>           v.initmacstate := addrSel; v.dmao.address := X"FFF01018"; v.counter2 := 0;          v.dmao.wdata := X"0040" & conv_std_logic_vector(block_size, 16);        when others => null;        end case;      end if;    when setphy2 =>       start := '1';      if dmain.ready = '1' then         v.initmacstate := setphy; start := '0'; v.counter2 := r.counter2 + 1;       end if;       when pollstat =>      start := '1';       if dmain.ready = '1' and dmain.rdata(1) = '0' then         start := '0'; v.initmacstate := readdata; v.dmao.address := X"FFF01038";      end if;    when readdata =>      start := '1';       if dmain.ready = '1' then         v.readbuf2 := dmain.rdata; start := '0'; v.initmacstate := addrSel;         v.dmao.address := X"FFF01018"; v.dmao.write := '1';        v.dmao.wdata := X"0040" & conv_std_logic_vector(block_size, 16);      end if;     when addrSel =>      start := '1';        if dmain.ready = '1' then  v.initmacstate := addrSel2;  start := '0'; end if;    when addrSel2 =>       if r.counter2 < 4 then  v.counter2 := r.counter2 + 1;  v.initmacstate := addrSel;        case r.counter2 is        when 0 =>           v.dmao.address := X"FFF01008";  v.dmao.wdata := X"0000000F";                                            when 1 =>           v.dmao.address := X"FFF01040";  v.dmao.wdata := eth_adr(31 downto 0);                                  when 2 =>          v.dmao.address := X"FFF01044";  v.dmao.wdata := X"0000" & eth_adr(47 downto 32);                     when 3 =>           v.dmao.address := X"FFF01000";              if autoneg = 1 and mdioenabled = 1 then            if r.readbuf(2) = '1' then v.dmao.wdata := X"0000A403";            else v.dmao.wdata := X"0000A003"; end if;          else            if fullduplex = 1 then v.dmao.wdata := X"0000A403";              else v.dmao.wdata := X"0000A003"; end if;          end if;	  -- pragma translate_off	  if sim = 1 then v.dmao.wdata(6) := '1'; end if; 	  -- pragma translate_on         when others => null;          end case;      else         v.initmacstate := finished;  v.counter2 := 0;       end if;    when finished => null;      when others => v.initmacstate := finished;    end case;        if rst = '0' then      v.tx_offset := 0; v.tx2_offset := 0; v.rx_offset := 0; v.rx2_offset := 0;       v.tx3_offset := 0; v.baseadr := ram_addr; v.counter := 0; v.counter2 := 0;      v.resetcounter := (others => '0'); v.laddr2 := X"C000"; v.ip_state := idle;      v.arp_state := idle;   v.udp_state := idle;       v.app_state := idle;  v.initmacstate := idle; v.main_state := idle;       v.rx_tx_state := init; v.write_stat := (others => '0'); v.no_snd := (others => '1');      v.read_stat := (others => '0'); v.read_error := (others => '0');      -- pragma translate_off      if sim = 1 then v.rcv_nxt := (others => '0'); end if;       -- pragma translate_on    end if;-------------------------------------------------------------------------------   --SIGNAL ASSIGNMENTS-------------------------------------------------------------------------------             rin <= v;    dmaout.address <= r.dmao.address;    dmaout.wdata <= r.dmao.wdata;    dmaout.start <= start;    dmaout.burst <=r.dmao.burst;    dmaout.write <= r.dmao.write;    dmaout.busy <= r.dmao.busy;    dmaout.irq <= r.dmao.irq;    dmaout.size <= r.dmao.size;        dmaout_m.address <= r.dmao_m.address;    dmaout_m.wdata <= r.dmao_m.wdata;    dmaout_m.start <= mstart;    dmaout_m.burst <= r.dmao_m.burst;    dmaout_m.write <= r.dmao_m.write;    dmaout_m.busy <= r.dmao_m.busy;    dmaout_m.irq <= r.dmao_m.irq;    dmaout_m.size <= r.dmao_m.size;        dmaout_rt.address <= r.dmao_rt.address;    dmaout_rt.wdata <= r.dmao_rt.wdata;    dmaout_rt.start <= rtstart;    dmaout_rt.burst <= r.dmao_rt.burst;    dmaout_rt.write <= r.dmao_rt.write;    dmaout_rt.busy <= r.dmao_rt.busy;    dmaout_rt.irq <= r.dmao_rt.irq;    dmaout_rt.size <= r.dmao_rt.size;        end process;--------------------------------------------------------------------------------   --REGISTERS--------------------------------------------------------------------------------    reg0: process(rst,clk)    begin if rising_edge(clk) then r<=rin; end if; end process;end;

⌨️ 快捷键说明

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