12810SN/A/*
213351Snikos.nikoleris@arm.com * Copyright (c) 2012-2013, 2015-2016, 2018 ARM Limited
39347SAndreas.Sandberg@arm.com * All rights reserved.
49347SAndreas.Sandberg@arm.com *
59347SAndreas.Sandberg@arm.com * The license below extends only to copyright in the software and shall
69347SAndreas.Sandberg@arm.com * not be construed as granting a license to any other intellectual
79347SAndreas.Sandberg@arm.com * property including but not limited to intellectual property relating
89347SAndreas.Sandberg@arm.com * to a hardware implementation of the functionality of the software
99347SAndreas.Sandberg@arm.com * licensed hereunder.  You may use the software subject to the license
109347SAndreas.Sandberg@arm.com * terms below provided that you ensure that this notice is replicated
119347SAndreas.Sandberg@arm.com * unmodified and in its entirety in all distributions of the software,
129347SAndreas.Sandberg@arm.com * modified or unmodified, in source code or in binary form.
139347SAndreas.Sandberg@arm.com *
142810SN/A * Copyright (c) 2003-2005 The Regents of The University of Michigan
152810SN/A * All rights reserved.
162810SN/A *
172810SN/A * Redistribution and use in source and binary forms, with or without
182810SN/A * modification, are permitted provided that the following conditions are
192810SN/A * met: redistributions of source code must retain the above copyright
202810SN/A * notice, this list of conditions and the following disclaimer;
212810SN/A * redistributions in binary form must reproduce the above copyright
222810SN/A * notice, this list of conditions and the following disclaimer in the
232810SN/A * documentation and/or other materials provided with the distribution;
242810SN/A * neither the name of the copyright holders nor the names of its
252810SN/A * contributors may be used to endorse or promote products derived from
262810SN/A * this software without specific prior written permission.
272810SN/A *
282810SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
292810SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
302810SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
312810SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
322810SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
332810SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
342810SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
352810SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
362810SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
372810SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
382810SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
392810SN/A *
402810SN/A * Authors: Erik Hallnor
419347SAndreas.Sandberg@arm.com *          Andreas Sandberg
422810SN/A */
432810SN/A
442810SN/A/** @file
454626SN/A * Definition of MSHRQueue class functions.
462810SN/A */
472810SN/A
485338Sstever@gmail.com#include "mem/cache/mshr_queue.hh"
492810SN/A
5012727Snikos.nikoleris@arm.com#include <cassert>
5112727Snikos.nikoleris@arm.com
5212727Snikos.nikoleris@arm.com#include "mem/cache/mshr.hh"
5312727Snikos.nikoleris@arm.com
545314SN/AMSHRQueue::MSHRQueue(const std::string &_label,
5511375Sandreas.hansson@arm.com                     int num_entries, int reserve, int demand_reserve)
5611375Sandreas.hansson@arm.com    : Queue<MSHR>(_label, num_entries, reserve),
5711375Sandreas.hansson@arm.com      demandReserve(demand_reserve)
5811375Sandreas.hansson@arm.com{}
594666SN/A
604626SN/AMSHR *
6110764Sandreas.hansson@arm.comMSHRQueue::allocate(Addr blk_addr, unsigned blk_size, PacketPtr pkt,
6211197Sandreas.hansson@arm.com                    Tick when_ready, Counter order, bool alloc_on_fill)
632810SN/A{
643149SN/A    assert(!freeList.empty());
652810SN/A    MSHR *mshr = freeList.front();
662810SN/A    assert(mshr->getNumTargets() == 0);
672810SN/A    freeList.pop_front();
682810SN/A
6911197Sandreas.hansson@arm.com    mshr->allocate(blk_addr, blk_size, pkt, when_ready, order, alloc_on_fill);
702810SN/A    mshr->allocIter = allocatedList.insert(allocatedList.end(), mshr);
714666SN/A    mshr->readyIter = addToReadyList(mshr);
722810SN/A
732810SN/A    allocated += 1;
742810SN/A    return mshr;
752810SN/A}
762810SN/A
772810SN/Avoid
782810SN/AMSHRQueue::moveToFront(MSHR *mshr)
792810SN/A{
802810SN/A    if (!mshr->inService) {
812810SN/A        assert(mshr == *(mshr->readyIter));
824666SN/A        readyList.erase(mshr->readyIter);
834666SN/A        mshr->readyIter = readyList.insert(readyList.begin(), mshr);
842810SN/A    }
852810SN/A}
862810SN/A
872810SN/Avoid
8813351Snikos.nikoleris@arm.comMSHRQueue::delay(MSHR *mshr, Tick delay_ticks)
8913351Snikos.nikoleris@arm.com{
9013351Snikos.nikoleris@arm.com    mshr->delay(delay_ticks);
9113351Snikos.nikoleris@arm.com    auto it = std::find_if(mshr->readyIter, readyList.end(),
9213351Snikos.nikoleris@arm.com                            [mshr] (const MSHR* _mshr) {
9313351Snikos.nikoleris@arm.com                                return mshr->readyTime >= _mshr->readyTime;
9413351Snikos.nikoleris@arm.com                            });
9513351Snikos.nikoleris@arm.com    readyList.splice(it, readyList, mshr->readyIter);
9613351Snikos.nikoleris@arm.com}
9713351Snikos.nikoleris@arm.com
9813351Snikos.nikoleris@arm.comvoid
9911284Sandreas.hansson@arm.comMSHRQueue::markInService(MSHR *mshr, bool pending_modified_resp)
1002810SN/A{
10111375Sandreas.hansson@arm.com    mshr->markInService(pending_modified_resp);
10211375Sandreas.hansson@arm.com    readyList.erase(mshr->readyIter);
10311375Sandreas.hansson@arm.com    _numInService += 1;
1042810SN/A}
1052810SN/A
1062810SN/Avoid
1074626SN/AMSHRQueue::markPending(MSHR *mshr)
1082810SN/A{
1094666SN/A    assert(mshr->inService);
1102810SN/A    mshr->inService = false;
11111375Sandreas.hansson@arm.com    --_numInService;
1122810SN/A    /**
1132810SN/A     * @ todo might want to add rerequests to front of pending list for
1142810SN/A     * performance.
1152810SN/A     */
1164666SN/A    mshr->readyIter = addToReadyList(mshr);
1172810SN/A}
1182810SN/A
11910192Smitch.hayenga@arm.combool
12010192Smitch.hayenga@arm.comMSHRQueue::forceDeallocateTarget(MSHR *mshr)
12110192Smitch.hayenga@arm.com{
12210192Smitch.hayenga@arm.com    bool was_full = isFull();
12310192Smitch.hayenga@arm.com    assert(mshr->hasTargets());
12410192Smitch.hayenga@arm.com    // Pop the prefetch off of the target list
12510192Smitch.hayenga@arm.com    mshr->popTarget();
12610192Smitch.hayenga@arm.com    // Delete mshr if no remaining targets
12710192Smitch.hayenga@arm.com    if (!mshr->hasTargets() && !mshr->promoteDeferredTargets()) {
12811375Sandreas.hansson@arm.com        deallocate(mshr);
12910192Smitch.hayenga@arm.com    }
13010192Smitch.hayenga@arm.com
13110192Smitch.hayenga@arm.com    // Notify if MSHR queue no longer full
13210192Smitch.hayenga@arm.com    return was_full && !isFull();
13310192Smitch.hayenga@arm.com}
134