Deleted Added
sdiff udiff text old ( 11133:81e46b63daff ) new ( 11135:9d09dab39689 )
full compact
1/*
2 * Copyright (c) 2013-2015 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

--- 20 unchanged lines hidden (view full) ---

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 * Authors: Stephan Diestelhorst <stephan.diestelhorst@arm.com>
38 */
39
40/**
41 * @file
42 * Definition of a snoop filter.
43 */
44
45#ifndef __MEM_SNOOP_FILTER_HH__

--- 45 unchanged lines hidden (view full) ---

91 SnoopFilter (const SnoopFilterParams *p) :
92 SimObject(p), reqLookupResult(cachedLocations.end()), retryItem{0, 0},
93 linesize(p->system->cacheLineSize()), lookupLatency(p->lookup_latency),
94 maxEntryCount(p->max_capacity / p->system->cacheLineSize())
95 {
96 }
97
98 /**
99 * Init a new snoop filter and tell it about all the
100 * slave ports of the enclosing bus.
101 *
102 * @param slave_ports Slave ports that the bus is attached to.
103 */
104 void setSlavePorts(const SnoopList& slave_ports) {
105 localSlavePortIds.resize(slave_ports.size(), InvalidPortID);
106
107 PortID id = 0;
108 for (const auto& p : slave_ports) {

--- 13 unchanged lines hidden (view full) ---

122 /**
123 * Lookup a request (from a slave port) in the snoop filter and
124 * return a list of other slave ports that need forwarding of the
125 * resulting snoops. Additionally, update the tracking structures
126 * with new request information. Note that the caller must also
127 * call finishRequest once it is known if the request needs to
128 * retry or not.
129 *
130 * @param cpkt Pointer to the request packet. Not changed.
131 * @param slave_port Slave port where the request came from.
132 * @return Pair of a vector of snoop target ports and lookup latency.
133 */
134 std::pair<SnoopList, Cycles> lookupRequest(const Packet* cpkt,
135 const SlavePort& slave_port);
136
137 /**
138 * For an un-successful request, revert the change to the snoop
139 * filter. Also take care of erasing any null entries. This method
140 * relies on the result from lookupRequest being stored in
141 * reqLookupResult.
142 *
143 * @param will_retry This request will retry on this bus / snoop filter
144 * @param cpkt Request packet, merely for sanity checking
145 */
146 void finishRequest(bool will_retry, const Packet* cpkt);
147
148 /**
149 * Handle an incoming snoop from below (the master port). These can upgrade the
150 * tracking logic and may also benefit from additional steering thanks to the
151 * snoop filter.
152 * @param cpkt Pointer to const Packet containing the snoop.
153 * @return Pair with a vector of SlavePorts that need snooping and a lookup
154 * latency.
155 */
156 std::pair<SnoopList, Cycles> lookupSnoop(const Packet* cpkt);
157
158 /**
159 * Let the snoop filter see any snoop responses that turn into request responses
160 * and indicate cache to cache transfers. These will update the corresponding
161 * state in the filter.
162 *
163 * @param cpkt Pointer to const Packet holding the snoop response.
164 * @param rsp_port SlavePort that sends the response.
165 * @param req_port SlavePort that made the original request and is the
166 * destination of the snoop response.
167 */
168 void updateSnoopResponse(const Packet *cpkt, const SlavePort& rsp_port,
169 const SlavePort& req_port);
170
171 /**
172 * Pass snoop responses that travel downward through the snoop filter and let
173 * them update the snoop filter state. No additional routing happens.
174 *
175 * @param cpkt Pointer to const Packet holding the snoop response.
176 * @param rsp_port SlavePort that sends the response.
177 * @param req_port MasterPort through which the response leaves this cluster.
178 */
179 void updateSnoopForward(const Packet *cpkt, const SlavePort& rsp_port,
180 const MasterPort& req_port);
181
182 /**
183 * Update the snoop filter with a response from below (outer / other cache,
184 * or memory) and update the tracking information in the snoop filter.
185 *
186 * @param cpkt Pointer to const Packet holding the snoop response.
187 * @param slave_port SlavePort that made the original request and is the target
188 * of this response.
189 */
190 void updateResponse(const Packet *cpkt, const SlavePort& slave_port);
191
192 /**
193 * Simple factory methods for standard return values for lookupRequest
194 */
195 std::pair<SnoopList, Cycles> snoopAll(Cycles latency) const
196 {
197 return std::make_pair(slavePorts, latency);
198 }
199 std::pair<SnoopList, Cycles> snoopSelected(const SnoopList& slave_ports,
200 Cycles latency) const
201 {
202 return std::make_pair(slave_ports, latency);
203 }
204 std::pair<SnoopList, Cycles> snoopDown(Cycles latency) const
205 {
206 SnoopList empty;
207 return std::make_pair(empty , latency);
208 }
209
210 virtual void regStats();
211
212 protected:
213 typedef uint64_t SnoopMask;
214 /**
215 * Per cache line item tracking a bitmask of SlavePorts who have an
216 * outstanding request to this line (requested) or already share a cache line
217 * with this address (holder).
218 */
219 struct SnoopItem {
220 SnoopMask requested;
221 SnoopMask holder;
222 };
223 /**
224 * HashMap of SnoopItems indexed by line address
225 */
226 typedef m5::hash_map<Addr, SnoopItem> SnoopFilterCache;
227
228 /**
229 * Convert a single port to a corresponding, one-hot bitmask
230 * @param port SlavePort that should be converted.
231 * @return One-hot bitmask corresponding to the port.
232 */
233 SnoopMask portToMask(const SlavePort& port) const;
234 /**
235 * Converts a bitmask of ports into the corresponing list of ports
236 * @param ports SnoopMask of the requested ports
237 * @return SnoopList containing all the requested SlavePorts
238 */
239 SnoopList maskToPortList(SnoopMask ports) const;
240
241 private:
242
243 /**
244 * Removes snoop filter items which have no requesters and no holders.
245 */
246 void eraseIfNullEntry(SnoopFilterCache::iterator& sf_it);
247 /** Simple hash set of cached addresses. */
248 SnoopFilterCache cachedLocations;
249 /**
250 * Iterator used to store the result from lookupRequest until we
251 * call finishRequest.
252 */
253 SnoopFilterCache::iterator reqLookupResult;
254 /**

--- 36 unchanged lines hidden (view full) ---

291SnoopFilter::maskToPortList(SnoopMask port_mask) const
292{
293 SnoopList res;
294 for (const auto& p : slavePorts)
295 if (port_mask & portToMask(*p))
296 res.push_back(p);
297 return res;
298}
299#endif // __MEM_SNOOP_FILTER_HH__