37 #ifndef __LDS_STATE_HH__ 38 #define __LDS_STATE_HH__ 43 #include <unordered_map> 47 #include "enums/MemType.hh" 50 #include "params/LdsState.hh" 76 fatal_if(!
chunk.size(),
"cannot read from an LDS chunk of size 0");
77 fatal_if(index >=
chunk.size(),
"out-of-bounds access to an LDS chunk");
78 T *p0 = (T *) (&(
chunk.at(index)));
89 fatal_if(!
chunk.size(),
"cannot write to an LDS chunk of size 0");
90 fatal_if(index >=
chunk.size(),
"out-of-bounds access to an LDS chunk");
91 T *p0 = (T *) (&(
chunk.at(index)));
156 SlavePort(_name, _ownerLds), ownerLds(_ownerLds)
217 std::unordered_map<uint32_t,
221 std::unordered_map<uint32_t,
233 bool retryResp =
false;
245 countBankConflicts(
PacketPtr packet,
unsigned *bankAccesses);
249 unsigned *numBankAccesses);
267 return dynamic_cast<const Params *
>(_params);
284 operator=(
const LdsState &) =
delete;
292 int refCount = getRefCounter(dispatchId, wgId);
294 "reference count should not be below zero");
295 return ++refCounter[dispatchId][wgId];
305 int refCount = getRefCounter(dispatchId, wgId);
308 "reference count should not be below zero or at zero to" 311 refCounter[dispatchId][wgId]--;
313 if (refCounter[dispatchId][wgId] == 0) {
314 releaseSpace(dispatchId, wgId);
317 return refCounter[dispatchId][wgId];
327 auto dispatchIter = chunkMap.find(dispatchId);
328 fatal_if(dispatchIter == chunkMap.end(),
329 "could not locate this dispatch id [%d]", dispatchId);
331 auto workgroup = dispatchIter->second.find(wgId);
332 fatal_if(workgroup == dispatchIter->second.end(),
333 "could not find this workgroup id within this dispatch id" 334 " did[%d] wgid[%d]", dispatchId, wgId);
336 auto refCountIter = refCounter.find(dispatchId);
337 if (refCountIter == refCounter.end()) {
338 fatal(
"could not locate this dispatch id [%d]", dispatchId);
340 auto workgroup = refCountIter->second.find(wgId);
341 if (workgroup == refCountIter->second.end()) {
342 fatal(
"could not find this workgroup id within this dispatch id" 343 " did[%d] wgid[%d]", dispatchId, wgId);
345 return refCounter.at(dispatchId).at(wgId);
349 fatal(
"should not reach this point");
361 if (chunkMap.find(dispatchId) != chunkMap.end()) {
363 chunkMap[dispatchId].find(wgId) != chunkMap[dispatchId].end(),
364 "duplicate workgroup ID asking for space in the LDS " 365 "did[%d] wgid[%d]", dispatchId, wgId);
368 fatal_if(bytesAllocated + size > maximumSize,
369 "request would ask for more space than is available");
371 bytesAllocated +=
size;
373 chunkMap[dispatchId].emplace(wgId,
LdsChunk(size));
375 refCounter[dispatchId][wgId] = 0;
377 return &chunkMap[dispatchId][wgId];
387 return returnQueue.empty() ?
curTick() : returnQueue.back().first;
421 return bankConflictPenalty;
430 return chunkMap[x_wgId].size();
442 if (if_name ==
"cuPort") {
446 fatal(
"cannot resolve the port name " + if_name);
456 return bytesAllocated + x_size <= maximumSize;
466 auto dispatchIter = chunkMap.find(x_dispatchId);
468 if (dispatchIter == chunkMap.end()) {
469 fatal(
"dispatch id not found [%d]", x_dispatchId);
471 auto workgroupIter = dispatchIter->second.find(x_wgId);
472 if (workgroupIter == dispatchIter->second.end()) {
473 fatal(
"workgroup id [%d] not found in dispatch id [%d]",
474 x_wgId, x_dispatchId);
478 fatal_if(bytesAllocated < chunkMap[x_dispatchId][x_wgId].
size(),
479 "releasing more space than was allocated");
481 bytesAllocated -= chunkMap[x_dispatchId][x_wgId].size();
482 chunkMap[x_dispatchId].erase(chunkMap[x_dispatchId].find(x_wgId));
494 int bytesAllocated = 0;
503 int bankConflictPenalty = 0;
509 #endif // __LDS_STATE_HH__ Ports are used to interface objects to each other.
an event to allow event-driven execution
#define fatal(...)
This implements a cprintf based fatal() function.
std::vector< uint8_t >::size_type size() const
get the size of this chunk
Tick earliestReturnTime() const
std::queue< std::pair< Tick, PacketPtr > > returnQueue
const Params * params() const
virtual AddrRangeList getAddrRanges() const
Get a list of the non-overlapping address ranges the owner is responsible for.
std::vector< uint8_t > chunk
TickEvent(LdsState *_ldsState)
vector< EventQueue * > mainEventQueue
Array for main event queues.
A SlavePort is a specialisation of a port.
this represents a slice of the overall LDS, intended to be associated with an individual workgroup ...
ComputeUnit * getParent() const
CuSidePort(const std::string &_name, LdsState *_ownerLds)
The AddrRange class encapsulates an address range, and supports a number of tests to check if two ran...
std::shared_ptr< GPUDynInst > GPUDynInstPtr
virtual void recvRangeChange()
void setRetryResp(const bool value)
Tick curTick()
The current simulated tick.
std::size_t ldsSize(const uint32_t x_wgId)
get the allocated size for this workgroup
uint64_t Tick
Tick count type.
The ClockedObject class extends the SimObject with a clock and accessor functions to relate ticks to ...
bool canReserve(uint32_t x_size) const
can this much space be reserved for a workgroup?
ClockedObject declaration and implementation.
Port & getPort(const std::string &if_name, PortID idx)
Get a port with a given name and index.
#define fatal_if(cond,...)
Conditional fatal macro that checks the supplied condition and only causes a fatal error if the condi...
std::unordered_map< uint32_t, std::unordered_map< uint32_t, int32_t > > refCounter
int increaseRefCounter(const uint32_t dispatchId, const uint32_t wgId)
use the dynamic wave id to create or just increase the reference count
int decreaseRefCounter(const uint32_t dispatchId, const uint32_t wgId)
decrease the reference count after making sure it is in the list give back this chunk if the ref coun...
T read(const uint32_t index)
a read operation
virtual Tick recvAtomic(PacketPtr pkt)
Receive an atomic request packet from the peer.
LdsChunk(const uint32_t x_size)
A Packet is used to encapsulate a transfer between two objects in the memory system (e...
std::unordered_map< uint32_t, std::unordered_map< uint32_t, LdsChunk > > chunkMap
LdsChunk * reserveSpace(const uint32_t dispatchId, const uint32_t wgId, const uint32_t size)
assign a parent and request this amount of space be set aside for this wgid
int getRefCounter(const uint32_t dispatchId, const uint32_t wgId) const
return the current reference count for this workgroup id
void write(const uint32_t index, const T value)
a write operation
int16_t PortID
Port index/ID type, and a symbolic name for an invalid port id.
int getBankConflictPenalty() const
bool releaseSpace(const uint32_t x_dispatchId, const uint32_t x_wgId)
give back the space
CuSidePort is the LDS Port closer to the CU side.
AddrRange getAddrRange() const
ComputeUnit * getComputeUnit() const