lsq_impl.hh revision 9868
15434Sgblack@eecs.umich.edu/* 24276Sgblack@eecs.umich.edu * Copyright (c) 2011-2012 ARM Limited 34276Sgblack@eecs.umich.edu * All rights reserved 47087Snate@binkert.org * 57087Snate@binkert.org * The license below extends only to copyright in the software and shall 67087Snate@binkert.org * not be construed as granting a license to any other intellectual 77087Snate@binkert.org * property including but not limited to intellectual property relating 87087Snate@binkert.org * to a hardware implementation of the functionality of the software 97087Snate@binkert.org * licensed hereunder. You may use the software subject to the license 107087Snate@binkert.org * terms below provided that you ensure that this notice is replicated 117087Snate@binkert.org * unmodified and in its entirety in all distributions of the software, 124276Sgblack@eecs.umich.edu * modified or unmodified, in source code or in binary form. 137087Snate@binkert.org * 147087Snate@binkert.org * Copyright (c) 2005-2006 The Regents of The University of Michigan 157087Snate@binkert.org * All rights reserved. 167087Snate@binkert.org * 177087Snate@binkert.org * Redistribution and use in source and binary forms, with or without 187087Snate@binkert.org * modification, are permitted provided that the following conditions are 197087Snate@binkert.org * met: redistributions of source code must retain the above copyright 207087Snate@binkert.org * notice, this list of conditions and the following disclaimer; 214276Sgblack@eecs.umich.edu * redistributions in binary form must reproduce the above copyright 227087Snate@binkert.org * notice, this list of conditions and the following disclaimer in the 234276Sgblack@eecs.umich.edu * documentation and/or other materials provided with the distribution; 244276Sgblack@eecs.umich.edu * neither the name of the copyright holders nor the names of its 254276Sgblack@eecs.umich.edu * contributors may be used to endorse or promote products derived from 264276Sgblack@eecs.umich.edu * this software without specific prior written permission. 274276Sgblack@eecs.umich.edu * 284276Sgblack@eecs.umich.edu * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 294276Sgblack@eecs.umich.edu * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 304276Sgblack@eecs.umich.edu * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 314276Sgblack@eecs.umich.edu * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 324276Sgblack@eecs.umich.edu * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 334276Sgblack@eecs.umich.edu * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 344276Sgblack@eecs.umich.edu * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 354276Sgblack@eecs.umich.edu * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 364276Sgblack@eecs.umich.edu * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 374276Sgblack@eecs.umich.edu * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 384276Sgblack@eecs.umich.edu * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 394276Sgblack@eecs.umich.edu * 404276Sgblack@eecs.umich.edu * Authors: Korey Sewell 414276Sgblack@eecs.umich.edu */ 424276Sgblack@eecs.umich.edu 434276Sgblack@eecs.umich.edu#include <algorithm> 445162Sgblack@eecs.umich.edu#include <list> 454276Sgblack@eecs.umich.edu#include <string> 464592Sgblack@eecs.umich.edu 475162Sgblack@eecs.umich.edu#include "cpu/o3/lsq.hh" 485162Sgblack@eecs.umich.edu#include "debug/Drain.hh" 494592Sgblack@eecs.umich.edu#include "debug/Fetch.hh" 504592Sgblack@eecs.umich.edu#include "debug/LSQ.hh" 515162Sgblack@eecs.umich.edu#include "debug/Writeback.hh" 525162Sgblack@eecs.umich.edu#include "params/DerivO3CPU.hh" 534592Sgblack@eecs.umich.edu 544725Sgblack@eecs.umich.eduusing namespace std; 554725Sgblack@eecs.umich.edu 564725Sgblack@eecs.umich.edutemplate <class Impl> 574746Sgblack@eecs.umich.eduLSQ<Impl>::LSQ(O3CPU *cpu_ptr, IEW *iew_ptr, DerivO3CPUParams *params) 584276Sgblack@eecs.umich.edu : cpu(cpu_ptr), iewStage(iew_ptr), 594276Sgblack@eecs.umich.edu LQEntries(params->LQEntries), 604592Sgblack@eecs.umich.edu SQEntries(params->SQEntries), 615162Sgblack@eecs.umich.edu numThreads(params->numThreads), 625162Sgblack@eecs.umich.edu retryTid(-1) 634592Sgblack@eecs.umich.edu{ 644276Sgblack@eecs.umich.edu assert(numThreads > 0 && numThreads <= Impl::MaxThreads); 654276Sgblack@eecs.umich.edu 664276Sgblack@eecs.umich.edu //**********************************************/ 674725Sgblack@eecs.umich.edu //************ Handle SMT Parameters ***********/ 684725Sgblack@eecs.umich.edu //**********************************************/ 694725Sgblack@eecs.umich.edu std::string policy = params->smtLSQPolicy; 704746Sgblack@eecs.umich.edu 714276Sgblack@eecs.umich.edu //Convert string to lowercase 724276Sgblack@eecs.umich.edu std::transform(policy.begin(), policy.end(), policy.begin(), 734592Sgblack@eecs.umich.edu (int(*)(int)) tolower); 745162Sgblack@eecs.umich.edu 755162Sgblack@eecs.umich.edu //Figure out fetch policy 764592Sgblack@eecs.umich.edu if (policy == "dynamic") { 774592Sgblack@eecs.umich.edu lsqPolicy = Dynamic; 785162Sgblack@eecs.umich.edu 795162Sgblack@eecs.umich.edu maxLQEntries = LQEntries; 804592Sgblack@eecs.umich.edu maxSQEntries = SQEntries; 814728Sgblack@eecs.umich.edu 824728Sgblack@eecs.umich.edu DPRINTF(LSQ, "LSQ sharing policy set to Dynamic\n"); 834728Sgblack@eecs.umich.edu } else if (policy == "partitioned") { 844746Sgblack@eecs.umich.edu lsqPolicy = Partitioned; 854276Sgblack@eecs.umich.edu 864276Sgblack@eecs.umich.edu //@todo:make work if part_amt doesnt divide evenly. 874592Sgblack@eecs.umich.edu maxLQEntries = LQEntries / numThreads; 885162Sgblack@eecs.umich.edu maxSQEntries = SQEntries / numThreads; 895162Sgblack@eecs.umich.edu 904592Sgblack@eecs.umich.edu DPRINTF(Fetch, "LSQ sharing policy set to Partitioned: " 914592Sgblack@eecs.umich.edu "%i entries per LQ | %i entries per SQ\n", 925162Sgblack@eecs.umich.edu maxLQEntries,maxSQEntries); 935162Sgblack@eecs.umich.edu } else if (policy == "threshold") { 944592Sgblack@eecs.umich.edu lsqPolicy = Threshold; 954728Sgblack@eecs.umich.edu 964728Sgblack@eecs.umich.edu assert(params->smtLSQThreshold > LQEntries); 974728Sgblack@eecs.umich.edu assert(params->smtLSQThreshold > SQEntries); 984746Sgblack@eecs.umich.edu 994276Sgblack@eecs.umich.edu //Divide up by threshold amount 1004276Sgblack@eecs.umich.edu //@todo: Should threads check the max and the total 1014276Sgblack@eecs.umich.edu //amount of the LSQ 1024276Sgblack@eecs.umich.edu maxLQEntries = params->smtLSQThreshold; 1034592Sgblack@eecs.umich.edu maxSQEntries = params->smtLSQThreshold; 1045162Sgblack@eecs.umich.edu 1055162Sgblack@eecs.umich.edu DPRINTF(LSQ, "LSQ sharing policy set to Threshold: " 1064592Sgblack@eecs.umich.edu "%i entries per LQ | %i entries per SQ\n", 1074725Sgblack@eecs.umich.edu maxLQEntries,maxSQEntries); 1084725Sgblack@eecs.umich.edu } else { 1094725Sgblack@eecs.umich.edu assert(0 && "Invalid LSQ Sharing Policy.Options Are:{Dynamic," 1104746Sgblack@eecs.umich.edu "Partitioned, Threshold}"); 1114276Sgblack@eecs.umich.edu } 1124276Sgblack@eecs.umich.edu 1134276Sgblack@eecs.umich.edu //Initialize LSQs 1144276Sgblack@eecs.umich.edu thread = new LSQUnit[numThreads]; 1155162Sgblack@eecs.umich.edu for (ThreadID tid = 0; tid < numThreads; tid++) { 1165162Sgblack@eecs.umich.edu thread[tid].init(cpu, iew_ptr, params, this, 1175162Sgblack@eecs.umich.edu maxLQEntries, maxSQEntries, tid); 1185162Sgblack@eecs.umich.edu thread[tid].setDcachePort(&cpu_ptr->getDataPort()); 1194725Sgblack@eecs.umich.edu } 1204725Sgblack@eecs.umich.edu} 1214725Sgblack@eecs.umich.edu 1224746Sgblack@eecs.umich.edu 1234276Sgblack@eecs.umich.edutemplate<class Impl> 1244276Sgblack@eecs.umich.edustd::string 1254276Sgblack@eecs.umich.eduLSQ<Impl>::name() const 1264276Sgblack@eecs.umich.edu{ 1274592Sgblack@eecs.umich.edu return iewStage->name() + ".lsq"; 1285162Sgblack@eecs.umich.edu} 1295162Sgblack@eecs.umich.edu 1304592Sgblack@eecs.umich.edutemplate<class Impl> 1314527Sgblack@eecs.umich.eduvoid 1324527Sgblack@eecs.umich.eduLSQ<Impl>::regStats() 1334725Sgblack@eecs.umich.edu{ 1344746Sgblack@eecs.umich.edu //Initialize LSQs 1354276Sgblack@eecs.umich.edu for (ThreadID tid = 0; tid < numThreads; tid++) { 1364276Sgblack@eecs.umich.edu thread[tid].regStats(); 1374276Sgblack@eecs.umich.edu } 1384276Sgblack@eecs.umich.edu} 1394592Sgblack@eecs.umich.edu 1405162Sgblack@eecs.umich.edutemplate<class Impl> 1415162Sgblack@eecs.umich.eduvoid 1424592Sgblack@eecs.umich.eduLSQ<Impl>::setActiveThreads(list<ThreadID> *at_ptr) 1434725Sgblack@eecs.umich.edu{ 1444725Sgblack@eecs.umich.edu activeThreads = at_ptr; 1454725Sgblack@eecs.umich.edu assert(activeThreads != 0); 1464746Sgblack@eecs.umich.edu} 1474276Sgblack@eecs.umich.edu 1485162Sgblack@eecs.umich.edutemplate <class Impl> 1495162Sgblack@eecs.umich.eduvoid 1505162Sgblack@eecs.umich.eduLSQ<Impl>::drainSanityCheck() const 1515162Sgblack@eecs.umich.edu{ 1524276Sgblack@eecs.umich.edu assert(isDrained()); 1535162Sgblack@eecs.umich.edu 1545162Sgblack@eecs.umich.edu for (ThreadID tid = 0; tid < numThreads; tid++) 1555162Sgblack@eecs.umich.edu thread[tid].drainSanityCheck(); 1565162Sgblack@eecs.umich.edu} 1575162Sgblack@eecs.umich.edu 1585162Sgblack@eecs.umich.edutemplate <class Impl> 1595162Sgblack@eecs.umich.edubool 1604276Sgblack@eecs.umich.eduLSQ<Impl>::isDrained() const 1614592Sgblack@eecs.umich.edu{ 1625162Sgblack@eecs.umich.edu bool drained(true); 1635162Sgblack@eecs.umich.edu 1644592Sgblack@eecs.umich.edu if (!lqEmpty()) { 1654592Sgblack@eecs.umich.edu DPRINTF(Drain, "Not drained, LQ not empty.\n"); 1665162Sgblack@eecs.umich.edu drained = false; 1675162Sgblack@eecs.umich.edu } 1684592Sgblack@eecs.umich.edu 1694592Sgblack@eecs.umich.edu if (!sqEmpty()) { 1705162Sgblack@eecs.umich.edu DPRINTF(Drain, "Not drained, SQ not empty.\n"); 1715164Sgblack@eecs.umich.edu drained = false; 1724592Sgblack@eecs.umich.edu } 1734595Sgblack@eecs.umich.edu 1744746Sgblack@eecs.umich.edu if (retryTid != InvalidThreadID) { 1754746Sgblack@eecs.umich.edu DPRINTF(Drain, "Not drained, the LSQ has blocked the caches.\n"); 1764746Sgblack@eecs.umich.edu drained = false; 1775162Sgblack@eecs.umich.edu } 1785162Sgblack@eecs.umich.edu 1794595Sgblack@eecs.umich.edu return drained; 1804276Sgblack@eecs.umich.edu} 1814276Sgblack@eecs.umich.edu 1824276Sgblack@eecs.umich.edutemplate <class Impl> 1834276Sgblack@eecs.umich.eduvoid 1844276Sgblack@eecs.umich.eduLSQ<Impl>::takeOverFrom() 1854276Sgblack@eecs.umich.edu{ 1864276Sgblack@eecs.umich.edu for (ThreadID tid = 0; tid < numThreads; tid++) { 1874276Sgblack@eecs.umich.edu thread[tid].takeOverFrom(); 1884276Sgblack@eecs.umich.edu } 1894276Sgblack@eecs.umich.edu} 1905162Sgblack@eecs.umich.edu 1915162Sgblack@eecs.umich.edutemplate <class Impl> 1925162Sgblack@eecs.umich.eduint 1935162Sgblack@eecs.umich.eduLSQ<Impl>::entryAmount(ThreadID num_threads) 1945167Sgblack@eecs.umich.edu{ 1955167Sgblack@eecs.umich.edu if (lsqPolicy == Partitioned) { 1965167Sgblack@eecs.umich.edu return LQEntries / num_threads; 1975167Sgblack@eecs.umich.edu } else { 1984276Sgblack@eecs.umich.edu return 0; 1995162Sgblack@eecs.umich.edu } 2005162Sgblack@eecs.umich.edu} 2015162Sgblack@eecs.umich.edu 2025162Sgblack@eecs.umich.edutemplate <class Impl> 2035162Sgblack@eecs.umich.eduvoid 2045162Sgblack@eecs.umich.eduLSQ<Impl>::resetEntries() 2055162Sgblack@eecs.umich.edu{ 2065162Sgblack@eecs.umich.edu if (lsqPolicy != Dynamic || numThreads > 1) { 2075162Sgblack@eecs.umich.edu int active_threads = activeThreads->size(); 2085162Sgblack@eecs.umich.edu 2095162Sgblack@eecs.umich.edu int maxEntries; 2105162Sgblack@eecs.umich.edu 2115162Sgblack@eecs.umich.edu if (lsqPolicy == Partitioned) { 2125162Sgblack@eecs.umich.edu maxEntries = LQEntries / active_threads; 2135162Sgblack@eecs.umich.edu } else if (lsqPolicy == Threshold && active_threads == 1) { 2145162Sgblack@eecs.umich.edu maxEntries = LQEntries; 2155162Sgblack@eecs.umich.edu } else { 2165162Sgblack@eecs.umich.edu maxEntries = LQEntries; 2175162Sgblack@eecs.umich.edu } 2185162Sgblack@eecs.umich.edu 2195162Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 2205162Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 2215162Sgblack@eecs.umich.edu 2225162Sgblack@eecs.umich.edu while (threads != end) { 2235162Sgblack@eecs.umich.edu ThreadID tid = *threads++; 2245162Sgblack@eecs.umich.edu 2255162Sgblack@eecs.umich.edu resizeEntries(maxEntries, tid); 2265162Sgblack@eecs.umich.edu } 2275162Sgblack@eecs.umich.edu } 2285162Sgblack@eecs.umich.edu} 2295162Sgblack@eecs.umich.edu 2304727Sgblack@eecs.umich.edutemplate<class Impl> 2315162Sgblack@eecs.umich.eduvoid 2325162Sgblack@eecs.umich.eduLSQ<Impl>::removeEntries(ThreadID tid) 2335162Sgblack@eecs.umich.edu{ 2345162Sgblack@eecs.umich.edu thread[tid].clearLQ(); 2355162Sgblack@eecs.umich.edu thread[tid].clearSQ(); 2365162Sgblack@eecs.umich.edu} 2375162Sgblack@eecs.umich.edu 2385162Sgblack@eecs.umich.edutemplate<class Impl> 2395162Sgblack@eecs.umich.eduvoid 2405162Sgblack@eecs.umich.eduLSQ<Impl>::resizeEntries(unsigned size, ThreadID tid) 2414727Sgblack@eecs.umich.edu{ 2425162Sgblack@eecs.umich.edu thread[tid].resizeLQ(size); 2435162Sgblack@eecs.umich.edu thread[tid].resizeSQ(size); 2445162Sgblack@eecs.umich.edu} 2455162Sgblack@eecs.umich.edu 2464728Sgblack@eecs.umich.edutemplate<class Impl> 2474728Sgblack@eecs.umich.eduvoid 2484728Sgblack@eecs.umich.eduLSQ<Impl>::tick() 2494728Sgblack@eecs.umich.edu{ 2504728Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 2514728Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 2524728Sgblack@eecs.umich.edu 2534728Sgblack@eecs.umich.edu while (threads != end) { 2544725Sgblack@eecs.umich.edu ThreadID tid = *threads++; 2554575Sgblack@eecs.umich.edu 2565162Sgblack@eecs.umich.edu thread[tid].tick(); 2575162Sgblack@eecs.umich.edu } 2585162Sgblack@eecs.umich.edu} 2595162Sgblack@eecs.umich.edu 2605162Sgblack@eecs.umich.edutemplate<class Impl> 2615162Sgblack@eecs.umich.eduvoid 2625162Sgblack@eecs.umich.eduLSQ<Impl>::insertLoad(DynInstPtr &load_inst) 2635162Sgblack@eecs.umich.edu{ 2645162Sgblack@eecs.umich.edu ThreadID tid = load_inst->threadNumber; 2655162Sgblack@eecs.umich.edu 2665162Sgblack@eecs.umich.edu thread[tid].insertLoad(load_inst); 2675162Sgblack@eecs.umich.edu} 2685162Sgblack@eecs.umich.edu 2695162Sgblack@eecs.umich.edutemplate<class Impl> 2705162Sgblack@eecs.umich.eduvoid 2714276Sgblack@eecs.umich.eduLSQ<Impl>::insertStore(DynInstPtr &store_inst) 2724276Sgblack@eecs.umich.edu{ 2735162Sgblack@eecs.umich.edu ThreadID tid = store_inst->threadNumber; 2745162Sgblack@eecs.umich.edu 2755162Sgblack@eecs.umich.edu thread[tid].insertStore(store_inst); 2765162Sgblack@eecs.umich.edu} 2775294Sgblack@eecs.umich.edu 2785294Sgblack@eecs.umich.edutemplate<class Impl> 2795294Sgblack@eecs.umich.eduFault 2805294Sgblack@eecs.umich.eduLSQ<Impl>::executeLoad(DynInstPtr &inst) 2815162Sgblack@eecs.umich.edu{ 2825294Sgblack@eecs.umich.edu ThreadID tid = inst->threadNumber; 2835294Sgblack@eecs.umich.edu 2845294Sgblack@eecs.umich.edu return thread[tid].executeLoad(inst); 2855294Sgblack@eecs.umich.edu} 2865294Sgblack@eecs.umich.edu 2875294Sgblack@eecs.umich.edutemplate<class Impl> 2885294Sgblack@eecs.umich.eduFault 2895294Sgblack@eecs.umich.eduLSQ<Impl>::executeStore(DynInstPtr &inst) 2905294Sgblack@eecs.umich.edu{ 2915294Sgblack@eecs.umich.edu ThreadID tid = inst->threadNumber; 2925168Sgblack@eecs.umich.edu 2935168Sgblack@eecs.umich.edu return thread[tid].executeStore(inst); 2945168Sgblack@eecs.umich.edu} 2955168Sgblack@eecs.umich.edu 2965168Sgblack@eecs.umich.edutemplate<class Impl> 2974276Sgblack@eecs.umich.eduvoid 2984276Sgblack@eecs.umich.eduLSQ<Impl>::writebackStores() 2995162Sgblack@eecs.umich.edu{ 3005162Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 3014276Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 3024276Sgblack@eecs.umich.edu 3035162Sgblack@eecs.umich.edu while (threads != end) { 3045162Sgblack@eecs.umich.edu ThreadID tid = *threads++; 3054592Sgblack@eecs.umich.edu 3065162Sgblack@eecs.umich.edu if (numStoresToWB(tid) > 0) { 3075162Sgblack@eecs.umich.edu DPRINTF(Writeback,"[tid:%i] Writing back stores. %i stores " 3084592Sgblack@eecs.umich.edu "available for Writeback.\n", tid, numStoresToWB(tid)); 3095162Sgblack@eecs.umich.edu } 3105174Sgblack@eecs.umich.edu 3115174Sgblack@eecs.umich.edu thread[tid].writebackStores(); 3125174Sgblack@eecs.umich.edu } 3135174Sgblack@eecs.umich.edu} 3145174Sgblack@eecs.umich.edu 3156460Sgblack@eecs.umich.edutemplate<class Impl> 3166460Sgblack@eecs.umich.edubool 3174276Sgblack@eecs.umich.eduLSQ<Impl>::violation() 3185162Sgblack@eecs.umich.edu{ 3195162Sgblack@eecs.umich.edu /* Answers: Does Anybody Have a Violation?*/ 3205162Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 3215162Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 3225162Sgblack@eecs.umich.edu 3235162Sgblack@eecs.umich.edu while (threads != end) { 3245162Sgblack@eecs.umich.edu ThreadID tid = *threads++; 3255162Sgblack@eecs.umich.edu 3265162Sgblack@eecs.umich.edu if (thread[tid].violation()) 3275162Sgblack@eecs.umich.edu return true; 3285162Sgblack@eecs.umich.edu } 3295162Sgblack@eecs.umich.edu 3305162Sgblack@eecs.umich.edu return false; 3315162Sgblack@eecs.umich.edu} 3325162Sgblack@eecs.umich.edu 3335162Sgblack@eecs.umich.edutemplate <class Impl> 3345162Sgblack@eecs.umich.eduvoid 3355162Sgblack@eecs.umich.eduLSQ<Impl>::recvRetry() 3365162Sgblack@eecs.umich.edu{ 3375162Sgblack@eecs.umich.edu if (retryTid == InvalidThreadID) 3385162Sgblack@eecs.umich.edu { 3395162Sgblack@eecs.umich.edu //Squashed, so drop it 3405162Sgblack@eecs.umich.edu return; 3415162Sgblack@eecs.umich.edu } 3425162Sgblack@eecs.umich.edu int curr_retry_tid = retryTid; 3435162Sgblack@eecs.umich.edu // Speculatively clear the retry Tid. This will get set again if 3445162Sgblack@eecs.umich.edu // the LSQUnit was unable to complete its access. 3455162Sgblack@eecs.umich.edu retryTid = -1; 3465162Sgblack@eecs.umich.edu thread[curr_retry_tid].recvRetry(); 3475162Sgblack@eecs.umich.edu} 3485162Sgblack@eecs.umich.edu 3495162Sgblack@eecs.umich.edutemplate <class Impl> 3505162Sgblack@eecs.umich.edubool 3515151Sgblack@eecs.umich.eduLSQ<Impl>::recvTimingResp(PacketPtr pkt) 3525162Sgblack@eecs.umich.edu{ 3535162Sgblack@eecs.umich.edu if (pkt->isError()) 3545162Sgblack@eecs.umich.edu DPRINTF(LSQ, "Got error packet back for address: %#X\n", 3555162Sgblack@eecs.umich.edu pkt->getAddr()); 3565162Sgblack@eecs.umich.edu thread[pkt->req->threadId()].completeDataAccess(pkt); 3575162Sgblack@eecs.umich.edu return true; 3585162Sgblack@eecs.umich.edu} 3595162Sgblack@eecs.umich.edu 3605162Sgblack@eecs.umich.edutemplate <class Impl> 3615162Sgblack@eecs.umich.eduvoid 3625150Sgblack@eecs.umich.eduLSQ<Impl>::recvTimingSnoopReq(PacketPtr pkt) 3635162Sgblack@eecs.umich.edu{ 3645162Sgblack@eecs.umich.edu DPRINTF(LSQ, "received pkt for addr:%#x %s\n", pkt->getAddr(), 3655162Sgblack@eecs.umich.edu pkt->cmdString()); 3665162Sgblack@eecs.umich.edu 3675162Sgblack@eecs.umich.edu // must be a snoop 3685162Sgblack@eecs.umich.edu if (pkt->isInvalidate()) { 3695162Sgblack@eecs.umich.edu DPRINTF(LSQ, "received invalidation for addr:%#x\n", 3705162Sgblack@eecs.umich.edu pkt->getAddr()); 3715162Sgblack@eecs.umich.edu for (ThreadID tid = 0; tid < numThreads; tid++) { 3725162Sgblack@eecs.umich.edu thread[tid].checkSnoop(pkt); 3735162Sgblack@eecs.umich.edu } 3745162Sgblack@eecs.umich.edu } 3755162Sgblack@eecs.umich.edu} 3765162Sgblack@eecs.umich.edu 3775162Sgblack@eecs.umich.edutemplate<class Impl> 3785162Sgblack@eecs.umich.eduint 3795162Sgblack@eecs.umich.eduLSQ<Impl>::getCount() 3805162Sgblack@eecs.umich.edu{ 3815162Sgblack@eecs.umich.edu unsigned total = 0; 3824575Sgblack@eecs.umich.edu 3834276Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 3845162Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 3855162Sgblack@eecs.umich.edu 3865171Sgblack@eecs.umich.edu while (threads != end) { 3875171Sgblack@eecs.umich.edu ThreadID tid = *threads++; 3885171Sgblack@eecs.umich.edu 3895171Sgblack@eecs.umich.edu total += getCount(tid); 3905162Sgblack@eecs.umich.edu } 3915162Sgblack@eecs.umich.edu 3925295Sgblack@eecs.umich.edu return total; 3935295Sgblack@eecs.umich.edu} 3945295Sgblack@eecs.umich.edu 3955295Sgblack@eecs.umich.edutemplate<class Impl> 3965162Sgblack@eecs.umich.eduint 3975957Sgblack@eecs.umich.eduLSQ<Impl>::numLoads() 3985162Sgblack@eecs.umich.edu{ 3995957Sgblack@eecs.umich.edu unsigned total = 0; 4005957Sgblack@eecs.umich.edu 4015957Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 4025957Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 4035957Sgblack@eecs.umich.edu 4046867Snate@binkert.org while (threads != end) { 4055957Sgblack@eecs.umich.edu ThreadID tid = *threads++; 4065957Sgblack@eecs.umich.edu 4075957Sgblack@eecs.umich.edu total += numLoads(tid); 4085957Sgblack@eecs.umich.edu } 4095162Sgblack@eecs.umich.edu 4105162Sgblack@eecs.umich.edu return total; 4115162Sgblack@eecs.umich.edu} 4125162Sgblack@eecs.umich.edu 4135434Sgblack@eecs.umich.edutemplate<class Impl> 4145434Sgblack@eecs.umich.eduint 4155434Sgblack@eecs.umich.eduLSQ<Impl>::numStores() 4165434Sgblack@eecs.umich.edu{ 4175434Sgblack@eecs.umich.edu unsigned total = 0; 4184592Sgblack@eecs.umich.edu 4194276Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 4204276Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 4215162Sgblack@eecs.umich.edu 4225162Sgblack@eecs.umich.edu while (threads != end) { 4235162Sgblack@eecs.umich.edu ThreadID tid = *threads++; 4245162Sgblack@eecs.umich.edu 4255162Sgblack@eecs.umich.edu total += thread[tid].numStores(); 4265162Sgblack@eecs.umich.edu } 4275162Sgblack@eecs.umich.edu 4285162Sgblack@eecs.umich.edu return total; 4295162Sgblack@eecs.umich.edu} 4305162Sgblack@eecs.umich.edu 4315162Sgblack@eecs.umich.edutemplate<class Impl> 4325162Sgblack@eecs.umich.eduunsigned 4335162Sgblack@eecs.umich.eduLSQ<Impl>::numFreeEntries() 4345162Sgblack@eecs.umich.edu{ 4355162Sgblack@eecs.umich.edu unsigned total = 0; 4365162Sgblack@eecs.umich.edu 4375162Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 4385162Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 4395162Sgblack@eecs.umich.edu 4405162Sgblack@eecs.umich.edu while (threads != end) { 4415162Sgblack@eecs.umich.edu ThreadID tid = *threads++; 4425162Sgblack@eecs.umich.edu 4435162Sgblack@eecs.umich.edu total += thread[tid].numFreeEntries(); 4445162Sgblack@eecs.umich.edu } 4455162Sgblack@eecs.umich.edu 4465162Sgblack@eecs.umich.edu return total; 4475162Sgblack@eecs.umich.edu} 4485162Sgblack@eecs.umich.edu 4495162Sgblack@eecs.umich.edutemplate<class Impl> 4505162Sgblack@eecs.umich.eduunsigned 4515162Sgblack@eecs.umich.eduLSQ<Impl>::numFreeEntries(ThreadID tid) 4525162Sgblack@eecs.umich.edu{ 4535162Sgblack@eecs.umich.edu //if (lsqPolicy == Dynamic) 4545162Sgblack@eecs.umich.edu //return numFreeEntries(); 4555162Sgblack@eecs.umich.edu //else 4565162Sgblack@eecs.umich.edu return thread[tid].numFreeEntries(); 4575162Sgblack@eecs.umich.edu} 4585162Sgblack@eecs.umich.edu 4595162Sgblack@eecs.umich.edutemplate<class Impl> 4605162Sgblack@eecs.umich.edubool 4615162Sgblack@eecs.umich.eduLSQ<Impl>::isFull() 4625162Sgblack@eecs.umich.edu{ 4635162Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 4645162Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 4655162Sgblack@eecs.umich.edu 4665162Sgblack@eecs.umich.edu while (threads != end) { 4674760Sgblack@eecs.umich.edu ThreadID tid = *threads++; 4684592Sgblack@eecs.umich.edu 4695162Sgblack@eecs.umich.edu if (!(thread[tid].lqFull() || thread[tid].sqFull())) 4705162Sgblack@eecs.umich.edu return false; 4714592Sgblack@eecs.umich.edu } 4724592Sgblack@eecs.umich.edu 4735162Sgblack@eecs.umich.edu return true; 4745162Sgblack@eecs.umich.edu} 4754592Sgblack@eecs.umich.edu 4764592Sgblack@eecs.umich.edutemplate<class Impl> 4775162Sgblack@eecs.umich.edubool 4785166Sgblack@eecs.umich.eduLSQ<Impl>::isFull(ThreadID tid) 4794592Sgblack@eecs.umich.edu{ 4805165Sgblack@eecs.umich.edu //@todo: Change to Calculate All Entries for 4814276Sgblack@eecs.umich.edu //Dynamic Policy 4824825Sgblack@eecs.umich.edu if (lsqPolicy == Dynamic) 4834276Sgblack@eecs.umich.edu return isFull(); 4845162Sgblack@eecs.umich.edu else 4855162Sgblack@eecs.umich.edu return thread[tid].lqFull() || thread[tid].sqFull(); 4865162Sgblack@eecs.umich.edu} 4875162Sgblack@eecs.umich.edu 4885162Sgblack@eecs.umich.edutemplate<class Impl> 4895162Sgblack@eecs.umich.edubool 4905162Sgblack@eecs.umich.eduLSQ<Impl>::isEmpty() const 4915162Sgblack@eecs.umich.edu{ 4924276Sgblack@eecs.umich.edu return lqEmpty() && sqEmpty(); 4934276Sgblack@eecs.umich.edu} 4945162Sgblack@eecs.umich.edu 4955162Sgblack@eecs.umich.edutemplate<class Impl> 4964592Sgblack@eecs.umich.edubool 4975162Sgblack@eecs.umich.eduLSQ<Impl>::lqEmpty() const 4986060Sgblack@eecs.umich.edu{ 4996060Sgblack@eecs.umich.edu list<ThreadID>::const_iterator threads = activeThreads->begin(); 5006060Sgblack@eecs.umich.edu list<ThreadID>::const_iterator end = activeThreads->end(); 5016060Sgblack@eecs.umich.edu 5024592Sgblack@eecs.umich.edu while (threads != end) { 5035162Sgblack@eecs.umich.edu ThreadID tid = *threads++; 5045162Sgblack@eecs.umich.edu 5055162Sgblack@eecs.umich.edu if (!thread[tid].lqEmpty()) 5065162Sgblack@eecs.umich.edu return false; 5075162Sgblack@eecs.umich.edu } 5084276Sgblack@eecs.umich.edu 5094276Sgblack@eecs.umich.edu return true; 5104276Sgblack@eecs.umich.edu} 5114276Sgblack@eecs.umich.edu 5125162Sgblack@eecs.umich.edutemplate<class Impl> 5134276Sgblack@eecs.umich.edubool 5144276Sgblack@eecs.umich.eduLSQ<Impl>::sqEmpty() const 5154276Sgblack@eecs.umich.edu{ 5164276Sgblack@eecs.umich.edu list<ThreadID>::const_iterator threads = activeThreads->begin(); 5175173Sgblack@eecs.umich.edu list<ThreadID>::const_iterator end = activeThreads->end(); 5185162Sgblack@eecs.umich.edu 5195162Sgblack@eecs.umich.edu while (threads != end) { 5205162Sgblack@eecs.umich.edu ThreadID tid = *threads++; 5215162Sgblack@eecs.umich.edu 5225162Sgblack@eecs.umich.edu if (!thread[tid].sqEmpty()) 5235162Sgblack@eecs.umich.edu return false; 5245162Sgblack@eecs.umich.edu } 5255162Sgblack@eecs.umich.edu 5265162Sgblack@eecs.umich.edu return true; 5275162Sgblack@eecs.umich.edu} 5285162Sgblack@eecs.umich.edu 5296484Sgblack@eecs.umich.edutemplate<class Impl> 5305162Sgblack@eecs.umich.edubool 5315162Sgblack@eecs.umich.eduLSQ<Impl>::lqFull() 5325162Sgblack@eecs.umich.edu{ 5335162Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 5345162Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 5355162Sgblack@eecs.umich.edu 5365162Sgblack@eecs.umich.edu while (threads != end) { 5375162Sgblack@eecs.umich.edu ThreadID tid = *threads++; 5385162Sgblack@eecs.umich.edu 5395162Sgblack@eecs.umich.edu if (!thread[tid].lqFull()) 5405162Sgblack@eecs.umich.edu return false; 5414746Sgblack@eecs.umich.edu } 5424276Sgblack@eecs.umich.edu 5434276Sgblack@eecs.umich.edu return true; 5445162Sgblack@eecs.umich.edu} 5455162Sgblack@eecs.umich.edu 5465448Sgblack@eecs.umich.edutemplate<class Impl> 5475448Sgblack@eecs.umich.edubool 5485162Sgblack@eecs.umich.eduLSQ<Impl>::lqFull(ThreadID tid) 5495162Sgblack@eecs.umich.edu{ 5505162Sgblack@eecs.umich.edu //@todo: Change to Calculate All Entries for 5515162Sgblack@eecs.umich.edu //Dynamic Policy 5525162Sgblack@eecs.umich.edu if (lsqPolicy == Dynamic) 5535162Sgblack@eecs.umich.edu return lqFull(); 5545162Sgblack@eecs.umich.edu else 5555162Sgblack@eecs.umich.edu return thread[tid].lqFull(); 5565162Sgblack@eecs.umich.edu} 5575162Sgblack@eecs.umich.edu 5585162Sgblack@eecs.umich.edutemplate<class Impl> 5595162Sgblack@eecs.umich.edubool 5605162Sgblack@eecs.umich.eduLSQ<Impl>::sqFull() 5615162Sgblack@eecs.umich.edu{ 5625162Sgblack@eecs.umich.edu list<ThreadID>::iterator threads = activeThreads->begin(); 5636060Sgblack@eecs.umich.edu list<ThreadID>::iterator end = activeThreads->end(); 5646060Sgblack@eecs.umich.edu 5656060Sgblack@eecs.umich.edu while (threads != end) { 5666060Sgblack@eecs.umich.edu ThreadID tid = *threads++; 5676060Sgblack@eecs.umich.edu 5686060Sgblack@eecs.umich.edu if (!sqFull(tid)) 5696060Sgblack@eecs.umich.edu return false; 5705162Sgblack@eecs.umich.edu } 5715162Sgblack@eecs.umich.edu 5724724Sgblack@eecs.umich.edu return true; 5734276Sgblack@eecs.umich.edu} 5744276Sgblack@eecs.umich.edu 5754276Sgblack@eecs.umich.edutemplate<class Impl> 5764276Sgblack@eecs.umich.edubool 577LSQ<Impl>::sqFull(ThreadID tid) 578{ 579 //@todo: Change to Calculate All Entries for 580 //Dynamic Policy 581 if (lsqPolicy == Dynamic) 582 return sqFull(); 583 else 584 return thread[tid].sqFull(); 585} 586 587template<class Impl> 588bool 589LSQ<Impl>::isStalled() 590{ 591 list<ThreadID>::iterator threads = activeThreads->begin(); 592 list<ThreadID>::iterator end = activeThreads->end(); 593 594 while (threads != end) { 595 ThreadID tid = *threads++; 596 597 if (!thread[tid].isStalled()) 598 return false; 599 } 600 601 return true; 602} 603 604template<class Impl> 605bool 606LSQ<Impl>::isStalled(ThreadID tid) 607{ 608 if (lsqPolicy == Dynamic) 609 return isStalled(); 610 else 611 return thread[tid].isStalled(); 612} 613 614template<class Impl> 615bool 616LSQ<Impl>::hasStoresToWB() 617{ 618 list<ThreadID>::iterator threads = activeThreads->begin(); 619 list<ThreadID>::iterator end = activeThreads->end(); 620 621 while (threads != end) { 622 ThreadID tid = *threads++; 623 624 if (hasStoresToWB(tid)) 625 return true; 626 } 627 628 return false; 629} 630 631template<class Impl> 632bool 633LSQ<Impl>::willWB() 634{ 635 list<ThreadID>::iterator threads = activeThreads->begin(); 636 list<ThreadID>::iterator end = activeThreads->end(); 637 638 while (threads != end) { 639 ThreadID tid = *threads++; 640 641 if (willWB(tid)) 642 return true; 643 } 644 645 return false; 646} 647 648template<class Impl> 649void 650LSQ<Impl>::dumpInsts() const 651{ 652 list<ThreadID>::const_iterator threads = activeThreads->begin(); 653 list<ThreadID>::const_iterator end = activeThreads->end(); 654 655 while (threads != end) { 656 ThreadID tid = *threads++; 657 658 thread[tid].dumpInsts(); 659 } 660} 661