diff options
Diffstat (limited to 'src/mem/cache/mshr_queue.cc')
-rw-r--r-- | src/mem/cache/mshr_queue.cc | 35 |
1 files changed, 34 insertions, 1 deletions
diff --git a/src/mem/cache/mshr_queue.cc b/src/mem/cache/mshr_queue.cc index b412891d9..af13d12d3 100644 --- a/src/mem/cache/mshr_queue.cc +++ b/src/mem/cache/mshr_queue.cc @@ -1,4 +1,16 @@ /* + * Copyright (c) 2012 ARM Limited + * All rights reserved. + * + * The license below extends only to copyright in the software and shall + * not be construed as granting a license to any other intellectual + * property including but not limited to intellectual property relating + * to a hardware implementation of the functionality of the software + * licensed hereunder. You may use the software subject to the license + * terms below provided that you ensure that this notice is replicated + * unmodified and in its entirety in all distributions of the software, + * modified or unmodified, in source code or in binary form. + * * Copyright (c) 2003-2005 The Regents of The University of Michigan * All rights reserved. * @@ -26,6 +38,7 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * * Authors: Erik Hallnor + * Andreas Sandberg */ /** @file @@ -40,7 +53,7 @@ MSHRQueue::MSHRQueue(const std::string &_label, int num_entries, int reserve, int _index) : label(_label), numEntries(num_entries + reserve - 1), numReserve(reserve), - index(_index) + drainManager(NULL), index(_index) { allocated = 0; inServiceEntries = 0; @@ -183,6 +196,13 @@ MSHRQueue::deallocateOne(MSHR *mshr) readyList.erase(mshr->readyIter); } mshr->deallocate(); + if (drainManager && allocated == 0) { + // Notify the drain manager that we have completed draining if + // there are no other outstanding requests in this MSHR queue. + drainManager->signalDrainDone(); + drainManager = NULL; + setDrainState(Drainable::Drained); + } return retval; } @@ -245,3 +265,16 @@ MSHRQueue::squash(int threadNum) } } } + +unsigned int +MSHRQueue::drain(DrainManager *dm) +{ + if (allocated == 0) { + setDrainState(Drainable::Drained); + return 0; + } else { + drainManager = dm; + setDrainState(Drainable::Draining); + return 1; + } +} |