#ifdef SYSTEMC
/*
 * $Id: Dcache_Access_genMealy_rsp.cpp 94 2008-12-15 11:04:03Z rosiere $
 *
 * [ Description ]
 * 
 */

#include "Behavioural/Core/Dcache_Access/include/Dcache_Access.h"

namespace morpheo                    {
namespace behavioural {
namespace core {
namespace dcache_access {


#undef  FUNCTION
#define FUNCTION "Dcache_Access::genMealy_rsp"
  void Dcache_Access::genMealy_rsp (void)
  {
    log_begin(Dcache_Access,FUNCTION);

    Tcontrol_t lsq_rsp_val [_param->_nb_execute_loop][_param->_max_nb_load_store_unit][_param->_max_nb_cache_access];
    for (uint32_t i=0; i<_param->_nb_execute_loop; ++i)
      for (uint32_t j=0; j<_param->_nb_load_store_unit[i]; ++j)
	for (uint32_t k=0; k<_param->_nb_cache_access [i][j]; ++k)
	  lsq_rsp_val [i][j][k] = 0;

    for (uint32_t i=0; i<_param->_nb_dcache_port; ++i)
      {
	Tcontrol_t val = PORT_READ(in_DCACHE_RSP_VAL [i]);
	Tcontrol_t ack;
	
	if (val)
	  {
            Tcontext_t thread_id = (_param->_have_port_dcache_thread_id)?PORT_READ(in_DCACHE_RSP_THREAD_ID [i]):0;
            Tcontext_t packet_id = (_param->_have_port_dcache_packet_id)?PORT_READ(in_DCACHE_RSP_PACKET_ID [i]):0;

	    Tcontext_t execute_loop_id     = _param->_translate_thread_to_execute_loop    [thread_id];
	    Tcontext_t load_store_unit_id  = _param->_translate_thread_to_load_store_unit [thread_id];
            Tcontext_t context_id          = _param->_translate_thread_to_context         [thread_id];

	    Tpacket_t  cache_access_id     = (packet_id >> _param->_shift_num_cache_access   ) & _param->_mask_num_cache_access;
	    Tpacket_t  lsq_packet_id       =  packet_id                                        & _param->_mask_num_lsq_packet;

// 	    log_printf(TRACE,Dcache_Access,FUNCTION,"thread_id          : %d",thread_id);
// 	    log_printf(TRACE,Dcache_Access,FUNCTION,"execute_loop_id    : %d",execute_loop_id);
// 	    log_printf(TRACE,Dcache_Access,FUNCTION,"load_store_unit_id : %d",load_store_unit_id);
// 	    log_printf(TRACE,Dcache_Access,FUNCTION,"cache_access_id    : %d",cache_access_id);
	    
#ifdef DEBUG_TEST
	    if (execute_loop_id > _param->_nb_execute_loop)
	      throw ERRORMORPHEO(FUNCTION,_("invalid execute_loop_id.\n"));

	    if (load_store_unit_id > _param->_nb_load_store_unit[execute_loop_id])
	      throw ERRORMORPHEO(FUNCTION,_("invalid load_store_unit_id.\n"));

	    if (context_id > _param->_nb_context[execute_loop_id])
	      throw ERRORMORPHEO(FUNCTION,_("invalid context_id.\n"));

	    if (cache_access_id > _param->_nb_cache_access[execute_loop_id][load_store_unit_id])
	      throw ERRORMORPHEO(FUNCTION,_("invalid cache_access_id.\n"));

	    if (_param->_table_routing [execute_loop_id][load_store_unit_id][cache_access_id] != i)
	      throw ERRORMORPHEO(FUNCTION,_("invalid route.\n"));
#endif

	    ack = PORT_READ(in_LSQ_RSP_ACK [execute_loop_id][load_store_unit_id][cache_access_id]);
	    
	    lsq_rsp_val [execute_loop_id][load_store_unit_id][cache_access_id] = 1;

	    if (_param->_have_port_lsq_thread_id [execute_loop_id][load_store_unit_id])
	    PORT_WRITE(out_LSQ_RSP_THREAD_ID   [execute_loop_id][load_store_unit_id][cache_access_id], context_id);
	    if (_param->_have_port_lsq_packet_id [execute_loop_id][load_store_unit_id])
	    PORT_WRITE(out_LSQ_RSP_PACKET_ID   [execute_loop_id][load_store_unit_id][cache_access_id], lsq_packet_id);
	    PORT_WRITE(out_LSQ_RSP_RDATA       [execute_loop_id][load_store_unit_id][cache_access_id], PORT_READ(in_DCACHE_RSP_RDATA       [i]));
	    PORT_WRITE(out_LSQ_RSP_ERROR       [execute_loop_id][load_store_unit_id][cache_access_id], PORT_READ(in_DCACHE_RSP_ERROR       [i]));
	  }
	else
	  ack = 0;
		
	PORT_WRITE(out_DCACHE_RSP_ACK [i],ack);
      }

    for (uint32_t i=0; i<_param->_nb_execute_loop; ++i)
      for (uint32_t j=0; j<_param->_nb_load_store_unit[i]; ++j)
	for (uint32_t k=0; k<_param->_nb_cache_access [i][j]; ++k)
	  PORT_WRITE(out_LSQ_RSP_VAL [i][j][k], lsq_rsp_val [i][j][k]);

    log_end(Dcache_Access,FUNCTION);
  };

}; // end namespace dcache_access
}; // end namespace core

}; // end namespace behavioural
}; // end namespace morpheo              
#endif
