indirect_memory.hh revision 13772:31b71dadc472
1/** 2 * Copyright (c) 2018 Metempsy Technology Consulting 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are 7 * met: redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer; 9 * redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution; 12 * neither the name of the copyright holders nor the names of its 13 * contributors may be used to endorse or promote products derived from 14 * this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 * 28 * Authors: Javier Bueno 29 */ 30 31/** 32 * Implementation of the Indirect Memory Prefetcher 33 * 34 * References: 35 * IMP: Indirect memory prefetcher. 36 * Yu, X., Hughes, C. J., Satish, N., & Devadas, S. (2015, December). 37 * In Proceedings of the 48th International Symposium on Microarchitecture 38 * (pp. 178-190). ACM. 39 */ 40 41#ifndef __MEM_CACHE_PREFETCH_INDIRECT_MEMORY_HH__ 42#define __MEM_CACHE_PREFETCH_INDIRECT_MEMORY_HH__ 43 44#include <vector> 45 46#include "mem/cache/prefetch/associative_set.hh" 47#include "mem/cache/prefetch/queued.hh" 48 49struct IndirectMemoryPrefetcherParams; 50 51class IndirectMemoryPrefetcher : public QueuedPrefetcher 52{ 53 /** Maximum number of prefetches generated per event */ 54 const unsigned int maxPrefetchDistance; 55 /** Shift values considered */ 56 const std::vector<int> shiftValues; 57 /** Counter threshold to start prefetching */ 58 const unsigned int prefetchThreshold; 59 /** Maximum value of the confidence indirectCounter */ 60 const unsigned int maxIndirectCounterValue; 61 /** streamCounter value to trigger the streaming prefetcher */ 62 const int streamCounterThreshold; 63 /** Number of prefetches generated when using the streaming prefetcher */ 64 const int streamingDistance; 65 66 /** Prefetch Table Entry */ 67 struct PrefetchTableEntry : public TaggedEntry 68 { 69 /* Stream table fields */ 70 71 /** Accessed address */ 72 Addr address; 73 /** Whether this address is in the secure region */ 74 bool secure; 75 /** Confidence counter of the stream */ 76 unsigned int streamCounter; 77 78 /* Indirect table fields */ 79 80 /** Enable bit of the indirect fields */ 81 bool enabled; 82 /** Current index value */ 83 int64_t index; 84 /** BaseAddr detected */ 85 Addr baseAddr; 86 /** Shift detected */ 87 int shift; 88 /** Confidence counter of the indirect fields */ 89 int indirectCounter; 90 /** 91 * This variable is set to indicate that there has been at least one 92 * match with the current index value. This information is later used 93 * when a new index is updated. If there were no increases in the 94 * indirectCounter, the counter is decremented. 95 */ 96 bool increasedIndirectCounter; 97 98 PrefetchTableEntry() : TaggedEntry(), address(0), secure(false), 99 streamCounter(0), enabled(false), index(0), baseAddr(0), shift(0), 100 indirectCounter(0), increasedIndirectCounter(false) 101 {} 102 103 void reset() override { 104 address = 0; 105 secure = false; 106 streamCounter = 0; 107 enabled = false; 108 index = 0; 109 baseAddr = 0; 110 shift = 0; 111 indirectCounter = 0; 112 increasedIndirectCounter = false; 113 } 114 }; 115 /** Prefetch table */ 116 AssociativeSet<PrefetchTableEntry> prefetchTable; 117 118 /** Indirect Pattern Detector entrt */ 119 struct IndirectPatternDetectorEntry : public TaggedEntry 120 { 121 /** First index */ 122 int64_t idx1; 123 /** Second index */ 124 int64_t idx2; 125 /** Valid bit for the second index */ 126 bool secondIndexSet; 127 /** Number of misses currently recorded */ 128 int numMisses; 129 /** 130 * Potential BaseAddr candidates for each recorded miss. 131 * The number of candidates per miss is determined by the number of 132 * elements in the shiftValues array. 133 */ 134 std::vector<std::vector<Addr>> baseAddr; 135 136 IndirectPatternDetectorEntry(unsigned int num_addresses, 137 unsigned int num_shifts) 138 : idx1(0), idx2(0), secondIndexSet(false), numMisses(0), 139 baseAddr(num_addresses, std::vector<Addr>(num_shifts)) 140 {} 141 142 void reset() override { 143 idx1 = 0; 144 idx2 = 0; 145 secondIndexSet = false; 146 numMisses = 0; 147 setInvalid(); 148 } 149 }; 150 /** Indirect Pattern Detector (IPD) table */ 151 AssociativeSet<IndirectPatternDetectorEntry> ipd; 152 153 /** Entry currently tracking misses */ 154 IndirectPatternDetectorEntry *ipdEntryTrackingMisses; 155 156 /** Byte order used to access the cache */ 157 const ByteOrder byteOrder; 158 159 /** 160 * Allocate or update an entry in the IPD 161 * @param pt_entry Pointer to the associated page table entry 162 * @param index Detected first index value 163 */ 164 void allocateOrUpdateIPDEntry(const PrefetchTableEntry *pt_entry, 165 int64_t index); 166 /** 167 * Update an IPD entry with a detected miss address, when the first index 168 * is being tracked 169 * @param miss_addr The address that caused the miss 170 */ 171 void trackMissIndex1(Addr miss_addr); 172 173 /** 174 * Update an IPD entry with a detected miss address, when the second index 175 * is being tracked 176 * @param miss_addr The address that caused the miss 177 */ 178 void trackMissIndex2(Addr miss_addr); 179 180 /** 181 * Checks if an access to the cache matches any active PT entry, if so, 182 * the indirect confidence counter is incremented 183 * @param addr address of the access 184 */ 185 void checkAccessMatchOnActiveEntries(Addr addr); 186 187 public: 188 IndirectMemoryPrefetcher(const IndirectMemoryPrefetcherParams *p); 189 ~IndirectMemoryPrefetcher() {} 190 191 void calculatePrefetch(const PrefetchInfo &pfi, 192 std::vector<AddrPriority> &addresses) override; 193}; 194#endif//__MEM_CACHE_PREFETCH_INDIRECT_MEMORY_HH__ 195