---------------------------------------------------------------------------------- -- Company: GRIIA - ETIS - LIP6 -- Engineer: GAMOM, KIEGAING -- -- Create Date: 01:02:10 06/17/2011 -- Design Name: -- Module Name: EX2_FSM - Behavioral -- Project Name: -- Target Devices: -- Tool versions: -- Description: -- machine a etat qui execute la reception des packet dans le core mpi -- Dependencies: --ss -- Revision: 26/01/2012 -- Revision 0.01 - File Created -- Additional Comments: -- ---------------------------------------------------------------------------------- library IEEE; library NocLib ; use IEEE.STD_LOGIC_1164.ALL; use IEEE.Numeric_std.ALL; use IEEE.STD_LOGIC_UNSIGNED.ALL; use Work.Packet_type.ALL; use NocLib.CoreTypes.all; ---- Uncomment the following library declaration if instantiating ---- any Xilinx primitives in this code. --library UNISIM; --use UNISIM.VComponents.all; entity EX2_FSM is generic ( pid : std_logic_vector(3 downto 0) :="0001"; -- id du processeur nprocs : std_logic_vector(3 downto 0):="0100"-- nombre de processeur du MPSOC - 1 ); Port ( clk : in STD_LOGIC; reset : in STD_LOGIC; Instruction_en : in std_logic; dma_wr_grant : in STD_LOGIC; dma_wr_request : out STD_LOGIC; dma_rd_grant : in STD_LOGIC; dma_rd_request : out STD_LOGIC; ram_rd : out std_logic; ram_wr : out std_logic; ram_address : out std_logic_vector(ADRLEN-1 downto 0); Ram_data_in : out STD_LOGIC_VECTOR (Word-1 downto 0); Ram_data_out : in STD_LOGIC_VECTOR (Word-1 downto 0); fifo_data : out STD_LOGIC_VECTOR (Word-1 downto 0); fifo_wr_en : out STD_LOGIC; fifo_full : in STD_LOGIC; Rec_Rdy : OUT std_logic; Rec_Data : buffer Typ_PortIO(0 to 3); Rec_Ack : IN std_logic; AppRank : in STD_LOGIC_VECTOR(3 downto 0); AppSize : in STD_LOGIC_VECTOR(3 downto 0); packet_received : out STD_LOGIC; packet_ack : in STD_LOGIC; barrier_completed : out STD_LOGIC; Ready : Out std_logic; AppInitReq :out STD_LOGIC; -- requête d'initialisation de l'application AppInitAck :in STD_LOGIC; -- Acquitement d'initialisation Initialized:in std_logic ; -- état de la Lib Result : out STD_LOGIC_VECTOR (Word-1 downto 0):=(others=>'0'); -- le résultat de l'exécution de ce module switch_data_available : in STD_LOGIC; switch_port_out_data : in STD_LOGIC_VECTOR (Word-1 downto 0); switch_port_out_rd_en : out STD_LOGIC ); end EX2_FSM; architecture Behavioral of EX2_FSM is --module pour la lecture des données sur le réseau CONSTANT MSIZE : natural :=4; --taille de la mémoire tampon pour les messages reçu component Proto_receiv is generic (sizemem : natural := 64); port ( clk,reset : in std_logic; fifo_empty,fifo_full : in std_logic; rcv_start : in std_logic; --début de la réception rcv_ack :in std_logic; -- acquittement de la réception rcv_comp : out std_logic; -- fin de la réception pop : out std_logic:='0'; fifo_out : in std_logic_vector(Word-1 downto 0); mem :out memory(0 to sizemem-1)); end component Proto_receiv; COMPONENT SetBit PORT( clk : IN std_logic; reset : IN std_logic; BitMask : IN std_logic_vector(7 downto 0); BitVal : IN std_logic; start : in std_logic; whole : in std_logic; done : out std_logic; dma_wr_grant : IN std_logic; dma_rd_grant : IN std_logic; Ram_data_in : out std_logic_vector(7 downto 0); dma_wr_request : OUT std_logic; dma_rd_request : OUT std_logic; ram_rd : OUT std_logic; ram_wr : OUT std_logic; ram_address : IN std_logic_vector(15 downto 0); Ram_data_out : in std_logic_vector(7 downto 0) ); End component SetBit; --constante constant Max_stack : integer:=7;--Le nombre de GET qui peuvent être empilés -- définition du type etat de la machine à etat type fsm_states is (Ex2_Ready,fetch_packet_type, decode_packet_type, decode_packet_type2, fetch_addresses,ex2_spawn1,ex2_spawn2,ex2_put1,ex2_put2,ex2_put3 ,ex2_put4, ex2_put5,ex2_get1, ex2_get2,ex2_get3,ex2_get4,ex2_ack1,ex2_ack2,ex2_ack3, Ex2_WSync,Ex2_WComp,ex2_barrier1, ex2_barrier2, ex2_barrier3, ex2_barrier4, ex2_barrier5, ex2_barrier6, ex2_barrier7,ex2_init1,ex2_init2,Ex2_Set_Busy); type fsm_ack is(ack0,ack_readwait,ack_checkwait,ack1,ack2,ack3,ack4,ack5,ack6); type mem32 is array (natural range <>) of std_logic_vector (31 downto 0); signal Next_Ex2_state,ex2_state :fsm_states; signal ack_state,next_ack_state : fsm_ack; -- signal mode_get,match_get:std_logic:='0'; signal mode_get_i,match_get_i:std_logic:='0'; -- machine a etat du module signal packet_type, packet_type_i : std_logic_vector(3 downto 0); signal P_len_i,P_len : std_logic_vector(Word-1 downto 0); signal barrier_counter,barrier_counter_i : std_logic_vector(3 downto 0); signal pading_data,data_to_ram,Data_to_ram_i : std_logic_vector(Word-1 downto 0):=(others=>'0'); signal n,n_i : natural range 0 to 15; signal dest_address,dest_address_i,ack_address : std_logic_vector(ADRLEN-1 downto 0):=(others=>'0'); signal data_to_write_fifo,data_to_write_fifo_i : std_logic_vector(Word-1 downto 0); --******************************************* --signaux pour la fonction SetBit signal sb_BitMask : std_logic_vector(7 downto 0):=(others=>'0'); signal sb_BitVal,sb_start,sb_done : std_logic:='0'; signal sb_whole : std_logic:='0'; --écrire le mot entier signal sb_Ram_data_in : std_logic_vector(7 downto 0); signal sb_dma_wr_request : std_logic; signal sb_dma_rd_request : std_logic; signal sb_ram_rd : std_logic; signal sb_ram_wr : std_logic; signal sb_ram_address : std_logic_vector(15 downto 0):=(others=>'0'); signal sb_Ram_data_out : std_logic_vector(7 downto 0):=(others=>'0'); -- deuxième module pour set busy bit signal Set_Wbusy : std_logic:='0'; --choix du Mux signal GPost_Set,Gpost_Set_i : std_logic:='0'; --indique l'arrivée de Win_Compl --********************************************* signal Ex2_on : std_logic:='0'; signal dma_rd,dma_wr,rd_ok ,wr_ok:std_logic:='0'; signal sent_ack, sent_ack_i,wr_ack,instr_ack,Instr_ack_i:std_logic:='0'; --signaux pour la gesion de l'acquittement signal dest_ack,dest_ack_i:std_logic_vector(3 downto 0) :=(others=>'0'); signal to_fifo_ack :std_logic_vector(Word-1 downto 0):=(others=>'0'); signal Result_i,result1 : STD_LOGIC_VECTOR (Word-1 downto 0):=(others=>'0'); --signaux pour l'untilisation du composant de réception signal rfifo_empty,rfifo_full:std_logic; signal rcv_start,rcv_comp,rcv_ack:std_logic; signal rpop:std_logic; signal initreq,initreq_i:std_logic:='0'; --Requete d'initialisation --signal mem:memory(0 to Msize-1)); --jusqu'à 16 Get peuvent être attendus! signal Wcomp : std_logic:='0'; --indique que tous les transferts sont terminés signal WStart,WPost,WBUSY, WBUSY_i,RGET,RGET_i: std_logic:='0'; -- signal Rec_WPost,Rec_WPost_i,GComp,GComp_i, GPost_i,GPost: std_logic_vector(Max_Stack downto 0):=(others=>'0'); signal Waited_Get,Waited_Get_i : mem32(0 to Max_stack); Signal Rec_Data_i : Typ_PortIO(0 to 3); signal Get_Instr,Get_instr_i,Put_instr,Put_instr_i :memory(0 to 8); signal Put_Id : std_logic_vector(31 downto 0):=(others=>'0'); signal P_G,P_G_i: natural range 0 to 3:=0; --Msg Ack : 1 -> Put, 2-->Get signal Ptr_Get,Ptr_Get_i : natural range 0 to Max_stack:=0; signal Received_get,Received_get_i : std_logic_vector(Max_stack downto 0):=(others=>'0');--sera remis à 0 lorsque Wstart/WPost est reçu begin ram_address <= ack_address when instr_ack='1' else dest_address; --fifo_data <= data_to_write_fifo; Result<=Result1; p_instr_fifo:process(ack_state,data_to_write_fifo_i,wr_ack,to_fifo_ack,instr_ack) begin if instr_ack='1' then fifo_data<=to_fifo_ack; else fifo_data<=data_to_write_fifo_i; end if; end process p_instr_fifo; R0:proto_receiv generic map (sizemem =>4) port map ( clk=>clk, reset=>reset, rcv_start=>rcv_start, rcv_comp=>rcv_comp, rcv_ack=>rcv_ack, fifo_empty=>rfifo_empty, fifo_full=>rfifo_full, fifo_out=>switch_port_out_data, pop=>rpop, mem=>open ); --envoie de l'acquittement setbit1:SetBit PORT MAP ( clk =>clk, reset =>reset, BitMask =>sb_bitMask, BitVal =>sb_bitval, dma_wr_grant =>dma_wr_grant, dma_rd_grant =>dma_rd_grant, Ram_data_in => sb_Ram_data_in, dma_wr_request =>sb_dma_wr_request, dma_rd_request =>sb_dma_rd_request, ram_rd =>sb_ram_rd, ram_wr =>sb_ram_wr, ram_address =>dest_address, Ram_data_out =>sb_ram_data_out, Start =>sb_start, whole=>sb_whole, done =>sb_done ); -- processus de transistion entre les etats ex2_fsm_logic : process(Ex2_state, Instruction_En,fifo_full,dma_rd_grant,dma_wr_grant,AppinitAck,Initialized, switch_data_available,switch_port_out_data,sb_ram_data_in,Data_to_Ram,Ram_data_out,sb_done,sb_dma_rd_request,n,P_len, sent_ack,wr_ack,to_fifo_ack,dest_address,WBusy,Ptr_Get,Get_Instr,P_G,Waited_get,Received_get,rget,GPost,GPost_Set,packet_type,barrier_counter, dest_ack,rec_wpost,Gcomp,rec_data,mode_get,match_get,Instr_ack,result1,data_to_write_fifo) variable delai : natural range 0 to 1:=0; --permet de détecter que l'écriture en RAM doit être décalée variable tempval : std_logic_vector(Word-1 downto 0); variable n_e,i:natural range 0 to 15 :=0; --=================================================================- procedure read_nocdat_fsm(sdata_avail: std_logic; signal rd,wr:out std_logic; signal Plen_i : in std_logic_vector(Word-1 downto 0); signal Plen_o : out std_logic_vector(Word-1 downto 0); variable n:out natural range 0 to 15;signal n_e:in natural range 0 to 15) is --lit la suite des données qui sont dans le NoC et identifie le paramètre important begin if n_e<3 then wr<='0'; if sdata_avail='1' then n:=n_e+1; rd<='1'; plen_o <=plen_i-1; else rd<='0'; end if; --result_i<=(others=>'0'); elsif n_e=3 then if sdata_avail='1' then n:=n_e+1; rd<='0'; --P_len <=P_len_i -1; --data_to_ram<=sportdout; --Result_i<=sport_out_data; else rd<='0'; end if; end if; end procedure; begin Next_Ex2_state <= Ex2_state; Ex2_on<='0'; sb_whole<='0'; sb_start<='0'; --valeur par défaut sb_bitmask<=x"FF"; sb_bitval<='1'; dma_rd<='0'; dma_wr<='0'; rd_ok<='0'; wr_ok<='0'; barrier_counter_i <= barrier_counter; GPost_Set_i<=GPost_Set; Rec_WPost_i<=Rec_WPost; GPost_i<=GPost; P_G_i<=P_G; RGET_i<=RGET; WBUSY_i<=WBUSY; Result_i<=Result1; Ptr_get_i<=Ptr_get; mode_get_i<=mode_get; data_to_write_fifo_i<=data_to_write_fifo; match_get_i<=match_get; GComp_i<=GComp; Instr_ack_i<=Instr_ack; received_get_i<=received_get; mode_get_i<=mode_get; InitReq_i<=InitReq; match_get_i<=match_get; Data_to_ram_i<=Data_to_ram; dest_address_i<=dest_address; for i in 0 to Max_stack loop Waited_get_i(i)<=Waited_get(i); end loop; For i in 0 to 7 loop Get_Instr_i(i)<=Get_instr(i); end loop; Ex2_on<=Instruction_en; --détermine si le module peut être activer ou non n_i<=n; --valeur par défaut de n_i P_len_i<=P_len; for i in 0 to 3 loop Rec_Data_i(i)<=Rec_Data(i); Packet_type_i<=Packet_type; dest_ack_i<=dest_ack; end loop; case ex2_state is when Ex2_ready => if Instruction_en='1' and switch_data_available='1' then Next_Ex2_state <= fetch_packet_type; end if; rd_ok<='0';wr_ok<='0'; when fetch_packet_type => if switch_data_available ='1' and Instruction_en='1' then --and initialized ='1' Next_Ex2_state <= decode_packet_type; packet_type_i<=switch_port_out_data(7 downto 4); Dest_ack_i<=switch_port_out_data(3 downto 0); Rec_Data_i(0)<=switch_port_out_data; --récupérer la première donnée reçue ! rd_ok<='1'; else --Next_Ex2_state <= Ex2_Ready; rd_ok<='0'; end if; n_i<=0; when decode_packet_type => rd_ok<='0'; if switch_data_available ='0' then Next_Ex2_state <= decode_packet_type; else rd_ok<='1'; Rec_Data_i(1)<=switch_port_out_data-2; if packet_type = MPI_PUT then P_len_i <= switch_port_out_data - 2; n_i<=0; Next_Ex2_state <= decode_packet_type2; elsif packet_type = MPI_GET then P_len_i <=switch_port_out_data-2; Next_Ex2_state <= decode_packet_type2; elsif packet_type = MPI_BARRIER_REACHED or packet_type = MPI_BARRIER_COMPLETED then P_len_i <= switch_port_out_data; n_i<=0; Next_Ex2_state <= ex2_barrier1; elsif packet_type = MPI_INIT or packet_type =INIT_SETRANK or packet_type =INIT_SEEKMAIN then n_i<=0; wr_ok<='0'; --rd_ok<='1'; P_len_i <= switch_port_out_data-2; Rec_Data_i(1)<=switch_port_out_data; Next_Ex2_state <= ex2_init1; elsif packet_type = MPI_ACK then n_i<=0; wr_ok<='0'; rd_ok<='0'; P_len_i <= switch_port_out_data-2; Next_Ex2_state <= ex2_ack1; elsif packet_type = MPI_WIN_SYNC then n_i<=0; wr_ok<='0'; rd_ok<='0'; P_len_i <= switch_port_out_data-2; Next_Ex2_state <= ex2_Wsync; elsif packet_type = MPI_SPAWN then Next_Ex2_state <= ex2_spawn1; wr_ok<='0'; rd_ok<='0'; else Next_Ex2_state <= decode_packet_type; rd_ok<='0'; end if; end if; when decode_packet_type2 => if packet_type = MPI_PUT then Next_Ex2_state <= fetch_addresses; else Next_Ex2_state <= ex2_get1; end if; when fetch_addresses => if n=0 then if switch_data_available = '1' then dest_address_i(15 downto 8) <= switch_port_out_data; Rec_data_i(2)<=switch_port_out_data; n_i <= n + 1; rd_ok<='1'; else rd_ok<='0'; end if; elsif n=1 then if switch_data_available = '1' then dest_address_i(Word-1 downto 0) <= switch_port_out_data; Rec_data_i(3)<=switch_port_out_data; P_len_i <= P_len - 2; Next_Ex2_state <= ex2_put1; n_i<=0; rd_ok<='1'; else rd_ok<='0'; Next_Ex2_state <= fetch_addresses; end if; end if; when ex2_ack1 => rd_ok<='0'; if n<2 then --réception de l'acquittement. n_e:=n; read_nocdat_fsm(switch_data_available,rd_ok,wr_ok,P_len,P_len_i,n_e,n); n_i<=n_e; elsif n=2 then if switch_data_available='1' then n_i<=n+1; rd_ok<='1'; data_to_ram_i<=switch_port_out_data; Result_i<=switch_port_out_data; end if; elsif n=3 then n_i<=n+1;P_G_i<=0; if data_to_ram(7 downto 4)=MPI_PUT then Result_i<=data_to_ram; dest_address_i<=std_logic_vector(to_unsigned(Core_Put_adr,16)); wr_ok<='1'; P_G_i<=1; --put ou get P_len_i<=x"06"; --longueur de l'entête à parcourir elsif data_to_ram(7 downto 4)=MPI_GET then Result_i<=data_to_ram; wr_ok<='1'; -- P_G_i<=2; --put get P_len_i<=x"06";--taille de l'instruction en mémoire dest_address_i<=std_logic_vector(to_unsigned(Core_Get_adr,16)); elsif data_to_ram(7 downto 4)=MPI_SPAWN then Result_i<=data_to_ram; wr_ok<='1'; -- dest_address_i<=std_logic_vector(to_unsigned(Core_Spawn_adr+7,16)); elsif data_to_ram(7 downto 4)=MPI_INIT then Result_i<=data_to_ram; dest_address_i<=std_logic_vector(to_unsigned(Core_Init_adr+7,16)); wr_ok<='1'; -- -- else Result_i<="00000000"; wr_ok<='0'; -- n_i<=n; --code inconnu ! end if; elsif n=4 then if P_G=1 or P_G=2 then Next_ex2_state<=ex2_ack2; else Next_ex2_state<=ex2_ack3; end if; n_i<=0; end if; when Ex2_ack2 =>if unsigned(p_len)>0 then If Dma_rd_grant='1' then if n=0 then n_i<=n+1; --cycle d'attente pour la RAM elsif n=1 then dest_address_i <= dest_address+1; n_i<=2; elsif n>=2 then --creer un délai sur ces signaux par rapport à src_adress n_i<=n+1; rd_ok<='1'; -- if n>1 then dest_address_i <= dest_address+1; p_len_i <= p_len - 1; --end if; Get_Instr_i(n-2)<=Ram_data_out; --deux cycles de retard Next_ex2_state <= ex2_ack2; end if; end if; dma_rd<='1'; rd_ok<='1'; else if P_G=1 then dest_address_i<=std_logic_vector(to_unsigned(Core_Put_adr+7,16)); else dest_address_i<=std_logic_vector(to_unsigned(Core_Get_adr+7,16)); Waited_get_i(ptr_get)(7 downto 0)<=Get_instr(0); --id Waited_get_i(ptr_get)(15 downto 8)<=Get_instr(1); --longueur Waited_get_i(ptr_get)(23 downto 16)<=Get_instr(4); --adr dest bas Waited_get_i(ptr_get)(31 downto 24)<=Get_instr(5); --adr dest haut RGET_i<='1'; Ptr_Get_i<=Ptr_Get+1; --prochain Get à traiter end if; Next_ex2_state <= ex2_ack3; n_i<=0; --suite du process ack rd_ok<='0'; dma_rd<='0'; end if; when ex2_ack3 => if n=0 then --set acknowlege bit of the instruction sb_start<='1'; sb_bitMask<=x"20";--cinquième bit à un sb_bitval<='1'; sb_whole<='0';--Modifier un seul bit ! if sb_done='1' then n_i<=1; sb_start<='0'; sb_bitval<='0'; dest_address_i<=dest_address+1; end if; elsif n=1 then sb_start<='1'; sb_bitMask<=Rec_Data(2); sb_bitval<='1'; sb_whole<='1'; if sb_done='1' then n_i<=n+1; sb_start<='0'; sb_bitval<='0'; sb_whole<='0'; end if; elsif n=2 then Next_Ex2_state<=Ex2_Ready; n_i<=0; end if; when ex2_Wsync => rd_ok<='0'; if n<2 then --réception de la synchronisation. n_e:=n; read_nocdat_fsm(switch_data_available,rd_ok,wr_ok,P_len,P_len_i,n_e,n); n_i<=n_e; elsif n=2 then if switch_data_available='1' then n_i<=n+1; rd_ok<='1'; data_to_ram_i<=switch_port_out_data; Result_i<=switch_port_out_data; end if; elsif n=3 then n_i<=n+1;P_G_i<=0; if data_to_ram(7 downto 4)=SYNC_WSTART then Result_i<=data_to_ram; dest_address_i<=std_logic_vector(to_unsigned(Win0_adr,16)); wr_ok<='1'; P_G_i<=1; --put ou get P_len_i<=x"06"; --longueur de l'entête à parcourir elsif data_to_ram(7 downto 4)=SYNC_WPOST then Result_i<=data_to_ram; wr_ok<='1'; -- P_G_i<=2; --put get P_len_i<=x"06";--taille de l'instruction en mémoire dest_address_i<=std_logic_vector(to_unsigned(Win0_adr,16)); elsif data_to_ram(7 downto 4)=SYNC_WWAIT then Result_i<=data_to_ram; wr_ok<='1'; -- dest_address_i<=std_logic_vector(to_unsigned(Win0_adr+7,16)); elsif data_to_ram(7 downto 4)=SYNC_WCOMP then Result_i<=data_to_ram; dest_address_i<=std_logic_vector(to_unsigned(Win0_adr+W_Gpost,16)); wr_ok<='1'; -- Next_Ex2_State<=Ex2_WCOMP; n_i<=0; else Result_i<="00000000"; wr_ok<='0'; -- n_i<=n; --code inconnu ! end if; end if; when Ex2_Wcomp => dma_rd<='1'; rd_ok<='1'; if n=0 then n_i<=n+1; --cycle d'attente pour la RAM i:=to_integer(unsigned(Rec_Data(0)(3 downto 0))); GComp_i(i)<='1'; elsif n=1 then dest_address_i<=std_logic_vector(to_unsigned(Win0_adr+W_Gpost,16)); If Dma_rd_grant='1' then n_i<=2; end if; elsif n=2 then If Dma_rd_grant='1' then --creer un délai sur ces signaux par rapport à dest_adress n_i<=n+1; rd_ok<='1'; dest_address_i <= dest_address+1; GPost_i(7 downto 0)<=Ram_data_out; --deux cycles de retard else n_i<=1; end if; elsif n=3 then If Dma_rd_grant='1' then --GPost_i(15 downto 8)<=Ram_data_out; --Uncomment if needed n_i<=n+1; rd_ok<='1'; dma_rd<='1'; end if; elsif n=4 then --GPost_i(15 downto 8)<=Ram_data_out; --Uncomment if needed rd_ok<='1'; dma_rd<='1'; n_i<=n+1; elsif n=5 then rd_ok<='0'; dma_rd<='0'; n_i<=0; If GPost=GComp then --le même nombre de post que de COmpleted ? GPost_Set_i<='1'; end if; Next_ex2_state <= ex2_set_busy; end if; when ex2_init1 => if n<2 then -- execution du mpi Init wr_ok<='0'; if switch_data_available='1' then n_i<=n+1; rd_ok<='1'; P_len_i <=P_len-1; Rec_Data_i(n+2)<=switch_port_out_data; data_to_ram_i<=switch_port_out_data; Result_i<=switch_port_out_data; else rd_ok<='0'; n_i<=n; end if; result_i<=(others=>'0'); elsif n=2 then n_i<=n+1; rd_ok<='0'; elsif n=3 then rd_ok<='0'; -- normalement plus rien à lire n_i<=n+1; if Initialized='1' then if data_to_ram(7 downto 4)=INIT_SEEKMAIN then Result_i<=data_to_ram; InitReq_i<='1'; --permet d'activer Init de Ex_4 elsif data_to_ram(7 downto 4)=INIT_STAT then Result_i<=data_to_ram; InitReq_i<='1'; --permet d'activer Init de Ex_4 elsif data_to_ram(7 downto 4)=INIT_REGISTER then Result_i<=data_to_ram; InitReq_i<='0'; --permet d'activer Init de Ex_4 report "Mise à jour des données d'initialisation"; Next_Ex2_state<=ex2_ready; n_i<=0; elsif data_to_ram(7 downto 4)=INIT_SPAWN then Result_i<=data_to_ram; InitReq_i<='1'; --permet d'activer Init de Ex_4 -- il faut mettre à jour l'état de Spawn else Result_i<="00000000"; InitReq_i<='0'; --permet d'activer Init de Ex_4 end if; end if; elsif n=4 then n_i<=n+1; elsif n=5 then if p_len=0 then Next_Ex2_state<=ex2_init2; rd_ok<='0'; else p_len_i <=p_len -1; rd_ok<='1'; --vider le tampon de lecture pour ce paquet ! end if; end if; when ex2_init2=> if n=5 then if AppInitAck='1' then n_i<=n+1; InitReq_i<='0'; Result_i<="00000001"; -- cette valeur permet d'acquitter la fonction Init end if; elsif n=6 then Next_Ex2_state<=Ex2_Ready; n_i<=0; InitReq_i<='0'; end if; when ex2_put1 => rd_ok<='0'; --ne pas autoriser la lecture du switch wr_ok<='0'; dma_rd<='1'; if n=0 then if RGET='1' then Lp: for i in 1 to Max_stack loop -- to Ptr_get normalement if i<=Ptr_Get then if waited_get(i-1)(3 downto 0)=rec_data(0)(3 downto 0) and waited_get(i-1)(15 downto 8)=(rec_data(1)-2) and waited_get(i-1)(23 downto 16)=rec_data(2) and waited_get(i-1)(31 downto 24)=rec_data(3) then if (waited_get(i-1)(7 downto 4)=MPI_GET) and (rec_data(0)(7 downto 4)=MPI_PUT) then match_get_i<='1'; end if; else end if; end if; exit Lp when i= Ptr_get; end loop Lp; end if; n_i<=1; elsif n=1 then if match_get='1' then n_i<=3; --ne pas envoyer ack dans ce cas report "GET Détecté ACK pas envoyé dans Ex2 du HCL n°" & image(pid); else n_i<=2; end if; elsif n=2 then instr_ack_i<='1'; --activer l'envoie de l'accusé de réception data_to_write_fifo_i<=to_fifo_ack; wr_ok<=wr_ack; if sent_ack='1' then n_i<=2; instr_ack_i<='0'; dma_wr<='1'; end if; elsif n=3 then dma_wr<='1'; if dma_wr_grant = '1' then Next_Ex2_state <= ex2_put2; data_to_ram_i<=switch_port_out_data; rd_ok<='0'; n_i<=0; delai:=0; else Next_Ex2_state <= ex2_put1; end if; end if; when ex2_put2 => rd_ok<='0'; n_i<=1; i:=to_integer(unsigned(Rec_Data(0)(3 downto 0))); --Rec_WPost_i(i)<='1'; --indiquer que ce port a emis des données ! if unsigned( P_len) > 0 then if switch_data_available = '1' and delai=0 then delai:=1; --une donné lue P_len_i <= P_len - 1; Next_Ex2_state <= ex2_put2; rd_ok<='1'; data_to_ram_i<=switch_port_out_data; end if; if dma_wr_grant='1' and delai=1 then -- if n=1 then wr_ok<='1'; dest_address_i <= dest_address + 1; delai:=0;--une donnée écrite -- else -- dest_address_i <= dest_address ; -- end if; --if delai=1 then --data_to_ram<=switch_port_out_data; --met en registre la donnée présente sur le port du switch --end if; else dest_address_i<=dest_address; wr_ok<='0'; n_i<=0; end if; Next_Ex2_state <= ex2_put2; else rd_ok<='0'; if dma_wr_grant='1' and n=1 then Next_Ex2_state <= ex2_put3; Wr_ok<='0'; n_i<=0; end if; end if; when ex2_put3 => if dma_rd_grant='1' then dest_address_i<=std_logic_vector(to_unsigned(core_base_adr+4,16)); Next_Ex2_state <= ex2_put4; n_i<=0; rd_ok<='1'; wr_ok<='0'; end if; when ex2_put4 => if n>0 then dma_wr<='1'; --demander un accès exclusif au bus dma_rd<='1'; -- pour éviter une mauvaise mise à jour des données else dma_wr<='0'; dma_rd<='0'; end if; if n=0 then if RGET='1' then L1: for i in 1 to Max_stack loop -- to Ptr_get normalement if i<=Ptr_Get then if waited_get(i-1)(3 downto 0)=rec_data(0)(3 downto 0) and waited_get(i-1)(15 downto 8)=(rec_data(1)-2) and waited_get(i-1)(23 downto 16)=rec_data(2) and waited_get(i-1)(31 downto 24)=rec_data(3) then if (waited_get(i-1)(7 downto 4)=MPI_GET) and (rec_data(0)(7 downto 4)=MPI_PUT) then received_get_i(i-1)<='1'; dest_address_i<=std_logic_vector(to_unsigned(core_base_adr+5,16)); mode_get_i<='1'; match_get_i<='1'; end if; else end if; end if; exit L1 when i= Ptr_get; end loop L1; end if; n_i<=n+1; rd_ok<='1'; wr_ok<='0'; elsif n=1 then if match_get='0' then i:=to_integer(unsigned(Rec_Data(0)(3 downto 0))); Rec_WPost_i(i)<='1'; --indiquer que ce port a emis des données ! end if; if dma_rd_grant='1' then if RGET='1' then --si on est en mode attente d'un Get RGET_i<='0'; --Supposons tous les Gets reçus ! test_wcomp:for i in 1 to Max_stack loop --Tous les Get reçus ? if Ptr_get>=i then if received_get(i-1)='0' then RGET_i<='1'; --Non ! end if; end if; exit test_wcomp when i=Ptr_get; end loop test_wcomp; end if; n_i<=n+1; rd_ok<='1'; else rd_ok<='1'; wr_ok<='0'; end if; elsif n=2 then if dma_rd_grant='1' and dma_wr_grant='1' then n_i<=n+1; tempval:=Ram_data_out; tempval(4):='1'; --SET du bit DReceived if Mode_Get='1' then --si get ack est détecté tempval(6):=RGET; -- Bit 6 Busy=0 si dernier get reçu !! mode_get_i<='1'; end if; data_to_ram_i<=tempval; rd_ok<='0'; wr_ok<='1'; else rd_ok<='1'; wr_ok<='0'; n_i<=0; end if; elsif n=3 then if dma_wr_grant='1' then rd_ok<='0'; wr_ok<='1'; n_i<=n+1; end if; elsif n=4 then if dma_wr_grant='1' then rd_ok<='0'; wr_ok<='1'; n_i<=5; end if; elsif n=5 then Next_Ex2_state <= ex2_set_busy; n_i<=0; rd_ok<='0'; wr_ok<='0'; mode_get_i<='0'; match_get_i<='0'; end if; -- dest_address_i<=std_logic_vector(to_unsigned(core_base_adr+4,16));--Adr de gest de la transaction when ex2_put5 => Next_Ex2_state <= Ex2_Ready; -- fin du mpi_put when ex2_spawn1 => if n<2 then n_e:=n; read_nocdat_fsm(switch_data_available,rd_ok,wr_ok,P_len,P_len_i,n_e,n); n_i<=n_e; Rec_Data_i(2)<=Switch_port_out_data; elsif n=2 then Rec_Data_i(3)<=Switch_port_out_data; Result_i<=Switch_port_out_data; Data_to_ram_i<=Switch_port_out_data; n_i<=n+1; rd_ok<='1'; elsif n=3 then if data_to_ram(7 downto 4)=SPAWN_LOAD then Result_i<=data_to_ram; wr_ok<='1'; --permet d'activer Init de Ex_4 elsif data_to_ram(7 downto 4)=SPAWN_COMP then Result_i<=data_to_ram; wr_ok<='0'; --permet d'activer Init de Ex_4 elsif data_to_ram(7 downto 4)=SPAWN_ERR then Result_i<=data_to_ram; wr_ok<='0'; --permet d'activer Init de Ex_4 else Result_i<=(others=>'0'); end if; n_i<=n+1; rd_ok<='0'; elsif n=4 then wr_ok<='1'; if AppInitAck='1' then wr_ok<='0'; rd_ok<='0'; n_i<=n+1; end if; elsif n=5 then wr_ok<='0'; rd_ok<='0'; n_i<=0; Next_Ex2_state <=Ex2_Ready; end if; when Ex2_Spawn2=> Next_Ex2_state <=Ex2_Ready; when ex2_get1 => rd_ok<='0'; --ne pas autoriser la lecture du switch --ack_state<=next_ack_state; --MAE d'envoie de AR dma_rd<='1'; if n=0 then instr_ack_i<='1'; --activer l'envoie de l'accusé de réception data_to_write_fifo_i<=to_fifo_ack; wr_ok<=wr_ack; if sent_ack='1' then n_i<=1; instr_ack_i<='0'; wr_ok<='0'; --if switch_data_available='1' then rd_ok<='0';-- --P_len<=P_len-1; --end if; end if; elsif n=1 then if switch_data_available='1' then if fifo_full = '0' then -- conversion du get en put en empilement dans le fifo data_to_write_fifo_i <= MPI_PUT & switch_port_out_data(3 downto 0);--la destination du Put wr_ok<='1'; rd_ok<='1'; --autoriser la lecture du crossbar P_len_i<=P_len-1; n_i<=n+1; else Wr_ok<='0'; Rd_ok<='0'; end if; else Wr_ok<='0'; rd_ok<='0'; end if; elsif n=2 then if switch_data_available='1' then if fifo_full = '0' then -- conversion du get en put en empilement dans le fifo --data_to_write_fifo <= MPI_PUT & switch_port_out_data(3 downto 0);--la destination du Put --P_len_i <= P_len-1;--le nombre d'octet qui restent à copier Next_Ex2_state <= ex2_get2; wr_ok<='0'; rd_ok<='0'; --autoriser la lecture du crossbar n_i<=0; else rd_ok<='0'; wr_ok<='0'; end if; else rd_ok<='0'; wr_ok<='0'; end if; end if; when ex2_get2 => if P_len>0 then if fifo_full = '0' and switch_data_available ='1' then data_to_write_fifo_i <= switch_port_out_data;--la longueur initiale du GET p_len_i <= P_len - 1; Next_Ex2_state <= ex2_get2; wr_ok<='1'; Rd_ok<='1'; elsE wr_ok<='0'; Rd_ok<='0'; END IF; else if n=0 then if fifo_full='0' then wr_ok<='0';--une impulsion en plus n_i<=n+1; Next_Ex2_state <= ex2_get2; else wr_ok<='0'; end if; else Next_Ex2_state <= ex2_get3; n_i<=0; wr_ok<='0'; end if; rd_ok<='0'; end if; i:=to_integer(unsigned(Rec_Data(0)(3 downto 0))); Rec_WPost_i(i)<='1'; --indiquer que ce port a emis des données ! --préparer en avance l'adresse de lecture/écriture dest_address_i<=std_logic_vector(to_unsigned(core_base_adr+4,16)); when ex2_get3 => wr_ok<='0'; if dma_rd_grant='1' then -- fin du mpi_get Next_Ex2_state <= ex2_get4; n_i<=0; --activer le bit sending du registre de transfert else Next_Ex2_state <= ex2_get3; end if; dest_address_i<=std_logic_vector(to_unsigned(core_base_adr+4,16)); when ex2_get4 => if n <4 then dma_wr<='1'; --demander un accès exclusif au bus dma_rd<='1'; -- pour éviter une mauvaise mise à jour des données else dma_wr<='0'; dma_rd<='0'; end if; if n=0 then if dma_rd_grant='1' then n_i<=n+1; end if; rd_ok<='1'; wr_ok<='0'; elsif n=1 then if dma_rd_grant='1' then n_i<=n+1; end if; rd_ok<='1'; wr_ok<='0'; data_to_ram_i<=Ram_data_out; elsif n=2 then if dma_rd_grant='1' and dma_wr_grant='1' then n_i<=n+1; tempval:=Ram_data_out; --tempval(2):='1'; --mise à 1 du Bit DSending --tempval(5):='0'; --Mise à 0 du Bit Sent data_to_ram_i(2)<='1'; --mise à 1 du Bit DSending data_to_ram_i(5)<='0'; --Mise à 0 du Bit Sent data_to_ram_i<=tempval; rd_ok<='1'; wr_ok<='0'; else rd_ok<='1'; wr_ok<='0'; n_i<=0; end if; elsif n=3 then if dma_wr_grant = '1' then n_i<=n+1; rd_ok<='0'; wr_ok<='1'; end if; elsif n=4 then if dma_wr_grant = '1' then n_i<=0; Next_Ex2_state <= Ex2_Ready; -- fin du mpi_get else rd_ok<='0'; wr_ok<='1'; --n<=n-1; end if; end if; dest_address_i<=std_logic_vector(to_unsigned(core_base_adr+4,16)); when ex2_Set_Busy => if n=0 then --set busy bit of the instruction dest_address_i<=std_logic_vector(to_unsigned(core_base_adr+4,16)); n_i<=1; if Gpost_Set='1' then if (rec_wpost=gpost) and RGET='0' then Wbusy_i<='0'; Gpost_Set_i<='0'; GComp_i<=(others=>'0'); rec_wpost_i<=(others=>'0');--reset des messages reçu else Wbusy_i<='1'; end if; else n_i<=2; end if; if RGET='1' then WBusy_i<='1'; end if; elsif n=1 then sb_start<='1'; sb_bitMask<=x"40";--6e bit à 1 sb_bitval<=WBusy; if sb_done='1' then n_i<=2; sb_start<='0'; sb_bitval<='0'; end if; elsif n=2 then Next_Ex2_state<=Ex2_Ready; n_i<=0; end if; -- execution du barrier when ex2_barrier1 => if switch_data_available = '1' then pading_data <= switch_port_out_data; Next_Ex2_state <= ex2_barrier2; else Next_Ex2_state <= ex2_barrier1; end if; when ex2_barrier2 => if packet_type = MPI_BARRIER_REACHED then barrier_counter_i <= barrier_counter + 1; Next_Ex2_state <= ex2_barrier4; else Next_Ex2_state <= ex2_barrier3; end if; when ex2_barrier3 => if n < 10 then n_i<= n + 1; Next_Ex2_state <= ex2_barrier3; else Next_Ex2_state <= Ex2_Ready; end if; when ex2_barrier4 => if barrier_counter = nprocs then -- entete du packet MPI_BARRIER_COMPLETED data_to_write_fifo_i <= MPI_BARRIER_COMPLETED & "0000"; Next_Ex2_state <= ex2_barrier5; else Next_Ex2_state <= Ex2_Ready; end if; when ex2_barrier5 => if fifo_full = '0' then -- taille du packet MPI_BARRIER_COMPLETED data_to_write_fifo_i <= "00000011"; Next_Ex2_state <= ex2_barrier6; else Next_Ex2_state <= ex2_barrier5; end if; when ex2_barrier6 => if fifo_full ='0' then -- troisième octet du packet MPI_BARRIER_COMPLETED data_to_write_fifo_i <= "00000000"; Next_Ex2_state <= ex2_barrier7; else Next_Ex2_state <= ex2_barrier6; end if; when ex2_barrier7 => if fifo_full = '0' then barrier_counter_i <= "0000"; Next_Ex2_state <= Ex2_Ready; else Next_Ex2_state <= ex2_barrier7; end if; when others => Next_Ex2_state <= Ex2_Ready; end case; end process; -- sortie de la machine à etat -- ex2_fsm_action : process(Ex2_state, Ex2_on,fifo_full, P_len, data_to_write_fifo, packet_type,Data_To_Ram,Dma_rd,Dma_wr, switch_data_available,switch_port_out_data,sb_ram_data_in,Ram_data_out,rd_ok,wr_ok,sb_ram_wr,sb_ram_rd,sb_dma_wr_request,sb_dma_rd_request, appInitAck,n,InitReq) variable transact : std_logic_vector(Word-1 downto 0); begin -- code fonctionnel sb_ram_data_out<=Ram_data_out; --presque toujours cette valeur case Ex2_state is when Ex2_Ready => fifo_wr_en <= '0'; switch_port_out_rd_en <= '0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; barrier_completed <= '0'; Ram_data_in<=(others=>'0'); Ram_rd<='0'; Ram_wr<='0'; Ready<='1'; AppInitReq<='0'; when fetch_packet_type => fifo_wr_en <= '0'; switch_port_out_rd_en <= rd_ok; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; barrier_completed <= '0'; Ram_data_in<=(others=>'0'); Ram_rd<='0'; Ram_wr<='0'; Ready<='0'; AppInitReq<='0'; when decode_packet_type => fifo_wr_en <= '0'; switch_port_out_rd_en <= rd_ok; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; Ready<='0'; when decode_packet_type2 => fifo_wr_en <= '0'; switch_port_out_rd_en <= '0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; Ready<='0'; when fetch_addresses => fifo_wr_en <= '0'; switch_port_out_rd_en <= rd_ok; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; Ready<='0'; when ex2_ack1 |ex2_Wsync => Ready<='0'; switch_port_out_rd_en<=rd_ok; fifo_wr_en <= '0'; packet_received <= '0'; AppInitReq<='0'; barrier_completed <= '0'; dma_rd_request <= sb_dma_rd_request; dma_wr_request <= sb_dma_wr_request; Ram_rd<=sb_ram_rd; Ram_wr<=sb_ram_wr; sb_ram_data_out<=Ram_data_out; Ram_data_in<=sb_ram_data_in; when ex2_ack2|Ex2_WCOMP => Ready<='0'; switch_port_out_rd_en<='0'; fifo_wr_en <= '0'; packet_received <= '0'; AppInitReq<='0'; barrier_completed <= '0'; dma_rd_request <= dma_rd; dma_wr_request <= '0'; Ram_rd<=rd_ok; Ram_wr<='0'; Ram_data_in<=(others=>'0'); when ex2_ack3 => Ready<='0'; switch_port_out_rd_en<=rd_ok; fifo_wr_en <= '0'; packet_received <= '0'; AppInitReq<='0'; barrier_completed <= '0'; dma_rd_request <= sb_dma_rd_request; dma_wr_request <= sb_dma_wr_request; Ram_rd<=sb_ram_rd; Ram_wr<=sb_ram_wr; sb_ram_data_out<=Ram_data_out; Ram_data_in<=sb_ram_data_in; when ex2_put1 => fifo_wr_en <= wr_ok; switch_port_out_rd_en <= '0'; packet_received <= '0'; dma_wr_request <= dma_wr; dma_rd_request <= dma_rd; Ram_rd<='1'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; Ready<='0'; when ex2_put2 => Ready<='0'; fifo_wr_en <= '0'; switch_port_out_rd_en <=rd_ok; if rd_ok = '1' then Ram_data_in<=switch_port_out_data; else Ram_data_in<=data_to_ram; end if; Ram_wr<=wr_ok; Ram_rd<='0'; packet_received <= '0'; dma_rd_request <= '0'; dma_wr_request <= '1'; AppInitReq<='0'; barrier_completed <= '0'; when ex2_put3 => Ready<='0'; fifo_wr_en <= '0'; switch_port_out_rd_en <='0'; --ne pas corrompre le contenu de la RAM --Ram_data_in<=data_to_ram; Ram_wr<='0'; Ram_rd<='1'; packet_received <= '0'; dma_rd_request <= '1'; dma_wr_request <= '0'; AppInitReq<='0'; barrier_completed <= '0'; Ram_data_in<=(others=>'0'); when ex2_put4 => fifo_wr_en <= '0'; Ready<='0'; switch_port_out_rd_en <= '0'; packet_received <= '1'; dma_rd_request <= dma_rd; dma_wr_request <=dma_wr; Ram_wr<=wr_ok; Ram_rd<=rd_ok; AppInitReq<='0'; barrier_completed <= '0'; Ram_data_in<=data_to_ram;--Ram_data_in or "00000010"; -- le résultat de l'exécution when ex2_put5 => Ready<='0'; switch_port_out_rd_en<='0'; fifo_wr_en <= '0'; packet_received <= '1'; AppInitReq<='0'; barrier_completed <= '0'; dma_rd_request <= dma_rd; dma_wr_request <= dma_wr; Ram_rd<=rd_ok; Ram_wr<=wr_ok; Ram_data_in<=data_to_ram; --Result <=(1=>'1',others=>'0'); --put completed when ex2_get1=> fifo_wr_en <= wr_ok; switch_port_out_rd_en <= rd_ok; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= dma_rd; Ram_rd<='1'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; Ready<='0'; when ex2_get2 => switch_port_out_rd_en <=rd_ok; fifo_wr_en <= Wr_ok; Ready<='0'; packet_received <= '0'; dma_rd_request <= '0'; dma_wr_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; when ex2_get3 => fifo_wr_en <= '0'; Ready<='0'; switch_port_out_rd_en <= '0'; packet_received <= '1'; dma_rd_request <= '1'; dma_wr_request <='0'; Ram_wr<='0'; Ram_rd<='1'; AppInitReq<='0'; barrier_completed <= '0'; Ram_data_in<=(others=>'0'); --Ram_data_out<=Ram_data_in or "00000010"; -- activer le bit DSending when ex2_get4 => Ready<='0'; barrier_completed <= '0'; switch_port_out_rd_en<='0'; fifo_wr_en <= '0'; packet_received <= '1'; AppInitReq<='0'; dma_rd_request <= dma_rd; dma_wr_request <= dma_wr; Ram_rd<=rd_ok; Ram_wr<=wr_ok; Ram_data_in<=data_to_ram; --activer le bit DSending when ex2_barrier1 => fifo_wr_en <= '0'; switch_port_out_rd_en <= switch_data_available; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; Ready<='0'; AppInitReq<='0'; when ex2_barrier2 => fifo_wr_en <= '0'; Ready<='0'; switch_port_out_rd_en <='0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; when ex2_barrier3 => fifo_wr_en <= '0'; switch_port_out_rd_en <='0'; Ready<='0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '1'; AppInitReq<='0'; when ex2_barrier4 => fifo_wr_en <= '0'; switch_port_out_rd_en <='0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; Ready<='0'; when ex2_barrier5 => fifo_wr_en <= not(fifo_full); switch_port_out_rd_en <='0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; Ready<='0'; when ex2_barrier6 => fifo_wr_en <= not(fifo_full); switch_port_out_rd_en <= '0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; Ready<='0'; when ex2_barrier7 => fifo_wr_en <= not(fifo_full); switch_port_out_rd_en <= '0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; Ram_data_in<=(others=>'0'); barrier_completed <= '0'; AppInitReq<='0'; Ready<='0'; when ex2_spawn1 => fifo_wr_en <= '0'; switch_port_out_rd_en <= rd_ok;--switch_data_available; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; barrier_completed <= '0'; Ready<='0'; Ram_data_in<=(others =>'0'); AppInitReq<=wr_ok; when ex2_Spawn2 => Ready<='0'; fifo_wr_en <= '0'; switch_port_out_rd_en <='0'; Ram_data_in<=data_to_ram; Ram_wr<=wr_ok; Ram_rd<='0'; packet_received <= '0'; dma_rd_request <= '0'; dma_wr_request <= '1'; AppInitReq<='0'; barrier_completed <= '0'; when ex2_init1 => fifo_wr_en <= '0'; switch_port_out_rd_en <= rd_ok;--switch_data_available; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; barrier_completed <= '0'; Ready<='0'; Ram_data_in<=(others =>'0'); AppInitReq<=InitReq; when ex2_init2 => fifo_wr_en <= '0'; switch_port_out_rd_en <='0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; Ram_rd<='0'; Ram_wr<='0'; barrier_completed <= '0'; Ram_data_in<=(others =>'0'); AppInitReq<= not(AppInitAck); Ready<='0'; when ex2_Set_Busy => Ready<='0'; switch_port_out_rd_en<='0'; fifo_wr_en <= '0'; packet_received <= '0'; AppInitReq<='0'; barrier_completed <= '0'; dma_rd_request <= sb_dma_rd_request; dma_wr_request <= sb_dma_wr_request; Ram_rd<=sb_ram_rd; Ram_wr<=sb_ram_wr; sb_ram_data_out<=Ram_data_out; Ram_data_in<=sb_ram_data_in; when others => Ready<='1'; -- le module est à nouveau libre fifo_wr_en <= '0'; switch_port_out_rd_en <= '0'; packet_received <= '0'; dma_wr_request <= '0'; dma_rd_request <= '0'; barrier_completed <= '0'; Ram_data_in<=(others=>'0'); Ram_rd<='0'; Ram_wr<='0'; Ready<='1'; AppInitReq<='0'; end case; end process; ex2_fsm_sync:process(clk,reset) begin if reset = '1' then ex2_state <= Ex2_Ready; ack_state<=ack0; --MAE d'envoie de AR n<=0; P_len<=(others=>'0'); GPost<=(others =>'0'); else if rising_edge(clk) then ex2_state<=next_ex2_state; ack_state<=next_ack_state; --MAE d'envoie de AR n<=n_i; P_len<=P_len_i; Packet_type<=packet_type_i; P_G<=P_G_i; Result1<=Result_i; --juste une copie dest_address <= dest_address_i; data_to_write_fifo<=data_to_write_fifo_i; WBUSY<=WBUSY_i; RGET<=RGET_i; InitReq<=InitReq_i; mode_get<=mode_get_i; match_get<=match_get_i; Sent_ack<=sent_ack_i; Instr_ack<=Instr_ack_i; Ptr_Get<=Ptr_Get_i; Rec_Wpost<=Rec_WPost_i; dest_ack<=dest_ack_i; barrier_counter<=barrier_counter_i; GPost<=GPost_i; GComp<=GComp_i; Received_get<=Received_get_i; GPost_set<=GPost_Set_i; data_to_ram<=data_to_ram_i; For i in 0 to Max_stack loop Waited_get(i)<=Waited_get_i(i); end loop; For i in 0 to 7 loop Get_Instr(i)<=Get_instr_i(i); end loop; for i in 0 to 3 loop Rec_Data(i)<=Rec_Data_i(i); end loop; end if; end if; end process ex2_fsm_sync; snd_ack:process (ack_state,reset,fifo_full,instr_ack,Dest_Ack,apprank,Packet_type,ram_data_out,dma_rd_grant) --ce processus est chargé d'emettre l'accusé de réception pour chaque instruction reçu begin -- if rising_edge(clk) then Sent_ack_i<='0'; --pas besoin de le mémoriser wr_ack<='0'; --valeur par défaut ack_address<=Std_logic_vector(to_unsigned(Core_Base_Adr+4+W_Gpost,Adrlen)); if reset='1' then next_ack_state<=ack0; to_fifo_ack<=(others=>'1'); else next_ack_state<=ack_state; case ack_state is when ack0 =>to_fifo_ack<=(others=>'0'); Wr_ack<='0'; if instr_ack='1' then next_ack_state<=ack_readwait; to_fifo_ack <= MPI_ACK & Dest_ack; wr_ack<='0'; end if; sent_ack_i<='0'; when ack_readwait => to_fifo_ack <= MPI_ACK & Dest_ack; ack_address<=Std_logic_vector(to_unsigned(Core_Base_Adr+4+W_Gpost,Adrlen)); --vérifier WinPost attend bien une action de cette source if dma_rd_grant='1' then next_ack_state<=ack_checkwait; end if; when ack_checkwait => to_fifo_ack <= MPI_ACK & Dest_ack; ack_address<=Std_logic_vector(to_unsigned(Core_Base_Adr+4+W_Gpost,Adrlen)); if dma_rd_grant='1' and ram_data_out(conv_integer(dest_ack))='1' then next_ack_state<=ack1; elsif dma_rd_grant='0' then next_ack_state<=ack_readwait; else next_ack_state<=ack6; --pas d'acknowledge à envoyer assert true report "Packet non attendu de cette source !" severity failure; end if; when ack1 => if fifo_full = '0' then -- conversion envoie lack à l'emetteur -- en empilement dans le fifo to_fifo_ack <= MPI_ACK & Dest_ack; next_ack_state <= ack2; wr_ack<='1'; else wr_ack<='0'; end if; sent_ack_i<='0'; to_fifo_ack <= MPI_ACK & Dest_ack; when ack2 => if fifo_full = '0' then to_fifo_ack <= "00000100";--la longueur next_ack_state <= ack3; wr_ack<='1'; else -- next_ack_state <= ack2; wr_ack<='0'; end if; to_fifo_ack <= "00000100"; sent_ack_i<='0'; when ack3 => if fifo_full = '0' then to_fifo_ack <= "00000000";-- next_ack_state <= ack4; wr_ack<='1'; else -- next_ack_state <= ack3; wr_ack<='0'; end if; to_fifo_ack <= "00000000"; sent_ack_i<='0'; when ack4 => if fifo_full = '0' then to_fifo_ack <=packet_type & apprank ;--l'instruction et le rang de lacquitteur next_ack_state <= ack5; wr_ack<='1'; sent_ack_i<='0'; else -- next_ack_state <= ack4; wr_ack<='0'; sent_ack_i<='0'; end if; to_fifo_ack <=packet_type & apprank ; when ack5 => if Instr_ack='0' then --dernier pulse next_ack_state <= ack0; else next_ack_state <= ack6; end if; wr_ack<='0'; sent_ack_i<='1'; to_fifo_ack<=(others=>'1'); when ack6 => if Instr_ack='0' then next_ack_state <= ack0; end if; wr_ack<='0'; sent_ack_i<='1'; to_fifo_ack<=(others=>'1'); end case; end if; --end if; end process; end Behavioral;