store_set.cc revision 2665
11689SN/A/* 21689SN/A * Copyright (c) 2004-2005 The Regents of The University of Michigan 31689SN/A * All rights reserved. 41689SN/A * 51689SN/A * Redistribution and use in source and binary forms, with or without 61689SN/A * modification, are permitted provided that the following conditions are 71689SN/A * met: redistributions of source code must retain the above copyright 81689SN/A * notice, this list of conditions and the following disclaimer; 91689SN/A * redistributions in binary form must reproduce the above copyright 101689SN/A * notice, this list of conditions and the following disclaimer in the 111689SN/A * documentation and/or other materials provided with the distribution; 121689SN/A * neither the name of the copyright holders nor the names of its 131689SN/A * contributors may be used to endorse or promote products derived from 141689SN/A * this software without specific prior written permission. 151689SN/A * 161689SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 171689SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 181689SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 191689SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 201689SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 211689SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 221689SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 231689SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 241689SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 251689SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 261689SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 272665Ssaidi@eecs.umich.edu * 282665Ssaidi@eecs.umich.edu * Authors: Kevin Lim 291689SN/A */ 301689SN/A 311689SN/A#include "base/trace.hh" 321717SN/A#include "cpu/o3/store_set.hh" 331061SN/A 341061SN/AStoreSet::StoreSet(int _SSIT_size, int _LFST_size) 351061SN/A : SSIT_size(_SSIT_size), LFST_size(_LFST_size) 361061SN/A{ 371061SN/A DPRINTF(StoreSet, "StoreSet: Creating store set object.\n"); 381062SN/A DPRINTF(StoreSet, "StoreSet: SSIT size: %i, LFST size: %i.\n", 391062SN/A SSIT_size, LFST_size); 401061SN/A 411061SN/A SSIT = new SSID[SSIT_size]; 421061SN/A 431061SN/A validSSIT.resize(SSIT_size); 441061SN/A 451061SN/A for (int i = 0; i < SSIT_size; ++i) 461061SN/A validSSIT[i] = false; 471061SN/A 481061SN/A LFST = new InstSeqNum[LFST_size]; 491061SN/A 501061SN/A validLFST.resize(LFST_size); 511061SN/A 521061SN/A SSCounters = new int[LFST_size]; 531061SN/A 541061SN/A for (int i = 0; i < LFST_size; ++i) 551061SN/A { 561061SN/A validLFST[i] = false; 571061SN/A SSCounters[i] = 0; 581061SN/A } 591061SN/A 601061SN/A index_mask = SSIT_size - 1; 611061SN/A 621061SN/A offset_bits = 2; 631061SN/A} 641061SN/A 651061SN/Avoid 661062SN/AStoreSet::violation(Addr store_PC, Addr load_PC) 671061SN/A{ 681061SN/A int load_index = calcIndex(load_PC); 691061SN/A int store_index = calcIndex(store_PC); 701061SN/A 711062SN/A assert(load_index < SSIT_size && store_index < SSIT_size); 721062SN/A 731061SN/A bool valid_load_SSID = validSSIT[load_index]; 741061SN/A bool valid_store_SSID = validSSIT[store_index]; 751061SN/A 761061SN/A if (!valid_load_SSID && !valid_store_SSID) { 771061SN/A // Calculate a new SSID here. 781061SN/A SSID new_set = calcSSID(load_PC); 791061SN/A 801061SN/A validSSIT[load_index] = true; 811061SN/A 821061SN/A SSIT[load_index] = new_set; 831061SN/A 841061SN/A validSSIT[store_index] = true; 851061SN/A 861061SN/A SSIT[store_index] = new_set; 871061SN/A 881062SN/A assert(new_set < LFST_size); 891062SN/A 901061SN/A SSCounters[new_set]++; 911062SN/A 921062SN/A 931062SN/A DPRINTF(StoreSet, "StoreSet: Neither load nor store had a valid " 941062SN/A "storeset, creating a new one: %i for load %#x, store %#x\n", 951062SN/A new_set, load_PC, store_PC); 961061SN/A } else if (valid_load_SSID && !valid_store_SSID) { 971061SN/A SSID load_SSID = SSIT[load_index]; 981061SN/A 991061SN/A validSSIT[store_index] = true; 1001061SN/A 1011061SN/A SSIT[store_index] = load_SSID; 1021061SN/A 1031062SN/A assert(load_SSID < LFST_size); 1041062SN/A 1051061SN/A SSCounters[load_SSID]++; 1061062SN/A 1071062SN/A DPRINTF(StoreSet, "StoreSet: Load had a valid store set. Adding " 1081062SN/A "store to that set: %i for load %#x, store %#x\n", 1091062SN/A load_SSID, load_PC, store_PC); 1101061SN/A } else if (!valid_load_SSID && valid_store_SSID) { 1111061SN/A SSID store_SSID = SSIT[store_index]; 1121061SN/A 1131061SN/A validSSIT[load_index] = true; 1141061SN/A 1151061SN/A SSIT[load_index] = store_SSID; 1161061SN/A 1171061SN/A // Because we are having a load point to an already existing set, 1181061SN/A // the size of the store set is not incremented. 1191062SN/A 1201062SN/A DPRINTF(StoreSet, "StoreSet: Store had a valid store set: %i for " 1211062SN/A "load %#x, store %#x\n", 1221062SN/A store_SSID, load_PC, store_PC); 1231061SN/A } else { 1241061SN/A SSID load_SSID = SSIT[load_index]; 1251061SN/A SSID store_SSID = SSIT[store_index]; 1261061SN/A 1271062SN/A assert(load_SSID < LFST_size && store_SSID < LFST_size); 1281062SN/A 1291061SN/A int load_SS_size = SSCounters[load_SSID]; 1301061SN/A int store_SS_size = SSCounters[store_SSID]; 1311061SN/A 1321061SN/A // If the load has the bigger store set, then assign the store 1331061SN/A // to the same store set as the load. Otherwise vice-versa. 1341061SN/A if (load_SS_size > store_SS_size) { 1351061SN/A SSIT[store_index] = load_SSID; 1361061SN/A 1371061SN/A SSCounters[load_SSID]++; 1381061SN/A SSCounters[store_SSID]--; 1391062SN/A 1401062SN/A DPRINTF(StoreSet, "StoreSet: Load had bigger store set: %i; " 1411062SN/A "for load %#x, store %#x\n", 1421062SN/A load_SSID, load_PC, store_PC); 1431061SN/A } else { 1441061SN/A SSIT[load_index] = store_SSID; 1451061SN/A 1461061SN/A SSCounters[store_SSID]++; 1471061SN/A SSCounters[load_SSID]--; 1481062SN/A 1491062SN/A DPRINTF(StoreSet, "StoreSet: Store had bigger store set: %i; " 1501062SN/A "for load %#x, store %#x\n", 1511062SN/A store_SSID, load_PC, store_PC); 1521061SN/A } 1531061SN/A } 1541061SN/A} 1551061SN/A 1561061SN/Avoid 1571061SN/AStoreSet::insertLoad(Addr load_PC, InstSeqNum load_seq_num) 1581061SN/A{ 1591061SN/A // Does nothing. 1601061SN/A return; 1611061SN/A} 1621061SN/A 1631061SN/Avoid 1641061SN/AStoreSet::insertStore(Addr store_PC, InstSeqNum store_seq_num) 1651061SN/A{ 1661061SN/A int index = calcIndex(store_PC); 1671061SN/A 1681061SN/A int store_SSID; 1691061SN/A 1701062SN/A assert(index < SSIT_size); 1711062SN/A 1721061SN/A if (!validSSIT[index]) { 1731061SN/A // Do nothing if there's no valid entry. 1741061SN/A return; 1751061SN/A } else { 1761061SN/A store_SSID = SSIT[index]; 1771061SN/A 1781061SN/A assert(store_SSID < LFST_size); 1791061SN/A 1801061SN/A // Update the last store that was fetched with the current one. 1811061SN/A LFST[store_SSID] = store_seq_num; 1821062SN/A 1831062SN/A validLFST[store_SSID] = 1; 1841062SN/A 1851062SN/A DPRINTF(StoreSet, "Store %#x updated the LFST, SSID: %i\n", 1861062SN/A store_PC, store_SSID); 1871061SN/A } 1881061SN/A} 1891061SN/A 1901061SN/AInstSeqNum 1911061SN/AStoreSet::checkInst(Addr PC) 1921061SN/A{ 1931061SN/A int index = calcIndex(PC); 1941061SN/A 1951061SN/A int inst_SSID; 1961061SN/A 1971062SN/A assert(index < SSIT_size); 1981062SN/A 1991061SN/A if (!validSSIT[index]) { 2001062SN/A DPRINTF(StoreSet, "Inst %#x with index %i had no SSID\n", 2011062SN/A PC, index); 2021062SN/A 2031061SN/A // Return 0 if there's no valid entry. 2041061SN/A return 0; 2051061SN/A } else { 2061061SN/A inst_SSID = SSIT[index]; 2071061SN/A 2081061SN/A assert(inst_SSID < LFST_size); 2091061SN/A 2101061SN/A if (!validLFST[inst_SSID]) { 2111062SN/A 2121062SN/A DPRINTF(StoreSet, "Inst %#x with index %i and SSID %i had no " 2131062SN/A "dependency\n", PC, index, inst_SSID); 2141062SN/A 2151061SN/A return 0; 2161061SN/A } else { 2171062SN/A DPRINTF(StoreSet, "Inst %#x with index %i and SSID %i had LFST " 2181062SN/A "inum of %i\n", PC, index, inst_SSID, LFST[inst_SSID]); 2191062SN/A 2201061SN/A return LFST[inst_SSID]; 2211061SN/A } 2221061SN/A } 2231061SN/A} 2241061SN/A 2251061SN/Avoid 2261061SN/AStoreSet::issued(Addr issued_PC, InstSeqNum issued_seq_num, bool is_store) 2271061SN/A{ 2281061SN/A // This only is updated upon a store being issued. 2291061SN/A if (!is_store) { 2301061SN/A return; 2311061SN/A } 2321061SN/A 2331061SN/A int index = calcIndex(issued_PC); 2341061SN/A 2351061SN/A int store_SSID; 2361061SN/A 2371062SN/A assert(index < SSIT_size); 2381062SN/A 2391061SN/A // Make sure the SSIT still has a valid entry for the issued store. 2401062SN/A if (!validSSIT[index]) { 2411062SN/A return; 2421062SN/A } 2431061SN/A 2441061SN/A store_SSID = SSIT[index]; 2451061SN/A 2461062SN/A assert(store_SSID < LFST_size); 2471062SN/A 2481061SN/A // If the last fetched store in the store set refers to the store that 2491061SN/A // was just issued, then invalidate the entry. 2501061SN/A if (validLFST[store_SSID] && LFST[store_SSID] == issued_seq_num) { 2511062SN/A DPRINTF(StoreSet, "StoreSet: store invalidated itself in LFST.\n"); 2521061SN/A validLFST[store_SSID] = false; 2531061SN/A } 2541061SN/A} 2551061SN/A 2561061SN/Avoid 2571061SN/AStoreSet::squash(InstSeqNum squashed_num) 2581061SN/A{ 2591061SN/A // Not really sure how to do this well. 2601062SN/A // Generally this is small enough that it should be okay; short circuit 2611062SN/A // evaluation should take care of invalid entries. 2621062SN/A 2631062SN/A DPRINTF(StoreSet, "StoreSet: Squashing until inum %i\n", 2641062SN/A squashed_num); 2651061SN/A 2661061SN/A for (int i = 0; i < LFST_size; ++i) { 2671062SN/A if (validLFST[i] && LFST[i] < squashed_num) { 2681061SN/A validLFST[i] = false; 2691061SN/A } 2701061SN/A } 2711061SN/A} 2721061SN/A 2731061SN/Avoid 2741061SN/AStoreSet::clear() 2751061SN/A{ 2761061SN/A for (int i = 0; i < SSIT_size; ++i) { 2771061SN/A validSSIT[i] = false; 2781061SN/A } 2791061SN/A 2801061SN/A for (int i = 0; i < LFST_size; ++i) { 2811061SN/A validLFST[i] = false; 2821061SN/A } 2831061SN/A} 2841061SN/A 285