mem_dep_unit_impl.hh revision 2307
16692SN/A/*
26692SN/A * Copyright (c) 2004-2005 The Regents of The University of Michigan
36692SN/A * All rights reserved.
410036SAli.Saidi@ARM.com *
58835SAli.Saidi@ARM.com * Redistribution and use in source and binary forms, with or without
610036SAli.Saidi@ARM.com * modification, are permitted provided that the following conditions are
77935SN/A * met: redistributions of source code must retain the above copyright
87935SN/A * notice, this list of conditions and the following disclaimer;
97935SN/A * redistributions in binary form must reproduce the above copyright
106692SN/A * notice, this list of conditions and the following disclaimer in the
116692SN/A * documentation and/or other materials provided with the distribution;
126692SN/A * neither the name of the copyright holders nor the names of its
1310315Snilay@cs.wisc.edu * contributors may be used to endorse or promote products derived from
148835SAli.Saidi@ARM.com * this software without specific prior written permission.
159885Sstever@gmail.com *
169885Sstever@gmail.com * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
1710036SAli.Saidi@ARM.com * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
188835SAli.Saidi@ARM.com * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
198835SAli.Saidi@ARM.com * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
2010315Snilay@cs.wisc.edu * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
218835SAli.Saidi@ARM.com * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
2210242Ssteve.reinhardt@amd.com * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
239449SAli.Saidi@ARM.com * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
249449SAli.Saidi@ARM.com * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
258464SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
268721SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
278835SAli.Saidi@ARM.com */
288835SAli.Saidi@ARM.com
297935SN/A#include <map>
307935SN/A
317935SN/A#include "cpu/o3/inst_queue.hh"
327935SN/A#include "cpu/o3/mem_dep_unit.hh"
337935SN/A
347935SN/Atemplate <class MemDepPred, class Impl>
357935SN/AMemDepUnit<MemDepPred, Impl>::MemDepUnit(Params *params)
368983Snate@binkert.org    : depPred(params->SSITSize, params->LFSTSize), loadBarrier(false),
376692SN/A      loadBarrierSN(0), storeBarrier(false), storeBarrierSN(0), iqPtr(NULL)
389885Sstever@gmail.com{
399885Sstever@gmail.com    DPRINTF(MemDepUnit, "Creating MemDepUnit object.\n");
409885Sstever@gmail.com}
4110315Snilay@cs.wisc.edu
4210036SAli.Saidi@ARM.comtemplate <class MemDepPred, class Impl>
4310315Snilay@cs.wisc.eduMemDepUnit<MemDepPred, Impl>::~MemDepUnit()
449885Sstever@gmail.com{
459885Sstever@gmail.com    for (int tid=0; tid < Impl::MaxThreads; tid++) {
466692SN/A
476692SN/A        ListIt inst_list_it = instList[tid].begin();
489481Snilay@cs.wisc.edu
496692SN/A        MemDepHashIt hash_it;
506692SN/A
518241SN/A        while (!instList[tid].empty()) {
528241SN/A            hash_it = memDepHash.find((*inst_list_it)->seqNum);
536692SN/A
546692SN/A            assert(hash_it != memDepHash.end());
556692SN/A
566692SN/A            memDepHash.erase(hash_it);
576692SN/A
589481Snilay@cs.wisc.edu            instList[tid].erase(inst_list_it++);
596692SN/A        }
606692SN/A    }
619885Sstever@gmail.com
626692SN/A    assert(MemDepEntry::memdep_count == 0);
636692SN/A}
646692SN/A
656692SN/Atemplate <class MemDepPred, class Impl>
666692SN/Astd::string
676692SN/AMemDepUnit<MemDepPred, Impl>::name() const
686692SN/A{
696692SN/A    return "memdepunit";
706692SN/A}
716692SN/A
726692SN/Atemplate <class MemDepPred, class Impl>
738835SAli.Saidi@ARM.comvoid
746692SN/AMemDepUnit<MemDepPred, Impl>::init(Params *params, int tid)
756692SN/A{
7610036SAli.Saidi@ARM.com    DPRINTF(MemDepUnit, "Creating MemDepUnit %i object.\n",tid);
7710036SAli.Saidi@ARM.com
786692SN/A    id = tid;
796692SN/A
806692SN/A    depPred.init(params->SSITSize, params->LFSTSize);
816692SN/A}
826692SN/A
836692SN/Atemplate <class MemDepPred, class Impl>
846692SN/Avoid
856692SN/AMemDepUnit<MemDepPred, Impl>::regStats()
866692SN/A{
876692SN/A    insertedLoads
886692SN/A        .name(name() + ".memDep.insertedLoads")
898835SAli.Saidi@ARM.com        .desc("Number of loads inserted to the mem dependence unit.");
909348SAli.Saidi@ARM.com
916692SN/A    insertedStores
926692SN/A        .name(name() + ".memDep.insertedStores")
936692SN/A        .desc("Number of stores inserted to the mem dependence unit.");
946692SN/A
956692SN/A    conflictingLoads
966692SN/A        .name(name() + ".memDep.conflictingLoads")
976692SN/A        .desc("Number of conflicting loads.");
988835SAli.Saidi@ARM.com
996692SN/A    conflictingStores
1009924Ssteve.reinhardt@amd.com        .name(name() + ".memDep.conflictingStores")
1016692SN/A        .desc("Number of conflicting stores.");
1026692SN/A}
1036692SN/A
1046692SN/Atemplate <class MemDepPred, class Impl>
1056692SN/Avoid
1068835SAli.Saidi@ARM.comMemDepUnit<MemDepPred, Impl>::switchOut()
1076692SN/A{
1086692SN/A    for (int i = 0; i < Impl::MaxThreads; ++i) {
1096692SN/A        instList[i].clear();
1106692SN/A    }
1116692SN/A    instsToReplay.clear();
1126692SN/A    memDepHash.clear();
1139885Sstever@gmail.com}
1146692SN/A
1156692SN/Atemplate <class MemDepPred, class Impl>
1166692SN/Avoid
1176692SN/AMemDepUnit<MemDepPred, Impl>::takeOverFrom()
1186692SN/A{
1196692SN/A    loadBarrier = storeBarrier = false;
1206692SN/A    loadBarrierSN = storeBarrierSN = 0;
1216692SN/A    depPred.clear();
1226692SN/A}
12310242Ssteve.reinhardt@amd.com
1246692SN/Atemplate <class MemDepPred, class Impl>
1258721SN/Avoid
1269449SAli.Saidi@ARM.comMemDepUnit<MemDepPred, Impl>::setIQ(InstructionQueue<Impl> *iq_ptr)
1276692SN/A{
1286692SN/A    iqPtr = iq_ptr;
1296692SN/A}
1306692SN/A
1316692SN/Atemplate <class MemDepPred, class Impl>
1326692SN/Avoid
1336692SN/AMemDepUnit<MemDepPred, Impl>::insert(DynInstPtr &inst)
1346692SN/A{
1356692SN/A    unsigned tid = inst->threadNumber;
1369481Snilay@cs.wisc.edu
1379481Snilay@cs.wisc.edu    MemDepEntryPtr inst_entry = new MemDepEntry(inst);
1389481Snilay@cs.wisc.edu
1399481Snilay@cs.wisc.edu    // Add the MemDepEntry to the hash.
1409481Snilay@cs.wisc.edu    memDepHash.insert(
1419481Snilay@cs.wisc.edu        std::pair<InstSeqNum, MemDepEntryPtr>(inst->seqNum, inst_entry));
1429481Snilay@cs.wisc.edu    MemDepEntry::memdep_insert++;
14310036SAli.Saidi@ARM.com
1449481Snilay@cs.wisc.edu    // Add the instruction to the instruction list.
1459481Snilay@cs.wisc.edu    instList[tid].push_back(inst);
1469481Snilay@cs.wisc.edu
1479481Snilay@cs.wisc.edu    inst_entry->listIt = --(instList[tid].end());
1489481Snilay@cs.wisc.edu
1499481Snilay@cs.wisc.edu    // Check the dependence predictor for any producing stores.
1509481Snilay@cs.wisc.edu    InstSeqNum producing_store;
1519481Snilay@cs.wisc.edu    if (inst->isLoad() && loadBarrier) {
1529481Snilay@cs.wisc.edu        producing_store = loadBarrierSN;
1536692SN/A    } else if (inst->isStore() && storeBarrier) {
1546692SN/A        producing_store = storeBarrierSN;
1559885Sstever@gmail.com    } else {
1568983Snate@binkert.org        producing_store = depPred.checkInst(inst->readPC());
1576692SN/A    }
1589885Sstever@gmail.com
15910036SAli.Saidi@ARM.com    MemDepEntryPtr store_entry = NULL;
1606692SN/A
1619348SAli.Saidi@ARM.com    // If there is a producing store, try to find the entry.
1628200SN/A    if (producing_store != 0) {
1636692SN/A        MemDepHashIt hash_it = memDepHash.find(producing_store);
1649348SAli.Saidi@ARM.com
1656692SN/A        if (hash_it != memDepHash.end()) {
1668835SAli.Saidi@ARM.com            store_entry = (*hash_it).second;
1679348SAli.Saidi@ARM.com        }
16810036SAli.Saidi@ARM.com    }
1696692SN/A
1708835SAli.Saidi@ARM.com    // If no store entry, then instruction can issue as soon as the registers
1719885Sstever@gmail.com    // are ready.
1726692SN/A    if (!store_entry) {
1736692SN/A        DPRINTF(MemDepUnit, "No dependency for inst PC "
1746692SN/A                "%#x [sn:%lli].\n", inst->readPC(), inst->seqNum);
1756692SN/A
1768983Snate@binkert.org        inst_entry->memDepReady = true;
1776692SN/A
1789885Sstever@gmail.com        if (inst->readyToIssue()) {
1799885Sstever@gmail.com            inst_entry->regsReady = true;
1809885Sstever@gmail.com
1819885Sstever@gmail.com            moveToReady(inst_entry);
1829885Sstever@gmail.com        }
18310036SAli.Saidi@ARM.com    } else {
1849885Sstever@gmail.com        // Otherwise make the instruction dependent on the store.
18510036SAli.Saidi@ARM.com        DPRINTF(MemDepUnit, "Adding to dependency list; "
1869885Sstever@gmail.com                "inst PC %#x is dependent on [sn:%lli].\n",
1879885Sstever@gmail.com                inst->readPC(), producing_store);
1886692SN/A
1896692SN/A        if (inst->readyToIssue()) {
19010036SAli.Saidi@ARM.com            inst_entry->regsReady = true;
1916692SN/A        }
1926692SN/A
1936692SN/A        // Add this instruction to the list of dependents.
1946692SN/A        store_entry->dependInsts.push_back(inst_entry);
1957761SN/A
1967761SN/A//        inst_entry->producingStore = store_entry;
19710036SAli.Saidi@ARM.com
1986692SN/A        if (inst->isLoad()) {
1996692SN/A            ++conflictingLoads;
2006692SN/A        } else {
2016692SN/A            ++conflictingStores;
2026692SN/A        }
20310036SAli.Saidi@ARM.com    }
2046692SN/A
2056692SN/A    if (inst->isStore()) {
2066692SN/A        DPRINTF(MemDepUnit, "Inserting store PC %#x [sn:%lli].\n",
2076692SN/A                inst->readPC(), inst->seqNum);
20810036SAli.Saidi@ARM.com
2096692SN/A        depPred.insertStore(inst->readPC(), inst->seqNum, inst->threadNumber);
2106692SN/A
2116692SN/A        ++insertedStores;
2126692SN/A    } else if (inst->isLoad()) {
2136692SN/A        ++insertedLoads;
2146692SN/A    } else {
2156692SN/A        panic("Unknown type! (most likely a barrier).");
2166692SN/A    }
21710036SAli.Saidi@ARM.com}
2186692SN/A
2196692SN/Atemplate <class MemDepPred, class Impl>
2206692SN/Avoid
2216692SN/AMemDepUnit<MemDepPred, Impl>::insertNonSpec(DynInstPtr &inst)
22210036SAli.Saidi@ARM.com{
2236692SN/A    unsigned tid = inst->threadNumber;
2246692SN/A
2256692SN/A    MemDepEntryPtr inst_entry = new MemDepEntry(inst);
2266692SN/A
2276692SN/A    // Insert the MemDepEntry into the hash.
2286692SN/A    memDepHash.insert(
22910036SAli.Saidi@ARM.com        std::pair<InstSeqNum, MemDepEntryPtr>(inst->seqNum, inst_entry));
2306692SN/A    MemDepEntry::memdep_insert++;
2316692SN/A
2326692SN/A    // Add the instruction to the list.
2336692SN/A    instList[tid].push_back(inst);
2346692SN/A
2356692SN/A    inst_entry->listIt = --(instList[tid].end());
2366692SN/A
2376692SN/A    // Might want to turn this part into an inline function or something.
23810036SAli.Saidi@ARM.com    // It's shared between both insert functions.
2396692SN/A    if (inst->isStore()) {
2406692SN/A        DPRINTF(MemDepUnit, "Inserting store PC %#x [sn:%lli].\n",
2416692SN/A                inst->readPC(), inst->seqNum);
2426692SN/A
24310036SAli.Saidi@ARM.com        depPred.insertStore(inst->readPC(), inst->seqNum, inst->threadNumber);
2446692SN/A
2456692SN/A        ++insertedStores;
2466692SN/A    } else if (inst->isLoad()) {
2476692SN/A        ++insertedLoads;
2486692SN/A    } else {
2496692SN/A        panic("Unknown type! (most likely a barrier).");
25010036SAli.Saidi@ARM.com    }
2516692SN/A}
2526692SN/A
2536692SN/Atemplate <class MemDepPred, class Impl>
2546692SN/Avoid
2556692SN/AMemDepUnit<MemDepPred, Impl>::insertBarrier(DynInstPtr &barr_inst)
2566692SN/A{
25710036SAli.Saidi@ARM.com    InstSeqNum barr_sn = barr_inst->seqNum;
2586692SN/A    if (barr_inst->isMemBarrier()) {
2596692SN/A        loadBarrier = true;
2606692SN/A        loadBarrierSN = barr_sn;
2616692SN/A        storeBarrier = true;
2626692SN/A        storeBarrierSN = barr_sn;
2636692SN/A        DPRINTF(MemDepUnit, "Inserted a memory barrier\n");
2646692SN/A    } else if (barr_inst->isWriteBarrier()) {
2656692SN/A        storeBarrier = true;
26610036SAli.Saidi@ARM.com        storeBarrierSN = barr_sn;
2676692SN/A        DPRINTF(MemDepUnit, "Inserted a write barrier\n");
2686692SN/A    }
2696692SN/A
2706692SN/A    unsigned tid = barr_inst->threadNumber;
27110036SAli.Saidi@ARM.com
2726692SN/A    MemDepEntryPtr inst_entry = new MemDepEntry(barr_inst);
2736692SN/A
2746692SN/A    // Add the MemDepEntry to the hash.
2756692SN/A    memDepHash.insert(
2766692SN/A        std::pair<InstSeqNum, MemDepEntryPtr>(barr_sn, inst_entry));
2776692SN/A    MemDepEntry::memdep_insert++;
27810036SAli.Saidi@ARM.com
2796692SN/A    // Add the instruction to the instruction list.
2806692SN/A    instList[tid].push_back(barr_inst);
2816692SN/A
2826692SN/A    inst_entry->listIt = --(instList[tid].end());
2836692SN/A}
2846692SN/A
28510036SAli.Saidi@ARM.comtemplate <class MemDepPred, class Impl>
2866692SN/Avoid
2876692SN/AMemDepUnit<MemDepPred, Impl>::regsReady(DynInstPtr &inst)
2886692SN/A{
2896692SN/A    DPRINTF(MemDepUnit, "Marking registers as ready for "
2906692SN/A            "instruction PC %#x [sn:%lli].\n",
2916692SN/A            inst->readPC(), inst->seqNum);
2926692SN/A
2936692SN/A    MemDepEntryPtr inst_entry = findInHash(inst);
29410036SAli.Saidi@ARM.com
2956692SN/A    inst_entry->regsReady = true;
2966692SN/A
2976692SN/A    if (inst_entry->memDepReady) {
2986692SN/A        DPRINTF(MemDepUnit, "Instruction has its memory "
29910036SAli.Saidi@ARM.com                "dependencies resolved, adding it to the ready list.\n");
3006692SN/A
3016692SN/A        moveToReady(inst_entry);
3026692SN/A    } else {
3036692SN/A        DPRINTF(MemDepUnit, "Instruction still waiting on "
3046692SN/A                "memory dependency.\n");
3056692SN/A    }
3067761SN/A}
3077761SN/A
30810036SAli.Saidi@ARM.comtemplate <class MemDepPred, class Impl>
3097761SN/Avoid
3106692SN/AMemDepUnit<MemDepPred, Impl>::nonSpecInstReady(DynInstPtr &inst)
3117761SN/A{
3126692SN/A    DPRINTF(MemDepUnit, "Marking non speculative "
31310036SAli.Saidi@ARM.com            "instruction PC %#x as ready [sn:%lli].\n",
3146692SN/A            inst->readPC(), inst->seqNum);
3157761SN/A
3167761SN/A    MemDepEntryPtr inst_entry = findInHash(inst);
3177761SN/A
3187761SN/A    moveToReady(inst_entry);
3197761SN/A}
32010036SAli.Saidi@ARM.com
3217761SN/Atemplate <class MemDepPred, class Impl>
3227761SN/Avoid
3237761SN/AMemDepUnit<MemDepPred, Impl>::reschedule(DynInstPtr &inst)
3247761SN/A{
3257761SN/A    instsToReplay.push_back(inst);
3267761SN/A}
32710036SAli.Saidi@ARM.com
3287761SN/Atemplate <class MemDepPred, class Impl>
3297761SN/Avoid
3307761SN/AMemDepUnit<MemDepPred, Impl>::replay(DynInstPtr &inst)
3317761SN/A{
3327761SN/A    DynInstPtr temp_inst;
3337761SN/A    bool found_inst = false;
33410036SAli.Saidi@ARM.com
3357761SN/A    while (!instsToReplay.empty()) {
3367761SN/A        temp_inst = instsToReplay.front();
3377761SN/A
3387761SN/A        MemDepEntryPtr inst_entry = findInHash(temp_inst);
3397761SN/A
3407761SN/A        DPRINTF(MemDepUnit, "Replaying mem instruction PC %#x "
34110036SAli.Saidi@ARM.com                "[sn:%lli].\n",
3427761SN/A                temp_inst->readPC(), temp_inst->seqNum);
3437761SN/A
3447761SN/A        moveToReady(inst_entry);
3457761SN/A
3467761SN/A        if (temp_inst == inst) {
3477761SN/A            found_inst = true;
34810036SAli.Saidi@ARM.com        }
3497761SN/A
3507761SN/A        instsToReplay.pop_front();
3517761SN/A    }
3527761SN/A
3537761SN/A    assert(found_inst);
3547761SN/A}
35510036SAli.Saidi@ARM.com
3567761SN/Atemplate <class MemDepPred, class Impl>
3577761SN/Avoid
3587761SN/AMemDepUnit<MemDepPred, Impl>::completed(DynInstPtr &inst)
3597761SN/A{
3607761SN/A    DPRINTF(MemDepUnit, "Completed mem instruction PC %#x "
3617761SN/A            "[sn:%lli].\n",
36210036SAli.Saidi@ARM.com            inst->readPC(), inst->seqNum);
3637761SN/A
3647761SN/A    unsigned tid = inst->threadNumber;
3657761SN/A
3667761SN/A    // Remove the instruction from the hash and the list.
3677761SN/A    MemDepHashIt hash_it = memDepHash.find(inst->seqNum);
3687761SN/A
36910036SAli.Saidi@ARM.com    assert(hash_it != memDepHash.end());
3707761SN/A
3717761SN/A    instList[tid].erase((*hash_it).second->listIt);
3727761SN/A
3737761SN/A//    (*hash_it).second->inst = NULL;
3747761SN/A
3757761SN/A    (*hash_it).second = NULL;
37610036SAli.Saidi@ARM.com
3777761SN/A    memDepHash.erase(hash_it);
3787761SN/A    MemDepEntry::memdep_erase++;
3797761SN/A}
3807761SN/A
3817761SN/Atemplate <class MemDepPred, class Impl>
3827761SN/Avoid
38310036SAli.Saidi@ARM.comMemDepUnit<MemDepPred, Impl>::completeBarrier(DynInstPtr &inst)
3847761SN/A{
3857761SN/A    wakeDependents(inst);
3867761SN/A    completed(inst);
3877761SN/A
3887761SN/A    InstSeqNum barr_sn = inst->seqNum;
3897761SN/A
39010036SAli.Saidi@ARM.com    if (inst->isMemBarrier()) {
3917761SN/A        assert(loadBarrier && storeBarrier);
3927761SN/A        if (loadBarrierSN == barr_sn)
3937761SN/A            loadBarrier = false;
3947761SN/A        if (storeBarrierSN == barr_sn)
3957761SN/A            storeBarrier = false;
3967761SN/A    } else if (inst->isWriteBarrier()) {
39710036SAli.Saidi@ARM.com        assert(storeBarrier);
3987761SN/A        if (storeBarrierSN == barr_sn)
3997761SN/A            storeBarrier = false;
4007761SN/A    }
4017761SN/A}
4027761SN/A
4037761SN/Atemplate <class MemDepPred, class Impl>
40410036SAli.Saidi@ARM.comvoid
4057761SN/AMemDepUnit<MemDepPred, Impl>::wakeDependents(DynInstPtr &inst)
4067761SN/A{
4077761SN/A    // Only stores and barriers have dependents.
4087761SN/A    if (!inst->isStore() && !inst->isMemBarrier() && !inst->isWriteBarrier()) {
4097761SN/A        return;
4107761SN/A    }
41110036SAli.Saidi@ARM.com
4127761SN/A    MemDepEntryPtr inst_entry = findInHash(inst);
4137761SN/A
4147761SN/A    for (int i = 0; i < inst_entry->dependInsts.size(); ++i ) {
4157761SN/A        MemDepEntryPtr woken_inst = inst_entry->dependInsts[i];
4167761SN/A
4177761SN/A        if (!woken_inst->inst) {
41810036SAli.Saidi@ARM.com            // Potentially removed mem dep entries could be on this list
4197761SN/A//            inst_entry->dependInsts[i] = NULL;
4207761SN/A            continue;
4217761SN/A        }
4227761SN/A
4237761SN/A        DPRINTF(MemDepUnit, "Waking up a dependent inst, "
4247761SN/A                "[sn:%lli].\n",
42510036SAli.Saidi@ARM.com                woken_inst->inst->seqNum);
4267761SN/A
4277761SN/A        if (woken_inst->regsReady && !woken_inst->squashed) {
4287761SN/A            moveToReady(woken_inst);
4297761SN/A        } else {
4307761SN/A            woken_inst->memDepReady = true;
4317761SN/A        }
43210036SAli.Saidi@ARM.com//        inst_entry->dependInsts[i] = NULL;
4337761SN/A    }
4347761SN/A
4357761SN/A    inst_entry->dependInsts.clear();
4367761SN/A}
4377761SN/A
4387761SN/Atemplate <class MemDepPred, class Impl>
43910036SAli.Saidi@ARM.comvoid
4407761SN/AMemDepUnit<MemDepPred, Impl>::squash(const InstSeqNum &squashed_num,
4417761SN/A                                     unsigned tid)
4427761SN/A{
4437761SN/A    if (!instsToReplay.empty()) {
4447761SN/A        ListIt replay_it = instsToReplay.begin();
4457761SN/A        while (replay_it != instsToReplay.end()) {
44610036SAli.Saidi@ARM.com            if ((*replay_it)->threadNumber == tid &&
4477761SN/A                (*replay_it)->seqNum > squashed_num) {
4487761SN/A                instsToReplay.erase(replay_it++);
4496692SN/A            } else {
4506692SN/A                ++replay_it;
4516692SN/A            }
4526692SN/A        }
4537761SN/A    }
4547761SN/A
45510036SAli.Saidi@ARM.com    ListIt squash_it = instList[tid].end();
4567761SN/A    --squash_it;
4576692SN/A
4587761SN/A    MemDepHashIt hash_it;
4596692SN/A
46010036SAli.Saidi@ARM.com    while (!instList[tid].empty() &&
4616692SN/A           (*squash_it)->seqNum > squashed_num) {
4626692SN/A
4636692SN/A        DPRINTF(MemDepUnit, "Squashing inst [sn:%lli]\n",
4646692SN/A                (*squash_it)->seqNum);
4656692SN/A
4666692SN/A        hash_it = memDepHash.find((*squash_it)->seqNum);
4677761SN/A
4687761SN/A        assert(hash_it != memDepHash.end());
46910036SAli.Saidi@ARM.com
4707761SN/A        (*hash_it).second->squashed = true;
4717761SN/A/*
4727761SN/A        for (int i = 0; i < (*hash_it).second->dependInsts.size(); ++i) {
4737761SN/A            (*hash_it).second->dependInsts[i] = NULL;
47410036SAli.Saidi@ARM.com        }
4757761SN/A
4767761SN/A        (*hash_it).second->inst = NULL;
4777761SN/A*/
4787761SN/A        (*hash_it).second = NULL;
4797761SN/A
4807761SN/A        memDepHash.erase(hash_it);
48110036SAli.Saidi@ARM.com        MemDepEntry::memdep_erase++;
4827761SN/A
4837761SN/A        instList[tid].erase(squash_it--);
4847761SN/A    }
4857761SN/A
4867761SN/A    // Tell the dependency predictor to squash as well.
4877761SN/A    depPred.squash(squashed_num, tid);
4886692SN/A}
4896692SN/A
49010036SAli.Saidi@ARM.comtemplate <class MemDepPred, class Impl>
4917761SN/Avoid
4926692SN/AMemDepUnit<MemDepPred, Impl>::violation(DynInstPtr &store_inst,
4937761SN/A                                        DynInstPtr &violating_load)
4946692SN/A{
49510036SAli.Saidi@ARM.com    DPRINTF(MemDepUnit, "Passing violating PCs to store sets,"
4966692SN/A            " load: %#x, store: %#x\n", violating_load->readPC(),
4976692SN/A            store_inst->readPC());
4986692SN/A    // Tell the memory dependence unit of the violation.
4996692SN/A    depPred.violation(violating_load->readPC(), store_inst->readPC());
5006692SN/A}
5016692SN/A
5029885Sstever@gmail.comtemplate <class MemDepPred, class Impl>
5038983Snate@binkert.orgvoid
5046692SN/AMemDepUnit<MemDepPred, Impl>::issue(DynInstPtr &inst)
5059885Sstever@gmail.com{
50610036SAli.Saidi@ARM.com    DPRINTF(MemDepUnit, "Issuing instruction PC %#x [sn:%lli].\n",
5076692SN/A            inst->readPC(), inst->seqNum);
5089348SAli.Saidi@ARM.com
5098200SN/A    depPred.issued(inst->readPC(), inst->seqNum, inst->isStore());
5106692SN/A}
5119348SAli.Saidi@ARM.com
5126692SN/Atemplate <class MemDepPred, class Impl>
5138835SAli.Saidi@ARM.cominline typename MemDepUnit<MemDepPred,Impl>::MemDepEntryPtr &
5149348SAli.Saidi@ARM.comMemDepUnit<MemDepPred, Impl>::findInHash(const DynInstPtr &inst)
51510036SAli.Saidi@ARM.com{
5166692SN/A    MemDepHashIt hash_it = memDepHash.find(inst->seqNum);
5178835SAli.Saidi@ARM.com
5189885Sstever@gmail.com    assert(hash_it != memDepHash.end());
5196692SN/A
5206692SN/A    return (*hash_it).second;
5216692SN/A}
5226692SN/A
5238983Snate@binkert.orgtemplate <class MemDepPred, class Impl>
5246692SN/Ainline void
5259885Sstever@gmail.comMemDepUnit<MemDepPred, Impl>::moveToReady(MemDepEntryPtr &woken_inst_entry)
5269885Sstever@gmail.com{
5279885Sstever@gmail.com    DPRINTF(MemDepUnit, "Adding instruction [sn:%lli] "
5289885Sstever@gmail.com            "to the ready list.\n", woken_inst_entry->inst->seqNum);
5299885Sstever@gmail.com
53010036SAli.Saidi@ARM.com    assert(!woken_inst_entry->squashed);
5319885Sstever@gmail.com
53210036SAli.Saidi@ARM.com    iqPtr->addReadyMemInst(woken_inst_entry->inst);
5339885Sstever@gmail.com}
5349885Sstever@gmail.com
5358835SAli.Saidi@ARM.com
5368835SAli.Saidi@ARM.comtemplate <class MemDepPred, class Impl>
53710036SAli.Saidi@ARM.comvoid
5388835SAli.Saidi@ARM.comMemDepUnit<MemDepPred, Impl>::dumpLists()
5399348SAli.Saidi@ARM.com{
5409348SAli.Saidi@ARM.com    for (unsigned tid=0; tid < Impl::MaxThreads; tid++) {
54110036SAli.Saidi@ARM.com        cprintf("Instruction list %i size: %i\n",
5429348SAli.Saidi@ARM.com                tid, instList[tid].size());
5436692SN/A
5446692SN/A        ListIt inst_list_it = instList[tid].begin();
54510036SAli.Saidi@ARM.com        int num = 0;
5466692SN/A
5476692SN/A        while (inst_list_it != instList[tid].end()) {
5486692SN/A            cprintf("Instruction:%i\nPC:%#x\n[sn:%i]\n[tid:%i]\nIssued:%i\n"
5496692SN/A                    "Squashed:%i\n\n",
5509885Sstever@gmail.com                    num, (*inst_list_it)->readPC(),
5518983Snate@binkert.org                    (*inst_list_it)->seqNum,
5529348SAli.Saidi@ARM.com                    (*inst_list_it)->threadNumber,
5539885Sstever@gmail.com                    (*inst_list_it)->isIssued(),
55410036SAli.Saidi@ARM.com                    (*inst_list_it)->isSquashed());
5556692SN/A            inst_list_it++;
5569348SAli.Saidi@ARM.com            ++num;
5578200SN/A        }
5586692SN/A    }
5599348SAli.Saidi@ARM.com
5606692SN/A    cprintf("Memory dependence hash size: %i\n", memDepHash.size());
5618835SAli.Saidi@ARM.com
5629348SAli.Saidi@ARM.com    cprintf("Memory dependence entries: %i\n", MemDepEntry::memdep_count);
56310036SAli.Saidi@ARM.com}
5646692SN/A