---------------------------------------------------------------------------------- -- Company: -- Engineer: -- -- Create Date: 21:20:54 07/16/2012 -- Design Name: -- Module Name: PE - Behavioral -- Project Name: -- Target Devices: -- Tool versions: -- Description: -- -- Dependencies: -- -- Revision: -- Revision 0.01 - File Created -- Additional Comments: -- ---------------------------------------------------------------------------------- library IEEE; use IEEE.STD_LOGIC_1164.ALL; library NocLib ; library Std; --use IEEE.STD_LOGIC_ARITH.ALL; --use IEEE.STD_LOGIC_UNSIGNED.ALL; use NocLib.CoreTypes.all; use work.Packet_type.all; use work.MPI_RMA.all; use std.textio.all; use IEEE.NUMERIC_STD.ALL; entity PE is Generic (DestId : natural ); Port ( Instruction : out STD_LOGIC_VECTOR (Word-1 downto 0); Instruction_en : out STD_LOGIC; Core_PushOut : in STD_LOGIC_VECTOR (Word-1 downto 0); clk : in STD_LOGIC; reset : in STD_LOGIC; Core_RAM_Data_Out : out STD_LOGIC_VECTOR (Word-1 downto 0); Core_RAM_Data_In : in STD_LOGIC_VECTOR (Word-1 downto 0); Core_RAM_WE : in STD_LOGIC; Core_RAM_EN : in STD_LOGIC; --Core_RAM_ENB : in STD_LOGIC; Core_RAM_ADDRESS_WR : in STD_LOGIC_VECTOR (ADRLEN-1 downto 0); Core_RAM_ADDRESS_RD : in STD_LOGIC_VECTOR (ADRLEN-1 downto 0); Core_Hold_req : in STD_LOGIC; Core_Hold_Ack : out STD_LOGIC); end PE; architecture Behavioral of PE is COMPONENT RAM_v generic (width : positive;size :positive); PORT( clka : IN std_logic; clkb : IN std_logic; wea : IN std_logic; ena : IN std_logic; enb : IN std_logic; addra : IN std_logic_vector; addrb : IN std_logic_vector; dia : IN std_logic_vector; dob : OUT std_logic_vector ); END COMPONENT; --données du programme PE --signaux pour l'interconnexionsignal datain :std_logic_vector(word-1 downto 0):= (others => '0'); signal ram_we ,ram_ena,ram_enb,ramsel: std_logic:='0'; signal pe_ram_we ,pe_ram_ena,pe_ram_enb: std_logic; signal pe_instr_en,pe_hold_ack: std_logic:='0'; signal ram_do,ram_din:std_logic_vector(word-1 downto 0):= (others => '0'); signal pe_ram_do,pe_ram_din:std_logic_vector(word-1 downto 0):= (others => '0'); signal ram_addra,ram_addrb :std_logic_vector(ADRLEN-1 downto 0); signal pe_ram_addra,pe_ram_addrb :std_logic_vector(ADRLEN-1 downto 0); signal sram : typ_dpram; signal SrcAdr0,SrcAdr1,destAdr0,destAdr1,Datalen:std_logic_vector(word-1 downto 0); signal dpid,dpid_i : natural range 0 to 15:=DestId; signal MyRank :std_logic_vector(3 downto 0); signal Libr : Core_io; --regroupe tous les signaux IO de la bibliothèque signal Lib_Ready:std_logic; --indique que l'exécution de la fonction est terminée signal Lib_instr_ack : std_logic; -- l'instruction est copiée dans le tampon FIFO signal Lib_Init : std_logic; -- l'initialisation est terminée --signaux pour la gestion de la MAE type typ_mae is (start,Fillmem,NextFill,InitApp,GetRank,WInCreate, putdata,getdata,WinCompleted,finalize,st_timeout); signal dcount : natural range 0 to 255:=0; --permet de compter le packet de données envoyées signal count,count_i : natural range 0 to 15:=0; signal RunState : typ_mae; signal Ram_busy :std_logic:='0'; begin Inst_RAM_v: RAM_v generic map(width=>word,size=>ADRLEN) PORT MAP( clka =>clk, clkb => clk, wea => ram_we, ena => ram_ena, enb => ram_enb, addra => ram_addra, addrb =>ram_addrb, dia => ram_din, dob => ram_do ); --================================================================ --MUX de la RAM Ram_mux: process (ramsel,pe_ram_addra,pe_ram_addrb,Core_ram_address_rd,Core_ram_address_wr, Core_ram_en,Core_ram_we,Core_ram_data_in,pe_ram_ena,pe_ram_enb,Ram_do, Pe_ram_din,Pe_ram_we ) begin case ramsel is when '1' => ram_addra <= Core_ram_address_wr ; ram_addrb <= Core_ram_address_rd ; ram_ena <= Core_ram_en; ram_enb <= Core_ram_en; ram_we<= Core_ram_we; ram_din <= Core_ram_data_in; pe_ram_do<=(others=>'Z'); Core_ram_data_out<=ram_do; when others => ram_addra <= pe_ram_addra; ram_addrb <= pe_ram_addrb; ram_ena <= pe_ram_ena; ram_enb <= pe_ram_enb; ram_we<= pe_ram_we; ram_din <=pe_ram_din; Core_ram_data_out<=(others=>'Z'); pe_ram_do<=ram_do; end case ; end process ; Instruction_En<=PE_instr_EN; -- Libr.Instr_en; --********A changer ********** --=== !!!!! attention la suppression de la ligne ci-dessous empêche ce -- composant de bien fonctionner !!! !!!!!!!!!!!!!!!!!!!!!!! instruction<=std_logic_vector(to_unsigned(Core_upper_adr,8)); dpid<=dpid_i; Lib_Instr_ack<=Core_Pushout(0); --l'instruction a été copié Lib_init<=Core_Pushout(4); -- Initialized -- pe_hold_req<=Core_hold_req; --Core_hold_ack<=pe_hold_ack; hold:process (Core_Hold_Req,clk,reset) begin if rising_edge(clk) then if reset='1' then Core_Hold_Ack<='0'; else if Core_Hold_Req='1' then ramsel<=not(ram_busy); Core_Hold_Ack<=not(ram_busy); --si la mémoire est occupé, forcé une libération Pe_hold_ack<=not(ram_busy); else Core_Hold_Ack<='0'; ramsel<='0'; Pe_hold_ack<='0'; end if; end if; end if; end process hold; --======================================================================= --======================================================================= --MAE du PE --======================================================================= pPutGet:process(clk,Core_Pushout,Core_Hold_req,PE_hold_Ack,RamSel,PE_Ram_do) constant DATAPTR : natural :=256; variable bfill,destrank,pid,mport : natural range 0 to 15; variable fsrc,ret : natural range 0 to 15:=0; variable timeout,ct,dlen : natural range 0 to 255; variable adrToset,SrcAdr,DestAdr : std_logic_vector(ADRLEN-1 downto 0); variable mywin : Mpi_win; variable iack : std_logic:='0'; variable adresse,adresse_rd :natural range 0 to 65536; variable status_reg,config_reg :std_logic_vector(Word-1 downto 0):=(others=>'0'); --======================================================= --variables pour la création du fichier de résultats type char_file is file of character; file f: text; variable status :file_open_status ; variable char_count: integer range 0 to 65536 := 0; variable str: string (1 to 79) ; variable L: line; variable fopened: std_logic:='0'; --====================================================== begin --=== Partie combinatoire du process =================================== Libr.Instr_ack<=Core_pushout(0); Libr.InitOk<=Core_pushout(4); Libr.Hold_Req<=Core_Hold_req; Libr.Hold_Ack<=Pe_Hold_Ack; Libr.RamSel<=RamSel; sram.data_out<=PE_ram_do; --=== Fin de la partie combinatoire du process ========================== --end loop; if (clk'event and clk='1') then if reset='1' then RunState<=start; else Libr.Instr_ack<=Core_pushout(0); Libr.InitOk<=Core_pushout(4); Libr.Hold_Req<=Core_Hold_req; Libr.Hold_Ack<=Pe_Hold_Ack; Libr.RamSel<=RamSel; sram.data_out<=PE_ram_do; case RunState is when start => Dcount<=0; if bfill=0 then -- si le nombre de bloc de mémoire remplis est vide RunState<=Fillmem; end if; Ram_busy<='0'; PE_Instr_En<='0'; iack:='0'; adresse:=DATAPTR; adresse_rd:=0; timeout:=0; dcount<=0; if fopened='0' then file_open(status,f, integer'image(destid) & "test_file0.txt", APPEND_MODE); --while not endfile(c_file_handle) loop --end if; --write (l,string'("Ce fichier contient des resultats de la simulation ; ;" & " started at time ; " & time'image(now))); --report l.all; -- writeline (f, l) ; fopened:='1'; end if; when Fillmem => if Ramsel='0' then PE_Ram_din<=std_logic_vector(to_unsigned(dcount,8)); -- x"0f"; PE_Instr_En<='0'; dcount<=dcount+1; if dcount=200 then bfill:=bfill+1; if bfill=4 then RunState<=InitApp; else RunState<=nextfill; end if; else adresse:=adresse+1; RunState<=Fillmem; end if; else -- attente de la libéraion de la mémoire timeout:=timeout+1; if timeout=100 then RunState<=st_timeout; end if; end if; when nextfill => --prépare le prochain bloc mémoire qui sera rempli adresse:=200*bfill; dcount<=0; ct:=0; RunState<=Fillmem; PE_Instr_En<='0'; when InitApp => --code pour Init dlen:=1; if ct=0 then write (l,string'("Dlen; ;INIT of Process n°; " & image(MyRank) & "; started at ; " & time'image(now))); report l.all; writeline (f, l) ; end if; pMPI_Init(ct,Libr,Clk,SRam); PE_Instr_EN<=Libr.instr_en; adresse:=to_integer(unsigned(sram.addr_wr)); adresse_rd:=to_integer(unsigned(sram.addr_rd)); PE_ram_din<=sram.data_in; --if Libr.InitOk='1' then if ct=0 then RunState<=GetRank; write (l,string'("Dlen; ;INIT;" & "; ended at ; " & time'image(now))); report l.all; writeline (f, l) ; end if; when GetRank => if ct=0 then write (l,string'("Dlen; ; Rank ; " & "; started ; " & time'image(now))); report l.all; writeline (f, l) ; end if; pMPI_Comm_rank(ct,Libr,sram,MPI_COMM_WORLD,MyRank); adresse_rd:=to_integer(unsigned(sram.addr_rd)); if ct=0 then RunState<=PutData; write (l,string'("Dlen; ; Rank ; " & "; ended at ; " & time'image(now))); report l.all; writeline (f, l) ; end if; when Wincreate => when putdata => --construire le packet pour le Put --dlen:=251; --- if ct=0 then write (l,string'("Dlen;" & integer'image(dlen) & ";Put of Pr n°; " & image(MyRank) & "; started at ; " & time'image(now))); report l.all; writeline (f, l) ; end if; if unsigned(MyRank) = 0 then Destrank:=1; else DestRank:=0; end if; SrcAdr:=std_logic_vector(to_unsigned(DATAPTR,ADRLEN)); DestAdr:=X"2000"; pMPI_put(ct,Libr,Clk,Sram,SrcAdr,Dlen,MPI_int,destrank,DestAdr,Dlen,Mpi_int,Default_win); adresse:=to_integer(unsigned(sram.addr_wr)); adresse_rd:=to_integer(unsigned(sram.addr_rd)); PE_Instr_EN<=Libr.instr_en; PE_ram_din<=sram.data_in; dcount<=ct; if ct=0 then RunState<=GetData; report "Put of Process n°; " & image(MyRank) & "; ended at ; " & time'image(now); write (l,string'("Dlen;" & integer'image(dlen) & ";Put of Pr n°; " & image(MyRank) & "; ended at time ; " & time'image(now))); report l.all; writeline (f, l) ; end if; when getdata => --positionnement du mot de longueur des données --dlen:=251; --- if ct=0 then write (l,string'("Dlen;" & integer'image(dlen) & ";GET of Process n°; " & image(MyRank) & "; started at ; " & time'image(now))); report l.all; writeline (f, l) ; end if; SrcAdr:=X"0120"; DestAdr:=X"4000"; pMPI_GET(ct,Libr,Clk,Sram,SrcAdr,Dlen,MPI_int,destrank,DestAdr,Dlen,Mpi_int,Default_win); adresse:=to_integer(unsigned(sram.addr_wr)); adresse_rd:=to_integer(unsigned(sram.addr_rd)); PE_Instr_EN<=Libr.instr_en; PE_ram_din<=sram.data_in; dcount<=ct; if ct=0 then RunState<=wincompleted; assert ct/=0 report "GET_END " & integer'image(destrank) severity Warning ; write (l,string'("Dlen ;" & integer'image(dlen) & ";GET of Proc n°; " & image(MyRank) & "; ended at ; " & time'image(now))); report l.all; writeline (f, l) ; end if; when WinCompleted => if ct=0 then write (l,string'("Dlen ;" & integer'image(dlen) & ";Wait of Proc n°; " & image(MyRank) & "; started at ; " & time'image(now))); report l.all; writeline (f, l) ; end if; pMPI_Win_wait(ct,Libr,sram,MyWin ); adresse:=to_integer(unsigned(sram.addr_wr)); adresse_rd:=to_integer(unsigned(sram.addr_rd)); if ct=0 then RunState<=finalize; write (l,string'("Dlen ;" & integer'image(dlen) & ";Wait of Proc n°; " & image(MyRank) & "; ended at ; " & time'image(now))); report l.all; writeline (f, l) ; end if; when finalize => if ct=0 then write (l,string'("Dlen ;" & integer'image(dlen) & ";Finalize of Proc n°; " & image(MyRank) & "; started at ; " & time'image(now))); report l.all; writeline (f, l) ; end if; if ct=0 then RunState<=start; write (l,string'("Dlen ;" & integer'image(dlen) & ";Finalize of Proc n°; " & image(MyRank) & "; ended at ; " & time'image(now))); report l.all; writeline (f, l) ; file_close(f); end if; when st_timeout => --if ram_busy='1' then RunState<=start; --end if RunState<=start; end case; pe_Ram_addra<=STD_LOGIC_VECTOR(to_unsigned(adresse,16)); pe_Ram_addrb<=STD_LOGIC_VECTOR(to_unsigned(adresse_rd,16)); end if; end if; end process pPutGet; majPutGet:process (RunState,pe_ram_do,sram,Lib_Init) begin case RunState is when start => PE_Ram_we<='0'; PE_Ram_ena<='0'; PE_Ram_enb<='0'; --PE_Instr_En<='0'; when fillmem => PE_Ram_we<='1'; PE_Ram_ena<='1'; PE_Ram_enb<='0'; --PE_Instr_En<='0'; when nextfill => PE_Ram_we<='1'; PE_Ram_ena<='1'; PE_Ram_enb<='0'; when InitApp => -- PE_Ram_we<='1'; -- PE_Ram_ena<='1'; -- PE_Ram_enb<='0'; PE_Ram_we<=sram.we; PE_Ram_ena<=sram.ena; PE_Ram_enb<=sram.enb; when GetRank => PE_Ram_we<=sram.we; PE_Ram_ena<=sram.ena; PE_Ram_enb<=sram.enb; when WinCreate => PE_Ram_we<=sram.we; PE_Ram_ena<=sram.ena; PE_Ram_enb<=sram.enb; --positionnement du mot de longueur des données when putdata => srcadr0<=X"00"; srcadr1<=X"01"; destadr0<=X"00"; destadr1<=X"02"; PE_Ram_we<=sram.we; PE_Ram_ena<=sram.ena; PE_Ram_enb<=sram.enb; when getdata => PE_Ram_we<=sram.we; PE_Ram_ena<=sram.ena; PE_Ram_enb<=sram.enb; when Wincompleted => PE_Ram_we<=sram.we; PE_Ram_ena<=sram.ena; PE_Ram_enb<=sram.enb; when finalize => PE_Ram_we<='0'; PE_Ram_ena<='0'; PE_Ram_enb<='0'; when st_timeout => PE_Ram_we<='0'; PE_Ram_ena<='0'; PE_Ram_enb<='0'; end case; end process majPutGet ; end Behavioral;