diff options
Diffstat (limited to 'src/mem')
-rw-r--r-- | src/mem/ruby/system/GPUCoalescer.cc | 28 | ||||
-rw-r--r-- | src/mem/ruby/system/GPUCoalescer.hh | 22 |
2 files changed, 31 insertions, 19 deletions
diff --git a/src/mem/ruby/system/GPUCoalescer.cc b/src/mem/ruby/system/GPUCoalescer.cc index fefda4d47..991b21717 100644 --- a/src/mem/ruby/system/GPUCoalescer.cc +++ b/src/mem/ruby/system/GPUCoalescer.cc @@ -625,9 +625,8 @@ GPUCoalescer::hitCallback(GPUCoalescerRequest* srequest, int len = reqCoalescer[request_line_address].size(); std::vector<PacketPtr> mylist; for (int i = 0; i < len; ++i) { - PacketPtr pkt = reqCoalescer[request_line_address][i].first; - assert(type == - reqCoalescer[request_line_address][i].second[PrimaryType]); + PacketPtr pkt = reqCoalescer[request_line_address][i].pkt; + assert(type == reqCoalescer[request_line_address][i].primaryType); request_address = pkt->getAddr(); request_line_address = makeLineAddress(pkt->getAddr()); if (pkt->getPtr<uint8_t>()) { @@ -848,25 +847,22 @@ GPUCoalescer::makeRequest(PacketPtr pkt) // let us see if we can coalesce this request with the previous // requests from this cycle } else if (primary_type != - reqCoalescer[line_addr][0].second[PrimaryType]) { + reqCoalescer[line_addr][0].primaryType) { // can't coalesce loads, stores and atomics! return RequestStatus_Aliased; } else if (pkt->req->isLockedRMW() || - reqCoalescer[line_addr][0].first->req->isLockedRMW()) { + reqCoalescer[line_addr][0].pkt->req->isLockedRMW()) { // can't coalesce locked accesses, but can coalesce atomics! return RequestStatus_Aliased; } else if (pkt->req->hasContextId() && pkt->req->isRelease() && pkt->req->contextId() != - reqCoalescer[line_addr][0].first->req->contextId()) { + reqCoalescer[line_addr][0].pkt->req->contextId()) { // can't coalesce releases from different wavefronts return RequestStatus_Aliased; } // in addition to the packet, we need to save both request types - reqCoalescer[line_addr].push_back( - RequestDesc(pkt, std::vector<RubyRequestType>()) ); - reqCoalescer[line_addr].back().second.push_back(primary_type); - reqCoalescer[line_addr].back().second.push_back(secondary_type); + reqCoalescer[line_addr].emplace_back(pkt, primary_type, secondary_type); if (!issueEvent.scheduled()) schedule(issueEvent, curTick()); // TODO: issue hardware prefetches here @@ -910,7 +906,7 @@ GPUCoalescer::issueRequest(PacketPtr pkt, RubyRequestType secondary_type) std::vector< std::pair<int,AtomicOpFunctor*> > atomicOps; uint32_t tableSize = reqCoalescer[line_addr].size(); for (int i = 0; i < tableSize; i++) { - PacketPtr tmpPkt = reqCoalescer[line_addr][i].first; + PacketPtr tmpPkt = reqCoalescer[line_addr][i].pkt; uint32_t tmpOffset = (tmpPkt->getAddr()) - line_addr; uint32_t tmpSize = tmpPkt->getSize(); if (tmpPkt->isAtomicOp()) { @@ -1020,12 +1016,12 @@ GPUCoalescer::completeIssue() // can be coalesced with the first request. So, only // one request is issued per cacheline. RequestDesc info = reqCoalescer[newRequests[i]][0]; - PacketPtr pkt = info.first; + PacketPtr pkt = info.pkt; DPRINTF(GPUCoalescer, "Completing for newReq %d: paddr %#x\n", i, pkt->req->getPaddr()); // Insert this request to the read/writeRequestTables. These tables // are used to track aliased requests in makeRequest subroutine - bool found = insertRequest(pkt, info.second[PrimaryType]); + bool found = insertRequest(pkt, info.primaryType); if (found) { panic("GPUCoalescer::makeRequest should never be called if the " @@ -1033,7 +1029,7 @@ GPUCoalescer::completeIssue() } // Issue request to ruby subsystem - issueRequest(pkt, info.second[SecondaryType]); + issueRequest(pkt, info.secondaryType); } newRequests.clear(); @@ -1107,9 +1103,9 @@ GPUCoalescer::atomicCallback(Addr address, int len = reqCoalescer[request_line_address].size(); std::vector<PacketPtr> mylist; for (int i = 0; i < len; ++i) { - PacketPtr pkt = reqCoalescer[request_line_address][i].first; + PacketPtr pkt = reqCoalescer[request_line_address][i].pkt; assert(srequest->m_type == - reqCoalescer[request_line_address][i].second[PrimaryType]); + reqCoalescer[request_line_address][i].primaryType); request_address = (pkt->getAddr()); request_line_address = makeLineAddress(request_address); if (pkt->getPtr<uint8_t>() && diff --git a/src/mem/ruby/system/GPUCoalescer.hh b/src/mem/ruby/system/GPUCoalescer.hh index fcf7cecf4..557d39235 100644 --- a/src/mem/ruby/system/GPUCoalescer.hh +++ b/src/mem/ruby/system/GPUCoalescer.hh @@ -73,6 +73,24 @@ struct GPUCoalescerRequest {} }; +class RequestDesc +{ + public: + RequestDesc(PacketPtr pkt, RubyRequestType p_type, RubyRequestType s_type) + : pkt(pkt), primaryType(p_type), secondaryType(s_type) + { + } + + RequestDesc() : pkt(nullptr), primaryType(RubyRequestType_NULL), + secondaryType(RubyRequestType_NULL) + { + } + + PacketPtr pkt; + RubyRequestType primaryType; + RubyRequestType secondaryType; +}; + std::ostream& operator<<(std::ostream& out, const GPUCoalescerRequest& obj); class GPUCoalescer : public RubyPort @@ -271,9 +289,7 @@ class GPUCoalescer : public RubyPort // The secondary request type comprises a subset of RubyRequestTypes that // are understood by the L1 Controller. A primary request type can be any // RubyRequestType. - enum {PrimaryType, SecondaryType}; - typedef std::pair<PacketPtr, std::vector<RubyRequestType> > RequestDesc; - typedef std::unordered_map<Addr, std::vector<RequestDesc> > CoalescingTable; + typedef std::unordered_map<Addr, std::vector<RequestDesc>> CoalescingTable; CoalescingTable reqCoalescer; std::vector<Addr> newRequests; |