/*
 * $Id$
 *
 * [ Description ]
 * 
 */

#include "Behavioural/Core/Multi_Execute_loop/Execute_loop/Multi_Write_unit/Write_unit/Write_queue/include/Write_queue.h"
#include "Behavioural/include/Allocation.h"

namespace morpheo                    {
namespace behavioural {
namespace core {
namespace multi_execute_loop {
namespace execute_loop {
namespace multi_write_unit {
namespace write_unit {
namespace write_queue {


#undef  FUNCTION
#define FUNCTION "Write_queue::allocation"
  void Write_queue::allocation (void)
  {
    string rename;

    log_printf(FUNC,Write_queue,FUNCTION,"Begin");

    _component   = new Component (_usage);

    Entity * entity = _component->set_entity (_name       
					      ,"Write_queue"
#ifdef POSITION
					      ,COMBINATORY 
#endif
					      );

    _interfaces = entity->set_interfaces();

    // ~~~~~[ Interface : "" ]~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

      Interface * interface = _interfaces->set_interface(""
#ifdef POSITION
							 ,IN
							 ,SOUTH,
							 "Generalist interface"
#endif
							 );

     in_CLOCK        = interface->set_signal_clk              ("clock" ,1, CLOCK_VHDL_YES);
     in_NRESET       = interface->set_signal_in  <Tcontrol_t> ("nreset",1, RESET_VHDL_YES);

    // -----[ Interface "Write_queue_in" ]--------------------------------    
     {
       ALLOC_INTERFACE ("write_queue_in", IN, WEST, "Input of write_queue");
       
       ALLOC_VAL_IN    ( in_WRITE_QUEUE_IN_VAL);
       ALLOC_ACK_OUT   (out_WRITE_QUEUE_IN_ACK);
       if(_param->_have_port_context_id)
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_CONTEXT_ID   ,"context_id"   ,Tcontext_t        ,_param->_size_context_id       );
       if(_param->_have_port_front_end_id)
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_FRONT_END_ID ,"front_end_id" ,Tcontext_t        ,_param->_size_front_end_id     );
       if(_param->_have_port_ooo_engine_id)
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_OOO_ENGINE_ID,"ooo_engine_id",Tcontext_t        ,_param->_size_ooo_engine_id    );
       if(_param->_have_port_packet_id)
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_PACKET_ID    ,"packet_id"    ,Tpacket_t         ,_param->_size_packet_id        );
//     ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_OPERATION    ,"operation"    ,Toperation_t      ,_param->_size_operation        );
//     ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_TYPE         ,"type"         ,Ttype_t           ,_param->_size_type             );
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_WRITE_RD     ,"write_rd"     ,Tcontrol_t        ,1                              );
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_NUM_REG_RD   ,"num_reg_rd"   ,Tgeneral_address_t,_param->_size_general_register );
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_DATA_RD      ,"data_rd"      ,Tgeneral_data_t   ,_param->_size_general_data     );
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_WRITE_RE     ,"write_re"     ,Tcontrol_t        ,1                              );
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_NUM_REG_RE   ,"num_reg_re"   ,Tspecial_address_t,_param->_size_special_register );
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_DATA_RE      ,"data_re"      ,Tspecial_data_t   ,_param->_size_special_data     );
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_EXCEPTION    ,"exception"    ,Texception_t      ,_param->_size_exception        );
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_NO_SEQUENCE  ,"no_sequence"  ,Tcontrol_t        ,1                              );
       ALLOC_SIGNAL_IN ( in_WRITE_QUEUE_IN_ADDRESS      ,"address"      ,Tgeneral_data_t   ,_param->_size_general_data     );
     }

    // -----[ Interface "Write_queue_out" ]-------------------------------
     {
       ALLOC_INTERFACE ("write_queue_out", OUT, EAST, "Output of write_queue");
       
       ALLOC_VAL_OUT   (out_WRITE_QUEUE_OUT_VAL);
       ALLOC_ACK_IN    ( in_WRITE_QUEUE_OUT_ACK);
       if(_param->_have_port_context_id)
       ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_CONTEXT_ID   ,"context_id"   ,Tcontext_t     ,_param->_size_context_id   );
       if(_param->_have_port_front_end_id)
       ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_FRONT_END_ID ,"front_end_id" ,Tcontext_t     ,_param->_size_front_end_id );
       if(_param->_have_port_ooo_engine_id)
       ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_OOO_ENGINE_ID,"ooo_engine_id",Tcontext_t     ,_param->_size_ooo_engine_id);
       if(_param->_have_port_packet_id)
       ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_PACKET_ID    ,"packet_id"    ,Tpacket_t      ,_param->_size_packet_id    );
//     ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_OPERATION    ,"operation"    ,Toperation_t   ,_param->_size_operation    );
//     ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_TYPE         ,"type"         ,Ttype_t        ,_param->_size_type         );
       ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_FLAGS        ,"flags"        ,Tspecial_data_t,_param->_size_special_data );
       ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_EXCEPTION    ,"exception"    ,Texception_t   ,_param->_size_exception    );
       ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_NO_SEQUENCE  ,"no_sequence"  ,Tcontrol_t     ,1                          );
       ALLOC_SIGNAL_OUT(out_WRITE_QUEUE_OUT_ADDRESS      ,"address"      ,Tgeneral_data_t,_param->_size_general_data );
     }

    // -----[ Interface "gpr_write" ]-------------------------------------
     {
       ALLOC1_INTERFACE("gpr_write", OUT, SOUTH ,"Output of write_queue", _param->_nb_gpr_write);

       ALLOC1_VAL_OUT   (out_GPR_WRITE_VAL          ,_param->_nb_gpr_write);
       ALLOC1_ACK_IN    ( in_GPR_WRITE_ACK          ,_param->_nb_gpr_write);
       if(_param->_have_port_ooo_engine_id)
       ALLOC1_SIGNAL_OUT(out_GPR_WRITE_OOO_ENGINE_ID,"ooo_engine_id",Tcontext_t        ,_param->_size_ooo_engine_id   ,_param->_nb_gpr_write);
       ALLOC1_SIGNAL_OUT(out_GPR_WRITE_NUM_REG      ,"num_reg"      ,Tgeneral_address_t,_param->_size_general_register,_param->_nb_gpr_write);
       ALLOC1_SIGNAL_OUT(out_GPR_WRITE_DATA         ,"data"         ,Tgeneral_data_t   ,_param->_size_general_data    ,_param->_nb_gpr_write);
     }

    // -----[ Interface "spr_write" ]-------------------------------------
     {
       ALLOC1_INTERFACE("spr_write", OUT, SOUTH ,"Output of write_queue", _param->_nb_spr_write);

       ALLOC1_VAL_OUT   (out_SPR_WRITE_VAL          ,_param->_nb_spr_write);
       ALLOC1_ACK_IN    ( in_SPR_WRITE_ACK          ,_param->_nb_spr_write);
       if(_param->_have_port_ooo_engine_id)
       ALLOC1_SIGNAL_OUT(out_SPR_WRITE_OOO_ENGINE_ID,"ooo_engine_id",Tcontext_t        ,_param->_size_ooo_engine_id   ,_param->_nb_spr_write);
       ALLOC1_SIGNAL_OUT(out_SPR_WRITE_NUM_REG      ,"num_reg"      ,Tspecial_address_t,_param->_size_special_register,_param->_nb_spr_write);
       ALLOC1_SIGNAL_OUT(out_SPR_WRITE_DATA         ,"data"         ,Tspecial_data_t   ,_param->_size_special_data    ,_param->_nb_spr_write);
     }

    // -----[ Interface "bypass_write" ]----------------------------------
     {
       ALLOC1_INTERFACE("bypass_write", OUT, NORTH ,"Output of internal write_queue", _param->_size_queue);
       
       if(_param->_have_port_ooo_engine_id)
       ALLOC1_SIGNAL_OUT(out_BYPASS_WRITE_OOO_ENGINE_ID,"ooo_engine_id",Tcontext_t        ,_param->_size_ooo_engine_id   , _param->_nb_bypass_write);
       ALLOC1_SIGNAL_OUT(out_BYPASS_WRITE_GPR_VAL      ,"gpr_val"      ,Tcontrol_t        ,1                             , _param->_nb_bypass_write);
       ALLOC1_SIGNAL_OUT(out_BYPASS_WRITE_GPR_NUM_REG  ,"gpr_num_reg"  ,Tgeneral_address_t,_param->_size_general_register, _param->_nb_bypass_write);
       ALLOC1_SIGNAL_OUT(out_BYPASS_WRITE_GPR_DATA     ,"gpr_data"     ,Tgeneral_data_t   ,_param->_size_general_data    , _param->_nb_bypass_write);
       ALLOC1_SIGNAL_OUT(out_BYPASS_WRITE_SPR_VAL      ,"spr_val"      ,Tcontrol_t        ,1                             , _param->_nb_bypass_write);
       ALLOC1_SIGNAL_OUT(out_BYPASS_WRITE_SPR_NUM_REG  ,"spr_num_reg"  ,Tspecial_address_t,_param->_size_special_register, _param->_nb_bypass_write);
       ALLOC1_SIGNAL_OUT(out_BYPASS_WRITE_SPR_DATA     ,"spr_data"     ,Tspecial_data_t   ,_param->_size_special_data    , _param->_nb_bypass_write);
     }
    // ~~~~~[ Component ]~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~    

  _queue = new list<write_queue_entry_t *>;

#ifdef POSITION
    _component->generate_file();
#endif

    log_printf(FUNC,Write_queue,FUNCTION,"End");
  };

}; // end namespace write_queue
}; // end namespace write_unit
}; // end namespace multi_write_unit
}; // end namespace execute_loop
}; // end namespace multi_execute_loop
}; // end namespace core

}; // end namespace behavioural
}; // end namespace morpheo              
