gem5  v21.2.1.1
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
snoop_filter.cc
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2013-2017,2019 ARM Limited
3  * All rights reserved
4  *
5  * The license below extends only to copyright in the software and shall
6  * not be construed as granting a license to any other intellectual
7  * property including but not limited to intellectual property relating
8  * to a hardware implementation of the functionality of the software
9  * licensed hereunder. You may use the software subject to the license
10  * terms below provided that you ensure that this notice is replicated
11  * unmodified and in its entirety in all distributions of the software,
12  * modified or unmodified, in source code or in binary form.
13  *
14  * Redistribution and use in source and binary forms, with or without
15  * modification, are permitted provided that the following conditions are
16  * met: redistributions of source code must retain the above copyright
17  * notice, this list of conditions and the following disclaimer;
18  * redistributions in binary form must reproduce the above copyright
19  * notice, this list of conditions and the following disclaimer in the
20  * documentation and/or other materials provided with the distribution;
21  * neither the name of the copyright holders nor the names of its
22  * contributors may be used to endorse or promote products derived from
23  * this software without specific prior written permission.
24  *
25  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
26  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
27  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
28  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
29  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
30  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
31  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
32  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
33  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
34  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
35  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
36  */
37 
43 #include "mem/snoop_filter.hh"
44 
45 #include "base/logging.hh"
46 #include "base/trace.hh"
47 #include "debug/SnoopFilter.hh"
48 #include "sim/system.hh"
49 
50 namespace gem5
51 {
52 
54 
55 void
56 SnoopFilter::eraseIfNullEntry(SnoopFilterCache::iterator& sf_it)
57 {
58  SnoopItem& sf_item = sf_it->second;
59  if ((sf_item.requested | sf_item.holder).none()) {
60  cachedLocations.erase(sf_it);
61  DPRINTF(SnoopFilter, "%s: Removed SF entry.\n",
62  __func__);
63  }
64 }
65 
68  cpu_side_port)
69 {
70  DPRINTF(SnoopFilter, "%s: src %s packet %s\n", __func__,
71  cpu_side_port.name(), cpkt->print());
72 
73  // check if the packet came from a cache
74  bool allocate = !cpkt->req->isUncacheable() && cpu_side_port.isSnooping()
75  && cpkt->fromCache();
76  Addr line_addr = cpkt->getBlockAddr(linesize);
77  if (cpkt->isSecure()) {
78  line_addr |= LineSecure;
79  }
80  SnoopMask req_port = portToMask(cpu_side_port);
81  reqLookupResult.it = cachedLocations.find(line_addr);
82  bool is_hit = (reqLookupResult.it != cachedLocations.end());
83 
84  // If the snoop filter has no entry, and we should not allocate,
85  // do not create a new snoop filter entry, simply return a NULL
86  // portlist.
87  if (!is_hit && !allocate)
88  return snoopDown(lookupLatency);
89 
90  // If no hit in snoop filter create a new element and update iterator
91  if (!is_hit) {
93  cachedLocations.emplace(line_addr, SnoopItem()).first;
94  }
95  SnoopItem& sf_item = reqLookupResult.it->second;
96  SnoopMask interested = sf_item.holder | sf_item.requested;
97 
98  // Store unmodified value of snoop filter item in temp storage in
99  // case we need to revert because of a send retry in
100  // updateRequest.
101  reqLookupResult.retryItem = sf_item;
102 
103  stats.totRequests++;
104  if (is_hit) {
105  if (interested.count() == 1)
107  else
109  }
110 
111  DPRINTF(SnoopFilter, "%s: SF value %x.%x\n",
112  __func__, sf_item.requested, sf_item.holder);
113 
114  // If we are not allocating, we are done
115  if (!allocate)
116  return snoopSelected(maskToPortList(interested & ~req_port),
117  lookupLatency);
118 
119  if (cpkt->needsResponse()) {
120  if (!cpkt->cacheResponding()) {
121  // Max one request per address per port
122  panic_if((sf_item.requested & req_port).any(),
123  "double request :( SF value %x.%x\n",
124  sf_item.requested, sf_item.holder);
125 
126  // Mark in-flight requests to distinguish later on
127  sf_item.requested |= req_port;
128  DPRINTF(SnoopFilter, "%s: new SF value %x.%x\n",
129  __func__, sf_item.requested, sf_item.holder);
130  } else {
131  // NOTE: The memInhibit might have been asserted by a cache closer
132  // to the CPU, already -> the response will not be seen by this
133  // filter -> we do not need to keep the in-flight request, but make
134  // sure that we know that that cluster has a copy
135  panic_if((sf_item.holder & req_port).none(),
136  "Need to hold the value!");
138  "%s: not marking request. SF value %x.%x\n",
139  __func__, sf_item.requested, sf_item.holder);
140  }
141  } else { // if (!cpkt->needsResponse())
142  assert(cpkt->isEviction());
143  // make sure that the sender actually had the line
144  panic_if((sf_item.holder & req_port).none(), "requestor %x is not a " \
145  "holder :( SF value %x.%x\n", req_port,
146  sf_item.requested, sf_item.holder);
147  // CleanEvicts and Writebacks -> the sender and all caches above
148  // it may not have the line anymore.
149  if (!cpkt->isBlockCached()) {
150  sf_item.holder &= ~req_port;
151  DPRINTF(SnoopFilter, "%s: new SF value %x.%x\n",
152  __func__, sf_item.requested, sf_item.holder);
153  }
154  }
155 
156  return snoopSelected(maskToPortList(interested & ~req_port), lookupLatency);
157 }
158 
159 void
160 SnoopFilter::finishRequest(bool will_retry, Addr addr, bool is_secure)
161 {
162  if (reqLookupResult.it != cachedLocations.end()) {
163  // since we rely on the caller, do a basic check to ensure
164  // that finishRequest is being called following lookupRequest
165  Addr line_addr = (addr & ~(Addr(linesize - 1)));
166  if (is_secure) {
167  line_addr |= LineSecure;
168  }
169  assert(reqLookupResult.it->first == line_addr);
170  if (will_retry) {
171  SnoopItem retry_item = reqLookupResult.retryItem;
172  // Undo any changes made in lookupRequest to the snoop filter
173  // entry if the request will come again. retryItem holds
174  // the previous value of the snoopfilter entry.
175  reqLookupResult.it->second = retry_item;
176 
177  DPRINTF(SnoopFilter, "%s: restored SF value %x.%x\n",
178  __func__, retry_item.requested, retry_item.holder);
179  }
180 
182  }
183 }
184 
187 {
188  DPRINTF(SnoopFilter, "%s: packet %s\n", __func__, cpkt->print());
189 
190  assert(cpkt->isRequest());
191 
192  Addr line_addr = cpkt->getBlockAddr(linesize);
193  if (cpkt->isSecure()) {
194  line_addr |= LineSecure;
195  }
196  auto sf_it = cachedLocations.find(line_addr);
197  bool is_hit = (sf_it != cachedLocations.end());
198 
199  panic_if(!is_hit && (cachedLocations.size() >= maxEntryCount),
200  "snoop filter exceeded capacity of %d cache blocks\n",
201  maxEntryCount);
202 
203  // If the snoop filter has no entry, simply return a NULL
204  // portlist, there is no point creating an entry only to remove it
205  // later
206  if (!is_hit)
207  return snoopDown(lookupLatency);
208 
209  SnoopItem& sf_item = sf_it->second;
210 
211  SnoopMask interested = (sf_item.holder | sf_item.requested);
212 
213  stats.totSnoops++;
214 
215  if (interested.count() == 1)
217  else
219 
220  // ReadEx and Writes require both invalidation and exlusivity, while reads
221  // require neither. Writebacks on the other hand require exclusivity but
222  // not the invalidation. Previously Writebacks did not generate upward
223  // snoops so this was never an issue. Now that Writebacks generate snoops
224  // we need a special case for Writebacks. Additionally cache maintenance
225  // operations can generate snoops as they clean and/or invalidate all
226  // caches down to the specified point of reference.
227  assert(cpkt->isWriteback() || cpkt->req->isUncacheable() ||
228  (cpkt->isInvalidate() == cpkt->needsWritable()) ||
229  cpkt->req->isCacheMaintenance());
230  if (cpkt->isInvalidate() && sf_item.requested.none()) {
231  // Early clear of the holder, if no other request is currently going on
232  // @todo: This should possibly be updated even though we do not filter
233  // upward snoops
234  DPRINTF(SnoopFilter, "%s: old SF value %x.%x\n",
235  __func__, sf_item.requested, sf_item.holder);
236  sf_item.holder = 0;
237  DPRINTF(SnoopFilter, "%s: new SF value %x.%x\n",
238  __func__, sf_item.requested, sf_item.holder);
239  eraseIfNullEntry(sf_it);
240  }
241 
242  return snoopSelected(maskToPortList(interested), lookupLatency);
243 }
244 
245 void
247  const ResponsePort& rsp_port,
248  const ResponsePort& req_port)
249 {
250  DPRINTF(SnoopFilter, "%s: rsp %s req %s packet %s\n",
251  __func__, rsp_port.name(), req_port.name(), cpkt->print());
252 
253  assert(cpkt->isResponse());
254  assert(cpkt->cacheResponding());
255 
256  // if this snoop response is due to an uncacheable request, or is
257  // being turned into a normal response, there is nothing more to
258  // do
259  if (cpkt->req->isUncacheable() || !req_port.isSnooping()) {
260  return;
261  }
262 
263  Addr line_addr = cpkt->getBlockAddr(linesize);
264  if (cpkt->isSecure()) {
265  line_addr |= LineSecure;
266  }
267  SnoopMask rsp_mask = portToMask(rsp_port);
268  SnoopMask req_mask = portToMask(req_port);
269  SnoopItem& sf_item = cachedLocations[line_addr];
270 
271  DPRINTF(SnoopFilter, "%s: old SF value %x.%x\n",
272  __func__, sf_item.requested, sf_item.holder);
273 
274  // The source should have the line
275  panic_if((sf_item.holder & rsp_mask).none(),
276  "SF value %x.%x does not have the line\n",
277  sf_item.requested, sf_item.holder);
278 
279  // The destination should have had a request in
280  panic_if((sf_item.requested & req_mask).none(), "SF value %x.%x missing "\
281  "the original request\n", sf_item.requested, sf_item.holder);
282 
283  // If the snoop response has no sharers the line is passed in
284  // Modified state, and we know that there are no other copies, or
285  // they will all be invalidated imminently
286  if (!cpkt->hasSharers()) {
288  "%s: dropping %x because non-shared snoop "
289  "response SF val: %x.%x\n", __func__, rsp_mask,
290  sf_item.requested, sf_item.holder);
291  sf_item.holder = 0;
292  }
293  assert(!cpkt->isWriteback());
294  // @todo Deal with invalidating responses
295  sf_item.holder |= req_mask;
296  sf_item.requested &= ~req_mask;
297  assert((sf_item.requested | sf_item.holder).any());
298  DPRINTF(SnoopFilter, "%s: new SF value %x.%x\n",
299  __func__, sf_item.requested, sf_item.holder);
300 }
301 
302 void
304  const ResponsePort& rsp_port, const RequestPort& req_port)
305 {
306  DPRINTF(SnoopFilter, "%s: rsp %s req %s packet %s\n",
307  __func__, rsp_port.name(), req_port.name(), cpkt->print());
308 
309  assert(cpkt->isResponse());
310  assert(cpkt->cacheResponding());
311 
312  Addr line_addr = cpkt->getBlockAddr(linesize);
313  if (cpkt->isSecure()) {
314  line_addr |= LineSecure;
315  }
316  auto sf_it = cachedLocations.find(line_addr);
317  bool is_hit = sf_it != cachedLocations.end();
318 
319  // Nothing to do if it is not a hit
320  if (!is_hit)
321  return;
322 
323  // If the snoop response has no sharers the line is passed in
324  // Modified state, and we know that there are no other copies, or
325  // they will all be invalidated imminently
326  if (!cpkt->hasSharers()) {
327  SnoopItem& sf_item = sf_it->second;
328 
329  DPRINTF(SnoopFilter, "%s: old SF value %x.%x\n",
330  __func__, sf_item.requested, sf_item.holder);
331  sf_item.holder = 0;
332  DPRINTF(SnoopFilter, "%s: new SF value %x.%x\n",
333  __func__, sf_item.requested, sf_item.holder);
334 
335  eraseIfNullEntry(sf_it);
336  }
337 }
338 
339 void
341  cpu_side_port)
342 {
343  DPRINTF(SnoopFilter, "%s: src %s packet %s\n",
344  __func__, cpu_side_port.name(), cpkt->print());
345 
346  assert(cpkt->isResponse());
347 
348  // we only allocate if the packet actually came from a cache, but
349  // start by checking if the port is snooping
350  if (cpkt->req->isUncacheable() || !cpu_side_port.isSnooping())
351  return;
352 
353  // next check if we actually allocated an entry
354  Addr line_addr = cpkt->getBlockAddr(linesize);
355  if (cpkt->isSecure()) {
356  line_addr |= LineSecure;
357  }
358  auto sf_it = cachedLocations.find(line_addr);
359  if (sf_it == cachedLocations.end())
360  return;
361 
362  SnoopMask response_mask = portToMask(cpu_side_port);
363  SnoopItem& sf_item = sf_it->second;
364 
365  DPRINTF(SnoopFilter, "%s: old SF value %x.%x\n",
366  __func__, sf_item.requested, sf_item.holder);
367 
368  // Make sure we have seen the actual request, too
369  panic_if((sf_item.requested & response_mask).none(),
370  "SF value %x.%x missing request bit\n",
371  sf_item.requested, sf_item.holder);
372 
373  sf_item.requested &= ~response_mask;
374  // Update the residency of the cache line.
375 
376  if (cpkt->req->isCacheMaintenance()) {
377  // A cache clean response does not carry any data so it
378  // shouldn't change the holders, unless it is invalidating.
379  if (cpkt->isInvalidate()) {
380  sf_item.holder &= ~response_mask;
381  }
382  eraseIfNullEntry(sf_it);
383  } else {
384  // Any other response implies that a cache above will have the
385  // block.
386  sf_item.holder |= response_mask;
387  assert((sf_item.holder | sf_item.requested).any());
388  }
389  DPRINTF(SnoopFilter, "%s: new SF value %x.%x\n",
390  __func__, sf_item.requested, sf_item.holder);
391 }
392 
394  : statistics::Group(parent),
395  ADD_STAT(totRequests, statistics::units::Count::get(),
396  "Total number of requests made to the snoop filter."),
397  ADD_STAT(hitSingleRequests, statistics::units::Count::get(),
398  "Number of requests hitting in the snoop filter with a single "
399  "holder of the requested data."),
400  ADD_STAT(hitMultiRequests, statistics::units::Count::get(),
401  "Number of requests hitting in the snoop filter with multiple "
402  "(>1) holders of the requested data."),
403  ADD_STAT(totSnoops, statistics::units::Count::get(),
404  "Total number of snoops made to the snoop filter."),
405  ADD_STAT(hitSingleSnoops, statistics::units::Count::get(),
406  "Number of snoops hitting in the snoop filter with a single "
407  "holder of the requested data."),
408  ADD_STAT(hitMultiSnoops, statistics::units::Count::get(),
409  "Number of snoops hitting in the snoop filter with multiple "
410  "(>1) holders of the requested data.")
411 {}
412 
413 void
415 {
417 }
418 
419 } // namespace gem5
gem5::Packet::getBlockAddr
Addr getBlockAddr(unsigned int blk_size) const
Definition: packet.hh:805
gem5::SnoopFilter::linesize
const unsigned linesize
Cache line size.
Definition: snoop_filter.hh:305
gem5::Packet::isRequest
bool isRequest() const
Definition: packet.hh:586
gem5::SnoopFilter::reqLookupResult
struct gem5::SnoopFilter::ReqLookupResult reqLookupResult
gem5::Port::name
const std::string name() const
Return port name (for DPRINTF).
Definition: port.hh:111
system.hh
gem5::SnoopFilter::SnoopFilterStats::SnoopFilterStats
SnoopFilterStats(statistics::Group *parent)
Definition: snoop_filter.cc:393
gem5::SnoopFilter::finishRequest
void finishRequest(bool will_retry, Addr addr, bool is_secure)
For an un-successful request, revert the change to the snoop filter.
Definition: snoop_filter.cc:160
gem5::SnoopFilter::updateSnoopResponse
void updateSnoopResponse(const Packet *cpkt, const ResponsePort &rsp_port, const ResponsePort &req_port)
Let the snoop filter see any snoop responses that turn into request responses and indicate cache to c...
Definition: snoop_filter.cc:246
gem5::SnoopFilter
This snoop filter keeps track of which connected port has a particular line of data.
Definition: snoop_filter.hh:89
gem5::Packet::req
RequestPtr req
A pointer to the original request.
Definition: packet.hh:366
gem5::SnoopFilter::maskToPortList
SnoopList maskToPortList(SnoopMask ports) const
Converts a bitmask of ports into the corresponing list of ports.
Definition: snoop_filter.hh:345
gem5::Packet::isWriteback
bool isWriteback() const
Definition: packet.hh:602
gem5::Packet::cacheResponding
bool cacheResponding() const
Definition: packet.hh:646
gem5::SnoopFilter::lookupSnoop
std::pair< SnoopList, Cycles > lookupSnoop(const Packet *cpkt)
Handle an incoming snoop from below (the memory-side port).
Definition: snoop_filter.cc:186
gem5::SnoopFilter::lookupLatency
const Cycles lookupLatency
Latency for doing a lookup in the filter.
Definition: snoop_filter.hh:307
gem5::Packet::isSecure
bool isSecure() const
Definition: packet.hh:810
gem5::Packet::hasSharers
bool hasSharers() const
Definition: packet.hh:673
gem5::SnoopFilter::regStats
virtual void regStats()
Callback to set stat parameters.
Definition: snoop_filter.cc:414
gem5::SnoopFilter::ReqLookupResult::it
SnoopFilterCache::iterator it
Iterator used to store the result from lookupRequest.
Definition: snoop_filter.hh:278
gem5::SnoopFilter::updateResponse
void updateResponse(const Packet *cpkt, const ResponsePort &cpu_side_port)
Update the snoop filter with a response from below (outer / other cache, or memory) and update the tr...
Definition: snoop_filter.cc:340
gem5::SnoopFilter::eraseIfNullEntry
void eraseIfNullEntry(SnoopFilterCache::iterator &sf_it)
Removes snoop filter items which have no requestors and no holders.
Definition: snoop_filter.cc:56
gem5::SnoopFilter::lookupRequest
std::pair< SnoopList, Cycles > lookupRequest(const Packet *cpkt, const ResponsePort &cpu_side_port)
Lookup a request (from a CPU-side port) in the snoop filter and return a list of other CPU-side ports...
Definition: snoop_filter.cc:67
gem5::RequestPort
A RequestPort is a specialisation of a Port, which implements the default protocol for the three diff...
Definition: port.hh:77
gem5::SnoopFilter::SnoopFilterStats::totSnoops
statistics::Scalar totSnoops
Definition: snoop_filter.hh:329
gem5::SnoopFilter::SnoopItem::requested
SnoopMask requested
Definition: snoop_filter.hh:220
gem5::SnoopFilter::updateSnoopForward
void updateSnoopForward(const Packet *cpkt, const ResponsePort &rsp_port, const RequestPort &req_port)
Pass snoop responses that travel downward through the snoop filter and let them update the snoop filt...
Definition: snoop_filter.cc:303
gem5::Packet::needsWritable
bool needsWritable() const
Definition: packet.hh:588
gem5::SnoopFilter::SNOOP_MASK_SIZE
static const int SNOOP_MASK_SIZE
Definition: snoop_filter.hh:94
gem5::Packet::print
void print(std::ostream &o, int verbosity=0, const std::string &prefix="") const
Definition: packet.cc:373
DPRINTF
#define DPRINTF(x,...)
Definition: trace.hh:186
ADD_STAT
#define ADD_STAT(n,...)
Convenience macro to add a stat to a statistics group.
Definition: group.hh:75
gem5::Packet
A Packet is used to encapsulate a transfer between two objects in the memory system (e....
Definition: packet.hh:283
gem5::ResponsePort::isSnooping
bool isSnooping() const
Find out if the peer request port is snooping or not.
Definition: port.hh:291
gem5::SnoopFilter::SnoopItem::holder
SnoopMask holder
Definition: snoop_filter.hh:221
gem5::SnoopFilter::snoopDown
std::pair< SnoopList, Cycles > snoopDown(Cycles latency) const
Definition: snoop_filter.hh:240
gem5::SnoopFilter::LineSecure
@ LineSecure
block holds data from the secure memory space
Definition: snoop_filter.hh:317
gem5::SnoopFilter::cachedLocations
SnoopFilterCache cachedLocations
Simple hash set of cached addresses.
Definition: snoop_filter.hh:267
gem5::SnoopFilter::maxEntryCount
const unsigned maxEntryCount
Max capacity in terms of cache blocks tracked, for sanity checking.
Definition: snoop_filter.hh:309
std::pair
STL pair class.
Definition: stl.hh:58
gem5::Packet::needsResponse
bool needsResponse() const
Definition: packet.hh:597
gem5::Addr
uint64_t Addr
Address type This will probably be moved somewhere else in the near future.
Definition: types.hh:147
gem5::statistics::Group::regStats
virtual void regStats()
Callback to set stat parameters.
Definition: group.cc:69
gem5::SnoopFilter::SnoopFilterStats::hitSingleRequests
statistics::Scalar hitSingleRequests
Definition: snoop_filter.hh:326
gem5::SnoopFilter::SnoopItem
Per cache line item tracking a bitmask of ResponsePorts who have an outstanding request to this line ...
Definition: snoop_filter.hh:218
gem5::ResponsePort
A ResponsePort is a specialization of a port.
Definition: port.hh:268
panic_if
#define panic_if(cond,...)
Conditional panic macro that checks the supplied condition and only panics if the condition is true a...
Definition: logging.hh:204
gem5::SnoopFilter::snoopSelected
std::pair< SnoopList, Cycles > snoopSelected(const SnoopList &_cpu_side_ports, Cycles latency) const
Definition: snoop_filter.hh:235
gem5::SnoopFilter::SnoopMask
std::bitset< SNOOP_MASK_SIZE > SnoopMask
The underlying type for the bitmask we use for tracking.
Definition: snoop_filter.hh:211
logging.hh
gem5::statistics::Group
Statistics container.
Definition: group.hh:93
gem5::SnoopFilter::portToMask
SnoopMask portToMask(const ResponsePort &port) const
Convert a single port to a corresponding, one-hot bitmask.
Definition: snoop_filter.hh:336
gem5::Packet::fromCache
bool fromCache() const
Definition: packet.hh:601
trace.hh
gem5::SnoopFilter::stats
gem5::SnoopFilter::SnoopFilterStats stats
snoop_filter.hh
gem5::SnoopFilter::ReqLookupResult::retryItem
SnoopItem retryItem
Variable to temporarily store value of snoopfilter entry in case finishRequest needs to undo changes ...
Definition: snoop_filter.hh:285
gem5
Reference material can be found at the JEDEC website: UFS standard http://www.jedec....
Definition: tlb.cc:60
gem5::SnoopFilter::SnoopFilterStats::totRequests
statistics::Scalar totRequests
Definition: snoop_filter.hh:325
gem5::SnoopFilter::SnoopFilterStats::hitMultiRequests
statistics::Scalar hitMultiRequests
Definition: snoop_filter.hh:327
gem5::Packet::isBlockCached
bool isBlockCached() const
Definition: packet.hh:747
gem5::Packet::isResponse
bool isResponse() const
Definition: packet.hh:587
gem5::SnoopFilter::SnoopFilterStats::hitMultiSnoops
statistics::Scalar hitMultiSnoops
Definition: snoop_filter.hh:331
gem5::Packet::isEviction
bool isEviction() const
Definition: packet.hh:599
gem5::Packet::isInvalidate
bool isInvalidate() const
Definition: packet.hh:598
gem5::X86ISA::addr
Bitfield< 3 > addr
Definition: types.hh:84
gem5::SnoopFilter::SnoopFilterStats::hitSingleSnoops
statistics::Scalar hitSingleSnoops
Definition: snoop_filter.hh:330

Generated on Wed May 4 2022 12:14:02 for gem5 by doxygen 1.8.17