void Router::stageTN() { for (int in_pc=0; in_pc<m_num_pc; in_pc++) { int tunnel_in_vc = m_tunnel_info_vec[in_pc].m_in_vc; int tunnel_out_pc = m_tunnel_info_vec[in_pc].m_out_pc; int tunnel_out_vc = m_tunnel_info_vec[in_pc].m_out_vc; if (tunnel_in_vc == INVALID_VC) // support tunneling ? continue; if (m_flitQ->isEmpty(in_pc, tunnel_in_vc)) // has a flit ? continue; // peek one flit from the input buffer Flit* p_flit = m_flitQ->peek(in_pc, tunnel_in_vc); assert(p_flit); switch (p_flit->type()) { case HEAD_FLIT: case ATOM_FLIT: { FlitHead* p_head_flit = (FlitHead*) p_flit; switch(g_cfg.router_tunnel_type) { case TUNNELING_PER_FLOW: if (m_tunnel_info_vec[in_pc].m_flow != make_pair(p_head_flit->src_router_id(), p_head_flit->dest_router_id())) goto NO_TUNNEL; break; case TUNNELING_PER_DEST: if (m_tunnel_info_vec[in_pc].m_dest_router_id != p_head_flit->dest_router_id()) goto NO_TUNNEL; break; case TUNNELING_PER_OUTPORT: break; default: assert(0); } // check input module status if (m_in_mod_vec[in_pc][tunnel_in_vc].m_state != IN_MOD_I) goto NO_TUNNEL; // Step 1.1: do routing int out_pc = g_Routing->selectOutPC(this, tunnel_in_vc, (FlitHead*) p_flit); assert(out_pc < (int) m_connNextRouter_vec.size()); int next_router_id = m_connNextRouter_vec[out_pc].first; int next_in_pc = m_connNextRouter_vec[out_pc].second; if (tunnel_out_pc != out_pc) goto NO_TUNNEL; // Step 2.1: reserve VC if (! isEjectChannel(out_pc)) { if (m_out_mod_vec[out_pc][tunnel_out_vc].m_state != OUT_MOD_I ) // reserved ? goto NO_TUNNEL; } // Step 3.1: check no request in SA for designated input and output ports // FIXME: do we need this? // if (! m_sw_alloc->hasNoReq(in_pc, out_pc)) // goto NO_TUNNEL; // 03/14/08 credit-based flow control if (! hasCredit(out_pc, tunnel_out_vc) ) // no credit? goto NO_TUNNEL; // Step 4.1: check no flit in xbar for designated input and output ports if (m_xbar.m_waiting_in_vc_vec[in_pc] != INVALID_VC || ! m_xbar.m_outport_free_vec[out_pc]) goto NO_TUNNEL; // Step 5.1: check no flit in a link if (! isEjectChannel(out_pc)) { if (((int) m_link_vec[out_pc].m_w_pipeline.size()) >= m_link_vec[out_pc].m_delay_factor*g_cfg.link_latency) goto NO_TUNNEL; } // Now checking is done for tunneling. // Step 2.2: reserve VC if (! isEjectChannel(out_pc)) { m_out_mod_vec[out_pc][tunnel_out_vc].m_state = OUT_MOD_V; } // create a credit and send it to upstream router int prev_router_id = m_connPrevRouter_vec[in_pc].first; int prev_out_pc = m_connPrevRouter_vec[in_pc].second; if (prev_router_id != INVALID_ROUTER_ID && prev_out_pc != INVALID_PC) { Credit* p_credit = g_CreditPool.alloc(); p_credit->m_out_pc = prev_out_pc; p_credit->m_out_vc = tunnel_in_vc; p_credit->m_num_credits = 1; p_credit->m_clk_deposit = simtime() + g_Router_vec[prev_router_id]->getLink(prev_out_pc).m_delay_factor * g_cfg.link_latency; g_Router_vec[prev_router_id]->depositCredit(p_credit); } // 11/05/05: no stall at ST stage if (! isEjectChannel(out_pc)) { assert(next_router_id != INVALID_PC); assert(next_in_pc != INVALID_PC); } // pipeline stage latency m_pipe_lat_ST_tab->tabulate(simtime() - p_flit->m_clk_enter_stage); p_flit->m_clk_enter_stage = simtime(); // assert(m_xbar.m_waiting_in_vc_vec[in_pc] == INVALID_VC); // m_xbar.m_waiting_in_vc_vec[in_pc] = tunnel_in_vc; // assert(m_xbar.m_outport_free_vec[out_pc] == true); // m_xbar.m_outport_free_vec[out_pc] = false; // Step 4.2: traverse a crossbar // move flit to the link if (isEjectChannel(out_pc)) { // select ejection port int epc = p_flit->getPkt()->m_NI_out_pos; NIOutput* p_ni_output = getNIOutput(epc); assert(p_ni_output); assert(m_id == p_flit->getPkt()->getDestRouterID()); p_ni_output->writeFlit(p_flit); // 03/15/06 fast simulation m_num_flits_inside--; } else { m_link_vec[out_pc].m_w_pipeline.push_back(make_pair(p_flit, make_pair(tunnel_out_vc, simtime()))); // decrease credit decCredit(out_pc, tunnel_out_vc, 1); } // read a flit m_flitQ->read(in_pc, tunnel_in_vc); // bypass pipeline m_num_tunnel_flit_vec[in_pc][tunnel_in_vc]++; printf("here1\n"); #ifdef _DEBUG_CHECK_BUFFER_INTEGRITY assert(checkBufferIntegrity(in_pc, tunnel_in_vc, p_flit)); #endif // change input module status for only multi-flit packets assert(m_in_mod_vec[in_pc][tunnel_in_vc].m_state == IN_MOD_I); if (p_flit->type() != ATOM_FLIT) { m_in_mod_vec[in_pc][tunnel_in_vc].m_state = IN_MOD_S; m_in_mod_vec[in_pc][tunnel_in_vc].m_out_pc = out_pc; m_in_mod_vec[in_pc][tunnel_in_vc].m_out_vc = tunnel_out_vc; } // printf("TN3 router=%d m_in_mod_vec[%d][%d]: state=%d, out_pc=%d, out_vc=%d\n", id(), in_pc, tunnel_in_vc, m_in_mod_vec[in_pc][tunnel_in_vc].m_state, m_in_mod_vec[in_pc][tunnel_in_vc].m_out_pc, m_in_mod_vec[in_pc][tunnel_in_vc].m_out_vc); #ifdef _DEBUG_ROUTER debugTN(p_flit, in_pc, tunnel_in_vc, out_pc, tunnel_out_vc); #endif } break; case MIDL_FLIT: case TAIL_FLIT: { assert(m_in_mod_vec[in_pc][tunnel_in_vc].m_state == IN_MOD_S); int out_pc = m_in_mod_vec[in_pc][tunnel_in_vc].m_out_pc; int out_vc = m_in_mod_vec[in_pc][tunnel_in_vc].m_out_vc; if (tunnel_out_pc != out_pc) goto NO_TUNNEL; if (tunnel_out_vc != out_vc) // output VC for tunneling is determined at previous packet delivery. goto NO_TUNNEL; // Step 3.1: check no request in SA for designated input and output ports // FIXME: do we need this? // if (! m_sw_alloc->hasNoReq(in_pc, out_pc)) // goto NO_TUNNEL; // check no flit in xbar for designated input and output ports if (m_xbar.m_waiting_in_vc_vec[in_pc] != INVALID_VC || ! m_xbar.m_outport_free_vec[out_pc]) goto NO_TUNNEL; // 03/14/08 credit-based flow control if (! hasCredit(out_pc, out_vc) ) // no credit? goto NO_TUNNEL; // check no flit in a link if (! isEjectChannel(out_pc)) { if (((int) m_link_vec[out_pc].m_w_pipeline.size()) >= m_link_vec[out_pc].m_delay_factor*g_cfg.link_latency) goto NO_TUNNEL; } // Now checking is done for tunneling. // delete switch allocation status if reserved m_sw_arb->del(in_pc, tunnel_in_vc); // create a credit and send it to upstream router int prev_router_id = m_connPrevRouter_vec[in_pc].first; int prev_out_pc = m_connPrevRouter_vec[in_pc].second; if (prev_router_id != INVALID_ROUTER_ID && prev_out_pc != INVALID_PC) { Credit* p_credit = g_CreditPool.alloc(); p_credit->m_out_pc = prev_out_pc; p_credit->m_out_vc = tunnel_in_vc; p_credit->m_num_credits = 1; p_credit->m_clk_deposit = simtime() + g_Router_vec[prev_router_id]->getLink(prev_out_pc).m_delay_factor * g_cfg.link_latency; g_Router_vec[prev_router_id]->depositCredit(p_credit); } // Step 4: traverse a crossbar // move flit to the link if (isEjectChannel(out_pc)) { // select ejection port int epc = p_flit->getPkt()->m_NI_out_pos; NIOutput* p_ni_output = getNIOutput(epc); assert(p_ni_output); assert(m_id == p_flit->getPkt()->getDestRouterID()); p_ni_output->writeFlit(p_flit); // 03/15/06 fast simulation m_num_flits_inside--; } else { m_link_vec[out_pc].m_w_pipeline.push_back(make_pair(p_flit, make_pair(out_vc, simtime()))); // decrease credit decCredit(out_pc, out_vc, 1); } // clear status of input module if (p_flit->isTail()) { // assert(eject_vc_sts[epc][out_vc] == false); // eject_vc_sts[epc][out_vc] = true; m_in_mod_vec[in_pc][tunnel_in_vc].m_state = IN_MOD_I; m_in_mod_vec[in_pc][tunnel_in_vc].m_out_pc = INVALID_PC; m_in_mod_vec[in_pc][tunnel_in_vc].m_out_vc = INVALID_VC; } // read a flit m_flitQ->read(in_pc, tunnel_in_vc); // bypass pipeline m_num_tunnel_flit_vec[in_pc][tunnel_in_vc]++; printf("here2\n"); #ifdef _DEBUG_CHECK_BUFFER_INTEGRITY assert(checkBufferIntegrity(in_pc, tunnel_in_vc, p_flit)); #endif #ifdef _DEBUG_ROUTER debugTN(p_flit, in_pc, tunnel_in_vc, out_pc, out_vc); #endif } break; default: assert(0); } // switch (p_flit->type()) { NO_TUNNEL: ; } // for (int in_pc=0; in_pc<m_num_pc; in_pc++) { return; }
void DrawingBuffer::reset(const IntSize& newSize) { if (!m_context) return; IntSize adjustedSize; bool evictContext = false; bool isNewContext = m_size.isEmpty(); if (s_allowContextEvictionOnCreate && isNewContext) adjustedSize = adjustSizeWithContextEviction(newSize, evictContext); else adjustedSize = adjustSize(newSize); if (adjustedSize.isEmpty()) return; if (evictContext) m_contextEvictionManager->forciblyLoseOldestContext("WARNING: WebGL contexts have exceeded the maximum allowed backbuffer area. Oldest context will be lost."); if (adjustedSize != m_size) { do { // resize multisample FBO if (!resizeMultisampleFramebuffer(adjustedSize) || !resizeFramebuffer(adjustedSize)) { adjustedSize.scale(s_resourceAdjustedRatio); continue; } #if OS(DARWIN) // FIXME: This can be removed once renderbufferStorageMultisample starts reporting GL_OUT_OF_MEMORY properly on OSX. if (!checkBufferIntegrity()) { adjustedSize.scale(s_resourceAdjustedRatio); continue; } #endif break; } while (!adjustedSize.isEmpty()); setSize(adjustedSize); if (adjustedSize.isEmpty()) return; } m_context->disable(GraphicsContext3D::SCISSOR_TEST); m_context->clearColor(0, 0, 0, 0); m_context->colorMask(true, true, true, true); GC3Dbitfield clearMask = GraphicsContext3D::COLOR_BUFFER_BIT; if (m_attributes.depth) { m_context->clearDepth(1.0f); clearMask |= GraphicsContext3D::DEPTH_BUFFER_BIT; m_context->depthMask(true); } if (m_attributes.stencil) { m_context->clearStencil(0); clearMask |= GraphicsContext3D::STENCIL_BUFFER_BIT; m_context->stencilMaskSeparate(GraphicsContext3D::FRONT, 0xFFFFFFFF); } clearFramebuffers(clearMask); }
void Router::stageST() { #ifdef _DEBUG_ROUTER_ST int _st_debug_router = 3; double _st_debug_clk = 141000012.0; if (m_id==_st_debug_router && simtime() > _st_debug_clk) { printf("ST_status router=%d, clk=%.0lf\n ", m_id, simtime()); for (int out_pc=0; out_pc<m_num_pc; out_pc++) { if (isEjectChannel(out_pc)) { } else { if (m_link_vec[out_pc].m_w_pipeline.size() == 0) { printf("out_pc=%d(free) ", out_pc); } else { printf("out_pc=%d", out_pc); for (unsigned int i=0; i<m_link_vec[out_pc].m_w_pipeline.size(); i++) printf("(fid=%lld) ", m_link_vec[out_pc].m_w_pipeline[i].first->id()); } } } printf("\n"); } #endif int num_xbar_passes = 0; for (int in_pc=0; in_pc<m_num_pc; in_pc++) { int in_vc = m_xbar.m_waiting_in_vc_vec[in_pc]; if (in_vc == INVALID_VC) continue; Flit* read_flit = m_flitQ->read(in_pc, in_vc); assert(read_flit); #ifdef _DEBUG_CHECK_BUFFER_INTEGRITY assert(checkBufferIntegrity(in_pc, in_vc, read_flit)); #endif // create a credit and send it to upstream router int prev_router_id = m_connPrevRouter_vec[in_pc].first; int prev_out_pc = m_connPrevRouter_vec[in_pc].second; if (prev_router_id != INVALID_ROUTER_ID && prev_out_pc != INVALID_PC) { Credit* p_credit = g_CreditPool.alloc(); p_credit->m_out_pc = prev_out_pc; p_credit->m_out_vc = in_vc; p_credit->m_num_credits = 1; p_credit->m_clk_deposit = simtime() + g_Router_vec[prev_router_id]->getLink(prev_out_pc).m_delay_factor * g_cfg.link_latency; g_Router_vec[prev_router_id]->depositCredit(p_credit); } assert(m_in_mod_vec[in_pc][in_vc].m_state == IN_MOD_S); int out_pc = m_in_mod_vec[in_pc][in_vc].m_out_pc; int out_vc = m_in_mod_vec[in_pc][in_vc].m_out_vc; int next_router_id = m_connNextRouter_vec[out_pc].first; int next_in_pc = m_connNextRouter_vec[out_pc].second; if (isEjectChannel(out_pc)) { // select ejection port int epc = out_pc - num_internal_pc(); // printf("epc=%d out_pc=%d\n", epc, out_pc); NIOutput* p_ni_output = getNIOutput(epc); assert(p_ni_output); // FIXME: The following assert() is not valid for DMesh topology, // because destination is encoded at injection function. // assert(m_id == read_flit->getPkt()->getDestRouterID()); p_ni_output->writeFlit(read_flit); // 03/15/06 fast simulation m_num_flits_inside--; #ifdef _DEBUG_ROUTER debugST(read_flit, in_pc, out_pc, INVALID_ROUTER_ID, INVALID_PC, out_vc, true); #endif } else { // 11/05/05: no stall at ST stage assert(next_router_id != INVALID_PC); assert(next_in_pc != INVALID_PC); #ifdef _DEBUG_CREDIT if(g_Router_vec[next_router_id]->flitQ()->isFull(next_in_pc, out_vc)) { printf("router=%d out_pc=%d next_router=%d next_in_pc=%d\n", m_id, out_pc, next_router_id, next_in_pc); for (int x_vc=0; x_vc<m_num_vc; x_vc++) printf(" vc=%d: credit=%d credit_rsv=%d\n", x_vc, m_out_mod_vec[out_pc][x_vc].m_num_credit, m_out_mod_vec[out_pc][x_vc].m_num_credit_rsv); for (int x_vc=0; x_vc<m_num_vc; x_vc++) printf(" vc=%d: Q_sz=%d\n", x_vc, g_Router_vec[next_router_id]->flitQ()->size(next_in_pc, x_vc)); } #endif // assert(! g_Router_vec[next_router_id]->flitQ()->isFull(next_in_pc, out_vc) ); // move flit to the link // NOTE: For wire pipelining, // # of traversing flits on the link must be less than link latency. assert(((int) m_link_vec[out_pc].m_w_pipeline.size()) < m_link_vec[out_pc].m_delay_factor*g_cfg.link_latency); m_link_vec[out_pc].m_w_pipeline.push_back(make_pair(read_flit, make_pair(out_vc, simtime()))); // pipeline stage latency m_pipe_lat_ST_tab->tabulate(simtime() - read_flit->m_clk_enter_stage); read_flit->m_clk_enter_stage = simtime(); #ifdef _DEBUG_ROUTER debugST(read_flit, in_pc, out_pc, next_router_id, next_in_pc, out_vc, false); #endif } // if (isEjectChannel(out_pc)) { // remove a flit from xbar m_xbar.m_waiting_in_vc_vec[in_pc] = INVALID_VC; // update xbar outport status assert(m_xbar.m_outport_free_vec[out_pc] == false); m_xbar.m_outport_free_vec[out_pc] = true; if (read_flit->isTail()) { // change input module status (S->I) m_in_mod_vec[in_pc][in_vc].m_state = IN_MOD_I; m_in_mod_vec[in_pc][in_vc].m_out_pc = INVALID_PC; m_in_mod_vec[in_pc][in_vc].m_out_vc = INVALID_VC; // change output module status (V->I) assert(m_out_mod_vec[out_pc][out_vc].m_state == OUT_MOD_V); m_out_mod_vec[out_pc][out_vc].m_state = OUT_MOD_I; } num_xbar_passes++; // intra-router flit latency m_flit_lat_router_tab->tabulate(simtime() - read_flit->m_clk_enter_router); // record power if (!g_sim.m_warmup_phase) { m_power_tmpl->record_buffer_read(read_flit, in_pc); m_power_tmpl->record_xbar_trav(read_flit, in_pc, out_pc); if (g_cfg.profile_power) { m_power_tmpl_profile->record_buffer_read(read_flit, in_pc); m_power_tmpl_profile->record_xbar_trav(read_flit, in_pc, out_pc); } } } // record power if (!g_sim.m_warmup_phase) { if (num_xbar_passes > 0) { m_power_tmpl->record_xbar_trav_num(num_xbar_passes); if (g_cfg.profile_power) m_power_tmpl_profile->record_xbar_trav_num(num_xbar_passes); } } }
bool DrawingBuffer::reset(const IntSize& newSize) { #if PLATFORM(JS) webkitTrace(); #endif if (!m_context) return false; m_context->makeContextCurrent(); int maxTextureSize = 0; m_context->getIntegerv(GraphicsContext3D::MAX_TEXTURE_SIZE, &maxTextureSize); if (newSize.height() > maxTextureSize || newSize.width() > maxTextureSize) { clear(); return false; } int pixelDelta = newSize.width() * newSize.height(); int oldSize = 0; if (!m_size.isEmpty()) { oldSize = m_size.width() * m_size.height(); pixelDelta -= oldSize; } IntSize adjustedSize = newSize; if (s_maximumResourceUsePixels) { while ((s_currentResourceUsePixels + pixelDelta) > s_maximumResourceUsePixels) { adjustedSize.scale(s_resourceAdjustedRatio); if (adjustedSize.isEmpty()) { clear(); return false; } pixelDelta = adjustedSize.width() * adjustedSize.height(); pixelDelta -= oldSize; } } const GraphicsContext3D::Attributes& attributes = m_context->getContextAttributes(); if (adjustedSize != m_size) { unsigned internalColorFormat, colorFormat, internalRenderbufferFormat; if (attributes.alpha) { internalColorFormat = GraphicsContext3D::RGBA; colorFormat = GraphicsContext3D::RGBA; internalRenderbufferFormat = Extensions3D::RGBA8_OES; } else { internalColorFormat = GraphicsContext3D::RGB; colorFormat = GraphicsContext3D::RGB; internalRenderbufferFormat = Extensions3D::RGB8_OES; } do { m_size = adjustedSize; // resize multisample FBO if (multisample()) { int maxSampleCount = 0; m_context->getIntegerv(Extensions3D::MAX_SAMPLES, &maxSampleCount); int sampleCount = std::min(4, maxSampleCount); m_context->bindFramebuffer(GraphicsContext3D::FRAMEBUFFER, m_multisampleFBO); m_context->bindRenderbuffer(GraphicsContext3D::RENDERBUFFER, m_multisampleColorBuffer); m_context->getExtensions()->renderbufferStorageMultisample(GraphicsContext3D::RENDERBUFFER, sampleCount, internalRenderbufferFormat, m_size.width(), m_size.height()); if (m_context->getError() == GraphicsContext3D::OUT_OF_MEMORY) { adjustedSize.scale(s_resourceAdjustedRatio); continue; } m_context->framebufferRenderbuffer(GraphicsContext3D::FRAMEBUFFER, GraphicsContext3D::COLOR_ATTACHMENT0, GraphicsContext3D::RENDERBUFFER, m_multisampleColorBuffer); resizeDepthStencil(sampleCount); if (m_context->checkFramebufferStatus(GraphicsContext3D::FRAMEBUFFER) != GraphicsContext3D::FRAMEBUFFER_COMPLETE) { adjustedSize.scale(s_resourceAdjustedRatio); continue; } } // resize regular FBO m_context->bindFramebuffer(GraphicsContext3D::FRAMEBUFFER, m_fbo); m_context->bindTexture(GraphicsContext3D::TEXTURE_2D, m_colorBuffer); m_context->texImage2D(GraphicsContext3D::TEXTURE_2D, 0, internalColorFormat, m_size.width(), m_size.height(), 0, colorFormat, GraphicsContext3D::UNSIGNED_BYTE, 0); m_context->framebufferTexture2D(GraphicsContext3D::FRAMEBUFFER, GraphicsContext3D::COLOR_ATTACHMENT0, GraphicsContext3D::TEXTURE_2D, m_colorBuffer, 0); // resize the front color buffer if (m_separateFrontTexture) { m_context->bindTexture(GraphicsContext3D::TEXTURE_2D, m_frontColorBuffer); m_context->texImage2D(GraphicsContext3D::TEXTURE_2D, 0, internalColorFormat, m_size.width(), m_size.height(), 0, colorFormat, GraphicsContext3D::UNSIGNED_BYTE, 0); } m_context->bindTexture(GraphicsContext3D::TEXTURE_2D, 0); if (!multisample()) resizeDepthStencil(0); if (m_context->checkFramebufferStatus(GraphicsContext3D::FRAMEBUFFER) != GraphicsContext3D::FRAMEBUFFER_COMPLETE) { adjustedSize.scale(s_resourceAdjustedRatio); continue; } #if OS(DARWIN) // FIXME: This can be removed once renderbufferStorageMultisample starts reporting GL_OUT_OF_MEMORY properly on OSX. if (!checkBufferIntegrity()) { adjustedSize.scale(s_resourceAdjustedRatio); continue; } #endif break; } while (!adjustedSize.isEmpty()); pixelDelta = m_size.width() * m_size.height(); pixelDelta -= oldSize; s_currentResourceUsePixels += pixelDelta; if (!newSize.isEmpty() && adjustedSize.isEmpty()) { clear(); return false; } } m_context->disable(GraphicsContext3D::SCISSOR_TEST); m_context->clearColor(0, 0, 0, 0); m_context->colorMask(true, true, true, true); GC3Dbitfield clearMask = GraphicsContext3D::COLOR_BUFFER_BIT; if (attributes.depth) { m_context->clearDepth(1.0f); clearMask |= GraphicsContext3D::DEPTH_BUFFER_BIT; m_context->depthMask(true); } if (attributes.stencil) { m_context->clearStencil(0); clearMask |= GraphicsContext3D::STENCIL_BUFFER_BIT; m_context->stencilMaskSeparate(GraphicsContext3D::FRONT, 0xFFFFFFFF); } clearFramebuffers(clearMask); return true; }