wsch Posted March 15, 2013 Report Posted March 15, 2013 Hi When I simulate my SystemC project in Modelsim I get this error: Error: (vsim-6596) Out of bounds: # In process: sc_main/hermes_2d/thread_p_2 @ 872800 ns # ** Fatal: Fatal SystemC error detected, exiting... From what I could ascertain according to the results collected, the logic is correct. Heres is the code: for(int i = 0; i < 16; ++i) { sc_spawn(sc_bind(&hermes_with_pkt_codec_vhd_bfm::sender, this, i)); sc_spawn(sc_bind(&hermes_with_pkt_codec_vhd_bfm::receiver, this, i)); } void receiver(unsigned int agent) { wait(reset); sc_core::sc_lv<16> tx_re_s; sctg::BufferInterface* buffer = _confIf->getBufferIf(agent); tgPacket* packet = 0; if(!buffer) {return;} while(true) { sc_core::wait(clk_ip->posedge_event()); packet = new tgPacket; do { sc_core::wait(clk_ip->posedge_event()); } while(tx_av.read()[agent] == sc_dt::SC_LOGIC_0); packet->address = tx_data.read().range((agent+1)*32-1, agent*32).to_ulong(); do { sc_core::wait(clk_ip->posedge_event()); } while(tx_av.read()[agent] == sc_dt::SC_LOGIC_1); unsigned int tam = tx_data.read().range((agent+1)*32-1, agent*32).to_uint(); for(unsigned int i = 0; i < tam; i++) { do { sc_core::wait(clk_ip->posedge_event()); } while(tx_free.read()[agent] == sc_dt::SC_LOGIC_0); packet->data = new unsigned char[sizeof(unsigned int)]; unsigned int data = tx_data.read().range((agent+1)*32-1, agent*32).to_uint(); *reinterpret_cast<unsigned int*>(packet->data) = data; packet->size += 32/8; do { sc_core::wait(clk_ip->posedge_event()); } while(tx_free.read()[agent] == sc_dt::SC_LOGIC_1); } // Wait until packet fits to agent's buffer while(buffer->rxSpaceLeft() < packet->size) { wait(*(buffer->rxGetReadEvent())); } buffer->rxPutPacket(packet); packet = 0; sc_core::wait(clk_ip->posedge_event()); } } Thanks Quote
apfitch Posted March 16, 2013 Report Posted March 16, 2013 Who knows? You need a stack backtrace to narrow down the location of the error. regards Alan P.S. One thing looks odd - why is packet->address assigned using to_ulong(), and tam assigned using to_uint()? Quote
dakupoto Posted March 16, 2013 Report Posted March 16, 2013 There are two issues that need to be tackled. 1. You are using sc_spawn == please ensure that you use sc_join to force the simulator to take care of dynamic threads after they have completed their task. This is very important, because otherwise threads get spawned, eat up memory and then a crash. 2. Correct interfacing with ModelSim Since it appears that you are trying to model packets being read in/out (some network device) why not stick to static threads only. All buffers on all network devices(e.g., router) have finite fixed memory and no matter what algorithm one uses, the final constraint is physical memory. Quote
Philipp A Hartmann Posted March 16, 2013 Report Posted March 16, 2013 Who knows? You need a stack backtrace to narrow down the location of the error. I agree with Alan here. Moreover, when you look at the backtrace, you'll most probably see that the problem is within the sender part: Error: (vsim-6596) Out of bounds: # In process: sc_main/hermes_2d/thread_p_2 @ 872800 ns # ** Fatal: Fatal SystemC error detected, exiting... The name thread_p_2 refers to the third dynamically created process in this module. Based on your loop above, this would be the second sender process. You didn't show the body of the sender. That said, it is always a good idea to add explicit names to the design elements you create. Something like: sc_spawn( sc_bind(&hermes_with_pkt_codec_vhd_bfm::sender, this, i), sc_core::sc_gen_unique_name("sender") ); Greetings from Oldenburg, Philipp maehne 1 Quote
wsch Posted March 17, 2013 Author Report Posted March 17, 2013 Hi Here is the body of sender void sender(unsigned int agent) { wait(reset); sctg::BufferInterface* buffer = _confIf->getBufferIf(agent); if(!buffer) {return;} tgPacket* packet = 0; sc_core::sc_lv<16> rx_av_s; sc_core::sc_lv<16*32> rx_data_s; sc_core::sc_lv<16> rx_tx_len_s; sc_core::sc_lv<16> rx_we_s; while(true) { // Wait for packets to send if(!buffer->txPacketAvailable()) { sc_core::wait(*(buffer->txGetPacketAvailableEvent())); } // Read packet from buffer packet = buffer->txGetPacket(); sc_core::wait(clk_ip->posedge_event()); //RX_AV = 1 // Send address - set address valid rx_av_s = rx_av.get_new_value(); rx_av_s[agent] = sc_dt::SC_LOGIC_1; rx_av = rx_av_s; // Put first data (is address) to bus //ENDEREÇO DO PE DESTINO rx_data_s = rx_data.get_new_value(); rx_data_s.range((agent+1)*32-1, agent*32) = addr_gen(agent, packet->address); rx_data = rx_data_s; // Set transfer length rx_tx_len_s = rx_tx_len.get_new_value(); rx_tx_len_s.range((agent+1)*16-1, agent*16) = sc_dt::sc_uint<16>(packet->size/4); rx_tx_len = rx_tx_len_s; // Set write enable rx_we_s = rx_we.get_new_value(); rx_we_s[agent] = sc_dt::SC_LOGIC_1; rx_we = rx_we_s; // Wait until NoC is ready to read do { sc_core::wait(clk_ip->posedge_event()); } while(rx_full.read()[agent] == sc_dt::SC_LOGIC_1); // Negate address valid rx_av_s = rx_av.get_new_value(); rx_av_s[agent] = sc_dt::SC_LOGIC_0; rx_av = rx_av_s; // Send data for(unsigned int i = 0; i < packet->size/4; ++i) { // Set data to line rx_data_s = rx_data.get_new_value(); if(i == 0) { // Send first byte actually, fill rest with dummy data rx_data_s.range((agent+1)*32-1, agent*32) = sc_dt::sc_uint<32> (*reinterpret_cast<int*>(packet->data)); //data_width_g = 4 bytes ou 32 bits // printf("\nDATA1: %d", (*reinterpret_cast<int*>(packet->data))); } else { rx_data_s.range((agent+1)*32-1, agent*32) = sc_dt::sc_uint<32>(agent); //data_width_g = 4 bytes ou 32 bits // printf("\nDATA2: %d", agent); } //RX_DATA = DADOS rx_data = rx_data_s; // Wait clock cycle or more if NoC can't read it do { sc_core::wait(clk_ip->posedge_event()); } while(rx_full.read()[agent] == sc_dt::SC_LOGIC_1); } //RX_WE = 0 // Negate write enable rx_we_s = rx_we.get_new_value(); rx_we_s[agent] = sc_dt::SC_LOGIC_0; rx_we = rx_we_s; //RX_DATA = 0 // Set data bus to zero (not necessary, for easier debugging in sim) rx_data_s = rx_data.get_new_value(); rx_data_s.range((agent+1)*32-1, agent*32) = sc_dt::sc_uint<32>(0); rx_data = rx_data_s; //RX_TX_LEN = 0 // Set tx len lines to zeros (not necessary) rx_tx_len_s = rx_tx_len.get_new_value(); rx_tx_len_s.range((agent+1)*16-1, agent*16) = sc_dt::sc_uint<16>(0); rx_tx_len = rx_tx_len_s; // Delete packet delete [] packet->data; delete packet; packet = 0; } } Quote
wsch Posted March 17, 2013 Author Report Posted March 17, 2013 Thanks all!!! I find out Philipp is right, the problem was in sender function I was using sc_core::sc_lv<16> rx_tx_len_s; instead sc_core::sc_lv<16*16> rx_tx_len_s; Best Regards Quote
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.