#ifdef SYSTEMC /* * $Id$ * * [ Description ] * */ #include "Behavioural/Core/Multi_Front_end/Front_end/Prediction_unit/Return_Address_Stack/include/Return_Address_Stack.h" namespace morpheo { namespace behavioural { namespace core { namespace multi_front_end { namespace front_end { namespace prediction_unit { namespace return_address_stack { #undef FUNCTION #define FUNCTION "Return_Address_Stack::transition" void Return_Address_Stack::transition (void) { log_printf(FUNC,Return_Address_Stack,FUNCTION,"Begin"); if (PORT_READ(in_NRESET)) { for (uint32_t i=0; i<_param->_nb_context; i++) { reg_TOP [i] = 0; reg_BOTTOM [i] = 0; reg_PREDICT_TOP [i] = 0; reg_PREDICT_BOTTOM [i] = 0; for (uint32_t j=0; j<_param->_size_queue [i]; j++) reg_stack[i][j]._val = false; } } else { // =================================================================== // =====[ PREDICT ]=================================================== // =================================================================== for (uint32_t i=0; i<_param->_nb_inst_predict; i++) if (PORT_READ(in_PREDICT_VAL [i]) and internal_PREDICT_ACK [i]) { Tcontrol_t context = (_param->_have_port_context_id)?PORT_READ(in_PREDICT_CONTEXT_ID [i]):0; Tcontrol_t push = PORT_READ(in_PREDICT_PUSH [i]); Tptr_t top_old = reg_PREDICT_TOP [i]; Tptr_t top_new; if (internal_PREDICT_HIT [i]) { if (push) { // push top_new = (top_old+1)%_param->_size_queue[context]; reg_stack [context][top_new]._val = true; // New addr reg_stack [context][top_new]._predict = true; // Is speculative (erase a old addr) //reg_stack [context][top_new]._miss = ; reg_stack [context][top_new]._address = PORT_READ(in_PREDICT_ADDRESS_PUSH [i]); // the stack is full, erase the most old stack if (top_new == reg_PREDICT_BOTTOM [i]) reg_PREDICT_BOTTOM [i] = (reg_PREDICT_BOTTOM [i]+1)%_param->_size_queue[context]; } else { // pop top_new = (top_old==0)?(_param->_size_queue[context]-1):(top_old-1); //reg_stack [context][top_new]._val = ; //reg_stack [context][top_new]._predict = ; //reg_stack [context][top_new]._miss = ; //reg_stack [context][top_new]._address = ; // the stack is empty if (top_old == reg_PREDICT_BOTTOM [i]) reg_PREDICT_BOTTOM [i] = top_new; } reg_PREDICT_TOP [i] = top_new; } } // // =================================================================== // // =====[ DECOD ]===================================================== // // =================================================================== // for (uint32_t i=0; i<_param->_nb_inst_decod; i++) // if (PORT_READ(in_DECOD_VAL [i]) and internal_DECOD_ACK [i]) // { // Tcontrol_t context = (_param->_have_port_context_id)?PORT_READ(in_DECOD_CONTEXT_ID [i]):0; // Tcontrol_t push = PORT_READ(in_DECOD_PUSH [i]); // Tptr_t top_old = reg_TOP [i]; // Tptr_t top_new; // Tcontrol_t hit = PORT_READ(in_DECOD_HIT [i]); // Tcontrol_t miss = PORT_READ(in_DECOD_MISS_PREDICTION [i]); // if (push) // { // // push // top_new = (top_old+1)%_param->_size_queue[context]; // reg_stack [context][top_new]._val = true; // reg_stack [context][top_new]._predict = false; // reg_stack [context][top_new]._miss = false; // reg_stack [context][top_new]._address = PORT_READ(in_DECOD_ADDRESS_PUSH [i]); // // the stack is full, erase the most old stack // if (top_old == reg_BOTTOM [i]) // reg_BOTTOM [i] = top_new; // } // else // { // // pop // top_new = (top_old==0)?(_param->_size_queue[context]-1):(top_old-1); // //reg_stack [context][top_new]._val = ; // //reg_stack [context][top_new]._predict = ; // //reg_stack [context][top_new]._miss = ; // //reg_stack [context][top_new]._address = ; // } // reg_TOP [i] = top_new; // // have previous miss of ifetch ? // // 2 miss : // // 1) miss predict : is very limited (local at context), can be update very quickly // // 2) miss decod : result is in commit stage ... // if (miss) // { // reg_PREDICT_BOTTOM [i] = reg_BOTTOM [i]; // reg_PREDICT_TOP [i] = reg_TOP [i]; // for (uint32_t j=0; j<_param->_size_queue [i]; j++) // if (reg_stack [context][top_new]._predict) // { // reg_stack [context][top_new]._predict = false; // reg_stack [context][top_new]._miss = true; // } // } // } // =================================================================== // =====[ UPDATE ]=================================================== // =================================================================== for (uint32_t i=0; i<_param->_nb_inst_update; i++) if (PORT_READ(in_UPDATE_VAL [i]) and internal_UPDATE_ACK [i]) { Tcontrol_t context = (_param->_have_port_context_id)?PORT_READ(in_UPDATE_CONTEXT_ID [i]):0; Tcontrol_t push = PORT_READ(in_UPDATE_PUSH [i]); Tptr_t index = PORT_READ(in_UPDATE_INDEX [i]); if (PORT_READ(in_UPDATE_MISS_PREDICTION [i])) { if (push) { // push top_new = (top_old+1)%_param->_size_queue[context]; reg_stack [context][index]._val = true; reg_stack [context][index]._predict = false; reg_stack [context][index]._miss = false; reg_stack [context][index]._address = PORT_READ(in_UPDATE_ADDRESS [i]); } else { //reg_stack [context][top_new]._val = ; //reg_stack [context][top_new]._predict = ; //reg_stack [context][top_new]._miss = ; //reg_stack [context][top_new]._address = ; } // Mouais bof ....... reg_PREDICT_TOP [i] = index; } } } #if defined(STATISTICS) or defined(VHDL_TESTBENCH) end_cycle (); #endif log_printf(FUNC,Return_Address_Stack,FUNCTION,"End"); }; }; // end namespace return_address_stack }; // end namespace prediction_unit }; // end namespace front_end }; // end namespace multi_front_end }; // end namespace core }; // end namespace behavioural }; // end namespace morpheo #endif