#ifdef SYSTEMC //#if defined(STATISTICS) or defined(VHDL_TESTBENCH) /* * $Id$ * * [ Description ] * */ #include "Behavioural/Core/Multi_Execute_loop/Execute_loop/Multi_Read_unit/Read_unit/Reservation_station/include/Reservation_station.h" namespace morpheo { namespace behavioural { namespace core { namespace multi_execute_loop { namespace execute_loop { namespace multi_read_unit { namespace read_unit { namespace reservation_station { #define dump_queue() \ do\ {\ log_printf(TRACE,Reservation_station,FUNCTION," * dump queue");\ log_printf(TRACE,Reservation_station,FUNCTION," * nb_elt : %d",_queue_nb_elt);\ for (uint32_t j=0;j<_param->_size_queue; j++)\ {\ cout << "\t"\ << "[" << (*_queue_control)[j] << "] "\ << "{" << _queue[(*_queue_control)[j]]._packet_id << " - "<< _queue[(*_queue_control)[j]]._context_id << "} "\ << _queue[(*_queue_control)[j]]._data_ra_val << ", "\ << _queue[(*_queue_control)[j]]._num_reg_ra << " - "\ << _queue[(*_queue_control)[j]]._data_rb_val << ","\ << _queue[(*_queue_control)[j]]._num_reg_rb << " - "\ << _queue[(*_queue_control)[j]]._data_rc_val << ","\ << _queue[(*_queue_control)[j]]._num_reg_rc \ << endl;\ }\ } while (0) #undef FUNCTION #define FUNCTION "Reservation_station::transition" void Reservation_station::transition (void) { log_printf(FUNC,Reservation_station,FUNCTION,"Begin"); if (PORT_READ(in_NRESET) == 0) { // clear all element in control. _queue_nb_elt = 0; _queue_control->clear(); for (uint32_t i=0; i<_param->_size_queue; i++) _queue_control->push_back(i); } else { // ***** PUSH to reservation station if ((PORT_READ(in_RESERVATION_STATION_IN_VAL) == 1) and ( internal_RESERVATION_STATION_IN_ACK == 1)) { log_printf(TRACE,Reservation_station,FUNCTION,"PUSH"); // Write in reservation station uint32_t index = (*_queue_control)[_queue_nb_elt]; _queue_nb_elt ++; log_printf(TRACE,Reservation_station,FUNCTION," * index : %d",index); _queue[index]._context_id = PORT_READ(in_RESERVATION_STATION_IN_CONTEXT_ID ); _queue[index]._packet_id = PORT_READ(in_RESERVATION_STATION_IN_PACKET_ID ); _queue[index]._operation = PORT_READ(in_RESERVATION_STATION_IN_OPERATION ); _queue[index]._type = PORT_READ(in_RESERVATION_STATION_IN_TYPE ); _queue[index]._has_immediat = PORT_READ(in_RESERVATION_STATION_IN_HAS_IMMEDIAT); _queue[index]._immediat = PORT_READ(in_RESERVATION_STATION_IN_IMMEDIAT ); // _queue[index]._read_ra = PORT_READ(in_RESERVATION_STATION_IN_READ_RA ); _queue[index]._num_reg_ra = PORT_READ(in_RESERVATION_STATION_IN_NUM_REG_RA ); _queue[index]._data_ra_val = PORT_READ(in_RESERVATION_STATION_IN_DATA_RA_VAL ); _queue[index]._data_ra = PORT_READ(in_RESERVATION_STATION_IN_DATA_RA ); // _queue[index]._read_rb = PORT_READ(in_RESERVATION_STATION_IN_READ_RB ); _queue[index]._num_reg_rb = PORT_READ(in_RESERVATION_STATION_IN_NUM_REG_RB ); _queue[index]._data_rb_val = PORT_READ(in_RESERVATION_STATION_IN_DATA_RB_VAL ); _queue[index]._data_rb = PORT_READ(in_RESERVATION_STATION_IN_DATA_RB ); // _queue[index]._read_rc = PORT_READ(in_RESERVATION_STATION_IN_READ_RC ); _queue[index]._num_reg_rc = PORT_READ(in_RESERVATION_STATION_IN_NUM_REG_RC ); _queue[index]._data_rc_val = PORT_READ(in_RESERVATION_STATION_IN_DATA_RC_VAL ); _queue[index]._data_rc = PORT_READ(in_RESERVATION_STATION_IN_DATA_RC ); _queue[index]._write_rd = PORT_READ(in_RESERVATION_STATION_IN_WRITE_RD ); _queue[index]._num_reg_rd = PORT_READ(in_RESERVATION_STATION_IN_NUM_REG_RD ); _queue[index]._write_re = PORT_READ(in_RESERVATION_STATION_IN_WRITE_RE ); _queue[index]._num_reg_re = PORT_READ(in_RESERVATION_STATION_IN_NUM_REG_RE ); // dump_queue(); } // ***** POP from reservation station // scan in reverse order, because when we pop the queue there are an auto reorder for (int32_t i=(static_cast(_queue_nb_elt))-1;i>=0; i--) { uint32_t index = (*_queue_control)[i]; if (( internal_RESERVATION_STATION_OUT_VAL [index] == 1) and (PORT_READ(in_RESERVATION_STATION_OUT_ACK [index]) == 1)) { log_printf(TRACE,Reservation_station,FUNCTION,"POP [%d]",i); _queue_control->erase (_queue_control->begin()+i); _queue_control->push_back(index); _queue_nb_elt --; log_printf(TRACE,Reservation_station,FUNCTION," * index : %d",index); // dump_queue(); } } // ***** Bypass // Note : we can take this sequence code before the PUSH in the queue, because read_queue make the bypass !!! // scan all entry for (uint32_t i=0; i<_queue_nb_elt; i++) { uint32_t index = (*_queue_control)[i]; // ***** bypass - gpr_write for (uint32_t j=0; j<_param->_nb_gpr_write; j++) { if ((PORT_READ(in_GPR_WRITE_VAL [j]) == 1) and (PORT_READ(in_GPR_WRITE_CONTEXT_ID [j]) == _queue[index]._context_id)) { if (PORT_READ(in_GPR_WRITE_NUM_REG [j]) == _queue[index]._num_reg_ra) { log_printf(TRACE,Reservation_station,FUNCTION," -> GPR_WRITE [%d] - Hit queue[%d]-GPR_RA[%d]",i,index,_queue[index]._num_reg_ra); _queue[index]._data_ra_val = 1; _queue[index]._data_ra = PORT_READ(in_GPR_WRITE_DATA [j]); } if (PORT_READ(in_GPR_WRITE_NUM_REG [j]) == _queue[index]._num_reg_rb) { log_printf(TRACE,Reservation_station,FUNCTION," -> GPR_WRITE [%d] - Hit queue[%d]-GPR_RB[%d]",i,index,_queue[index]._num_reg_rb); _queue[index]._data_rb_val = 1; _queue[index]._data_rb = PORT_READ(in_GPR_WRITE_DATA [j]); } } } // ***** bypass - spr_write for (uint32_t j=0; j<_param->_nb_spr_write; j++) { if ((PORT_READ(in_SPR_WRITE_VAL [j]) == 1) and (PORT_READ(in_SPR_WRITE_CONTEXT_ID [j]) == _queue[index]._context_id) and (PORT_READ(in_SPR_WRITE_NUM_REG [j]) == _queue[index]._num_reg_rc)) { log_printf(TRACE,Reservation_station,FUNCTION," -> SPR_WRITE [%d] - Hit queue[%d]-SPR_RC[%d]",i,index,_queue[index]._num_reg_rc); _queue[index]._data_rc_val = 1; _queue[index]._data_rc = PORT_READ(in_SPR_WRITE_DATA [j]); } } // ***** bypass - bypass_write for (uint32_t j=0; j<_param->_nb_bypass_write; j++) { if (PORT_READ(in_BYPASS_WRITE_CONTEXT_ID [j]) == _queue[index]._context_id) { if (PORT_READ(in_BYPASS_WRITE_GPR_VAL [j]) == 1) { if (PORT_READ(in_BYPASS_WRITE_GPR_NUM_REG[j]) == _queue[index]._num_reg_ra) { log_printf(TRACE,Reservation_station,FUNCTION," -> BYPASS_WRITE [%d] - Hit queue[%d]-GPR_RA[%d]",i,index,_queue[index]._num_reg_ra); _queue[index]._data_ra_val = 1; _queue[index]._data_ra = PORT_READ(in_BYPASS_WRITE_GPR_DATA [j]); } if (PORT_READ(in_BYPASS_WRITE_GPR_NUM_REG [j]) == _queue[index]._num_reg_rb) { log_printf(TRACE,Reservation_station,FUNCTION," -> BYPASS_WRITE [%d] - Hit queue[%d]-GPR_RB[%d]",i,index,_queue[index]._num_reg_rb); _queue[index]._data_rb_val = 1; _queue[index]._data_rb = PORT_READ(in_BYPASS_WRITE_GPR_DATA [j]); } } if ((PORT_READ(in_BYPASS_WRITE_SPR_VAL [j]) == 1) and (PORT_READ(in_BYPASS_WRITE_SPR_NUM_REG[j]) == _queue[index]._num_reg_rc)) { log_printf(TRACE,Reservation_station,FUNCTION," -> BYPASS_WRITE [%d] - Hit queue[%d]-SPR_RC[%d]",i,index,_queue[index]._num_reg_rc); _queue[index]._data_rc_val = 1; _queue[index]._data_rc = PORT_READ(in_BYPASS_WRITE_SPR_DATA [j]); } } } // ***** bypass - bypass_memory for (uint32_t j=0; j<_param->_nb_bypass_memory; j++) { if ((PORT_READ(in_BYPASS_MEMORY_VAL [j]) == 1) and (PORT_READ(in_BYPASS_MEMORY_CONTEXT_ID [j]) == _queue[index]._context_id)) { if (PORT_READ(in_BYPASS_MEMORY_NUM_REG [j]) == _queue[index]._num_reg_ra) { log_printf(TRACE,Reservation_station,FUNCTION," -> BYPASS_MEMORY [%d] - Hit queue[%d]-GPR_RA[%d]",i,index,_queue[index]._num_reg_ra); _queue[index]._data_ra_val = 1; _queue[index]._data_ra = PORT_READ(in_BYPASS_MEMORY_DATA [j]); } if (PORT_READ(in_BYPASS_MEMORY_NUM_REG [j]) == _queue[index]._num_reg_rb) { log_printf(TRACE,Reservation_station,FUNCTION," -> BYPASS_MEMORY [%d] - Hit queue[%d]-GPR_RB[%d]",i,index,_queue[index]._num_reg_rb); _queue[index]._data_rb_val = 1; _queue[index]._data_rb = PORT_READ(in_BYPASS_MEMORY_DATA [j]); } } } } } #ifdef STATISTICS _stat->add(); #endif #ifdef VHDL_TESTBENCH vhdl_testbench_transition (); #endif log_printf(FUNC,Reservation_station,FUNCTION,"End"); }; }; // end namespace reservation_station }; // end namespace read_unit }; // end namespace multi_read_unit }; // end namespace execute_loop }; // end namespace multi_execute_loop }; // end namespace core }; // end namespace behavioural }; // end namespace morpheo #endif //#endif