110623Smitch.hayenga@arm.com/*
211439SRekai.GonzalezAlberquilla@arm.com * Copyright (c) 2014-2015 ARM Limited
310623Smitch.hayenga@arm.com * All rights reserved
410623Smitch.hayenga@arm.com *
510623Smitch.hayenga@arm.com * The license below extends only to copyright in the software and shall
610623Smitch.hayenga@arm.com * not be construed as granting a license to any other intellectual
710623Smitch.hayenga@arm.com * property including but not limited to intellectual property relating
810623Smitch.hayenga@arm.com * to a hardware implementation of the functionality of the software
910623Smitch.hayenga@arm.com * licensed hereunder.  You may use the software subject to the license
1010623Smitch.hayenga@arm.com * terms below provided that you ensure that this notice is replicated
1110623Smitch.hayenga@arm.com * unmodified and in its entirety in all distributions of the software,
1210623Smitch.hayenga@arm.com * modified or unmodified, in source code or in binary form.
1310623Smitch.hayenga@arm.com *
1410623Smitch.hayenga@arm.com * Redistribution and use in source and binary forms, with or without
1510623Smitch.hayenga@arm.com * modification, are permitted provided that the following conditions are
1610623Smitch.hayenga@arm.com * met: redistributions of source code must retain the above copyright
1710623Smitch.hayenga@arm.com * notice, this list of conditions and the following disclaimer;
1810623Smitch.hayenga@arm.com * redistributions in binary form must reproduce the above copyright
1910623Smitch.hayenga@arm.com * notice, this list of conditions and the following disclaimer in the
2010623Smitch.hayenga@arm.com * documentation and/or other materials provided with the distribution;
2110623Smitch.hayenga@arm.com * neither the name of the copyright holders nor the names of its
2210623Smitch.hayenga@arm.com * contributors may be used to endorse or promote products derived from
2310623Smitch.hayenga@arm.com * this software without specific prior written permission.
2410623Smitch.hayenga@arm.com *
2510623Smitch.hayenga@arm.com * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
2610623Smitch.hayenga@arm.com * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
2710623Smitch.hayenga@arm.com * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
2810623Smitch.hayenga@arm.com * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
2910623Smitch.hayenga@arm.com * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
3010623Smitch.hayenga@arm.com * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
3110623Smitch.hayenga@arm.com * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
3210623Smitch.hayenga@arm.com * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
3310623Smitch.hayenga@arm.com * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
3410623Smitch.hayenga@arm.com * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
3510623Smitch.hayenga@arm.com * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
3610623Smitch.hayenga@arm.com *
3710623Smitch.hayenga@arm.com * Authors: Mitch Hayenga
3810623Smitch.hayenga@arm.com */
3910623Smitch.hayenga@arm.com
4010623Smitch.hayenga@arm.com#ifndef __MEM_CACHE_PREFETCH_QUEUED_HH__
4110623Smitch.hayenga@arm.com#define __MEM_CACHE_PREFETCH_QUEUED_HH__
4210623Smitch.hayenga@arm.com
4312727Snikos.nikoleris@arm.com#include <cstdint>
4410623Smitch.hayenga@arm.com#include <list>
4512727Snikos.nikoleris@arm.com#include <utility>
4610623Smitch.hayenga@arm.com
4712727Snikos.nikoleris@arm.com#include "base/statistics.hh"
4812727Snikos.nikoleris@arm.com#include "base/types.hh"
4910623Smitch.hayenga@arm.com#include "mem/cache/prefetch/base.hh"
5012727Snikos.nikoleris@arm.com#include "mem/packet.hh"
5112727Snikos.nikoleris@arm.com
5212727Snikos.nikoleris@arm.comstruct QueuedPrefetcherParams;
5310623Smitch.hayenga@arm.com
5410623Smitch.hayenga@arm.comclass QueuedPrefetcher : public BasePrefetcher
5510623Smitch.hayenga@arm.com{
5610623Smitch.hayenga@arm.com  protected:
5714013Sjavier.bueno@metempsy.com    struct DeferredPacket : public BaseTLB::Translation {
5814013Sjavier.bueno@metempsy.com        /** Owner of the packet */
5914013Sjavier.bueno@metempsy.com        QueuedPrefetcher *owner;
6013551Sjavier.bueno@metempsy.com        /** Prefetch info corresponding to this packet */
6113551Sjavier.bueno@metempsy.com        PrefetchInfo pfInfo;
6213551Sjavier.bueno@metempsy.com        /** Time when this prefetch becomes ready */
6310623Smitch.hayenga@arm.com        Tick tick;
6413551Sjavier.bueno@metempsy.com        /** The memory packet generated by this prefetch */
6510623Smitch.hayenga@arm.com        PacketPtr pkt;
6613551Sjavier.bueno@metempsy.com        /** The priority of this prefetch */
6711439SRekai.GonzalezAlberquilla@arm.com        int32_t priority;
6814013Sjavier.bueno@metempsy.com        /** Request used when a translation is needed */
6914013Sjavier.bueno@metempsy.com        RequestPtr translationRequest;
7014013Sjavier.bueno@metempsy.com        ThreadContext *tc;
7114013Sjavier.bueno@metempsy.com        bool ongoingTranslation;
7213551Sjavier.bueno@metempsy.com
7313551Sjavier.bueno@metempsy.com        /**
7413551Sjavier.bueno@metempsy.com         * Constructor
7514013Sjavier.bueno@metempsy.com         * @param o QueuedPrefetcher in charge of this request
7613551Sjavier.bueno@metempsy.com         * @param pfi PrefechInfo object associated to this packet
7713551Sjavier.bueno@metempsy.com         * @param t Time when this prefetch becomes ready
7813551Sjavier.bueno@metempsy.com         * @param p PacketPtr with the memory request of the prefetch
7913551Sjavier.bueno@metempsy.com         * @param prio This prefetch priority
8013551Sjavier.bueno@metempsy.com         */
8114013Sjavier.bueno@metempsy.com        DeferredPacket(QueuedPrefetcher *o, PrefetchInfo const &pfi, Tick t,
8214013Sjavier.bueno@metempsy.com            int32_t prio) : owner(o), pfInfo(pfi), tick(t), pkt(nullptr),
8314013Sjavier.bueno@metempsy.com            priority(prio), translationRequest() {
8413551Sjavier.bueno@metempsy.com        }
8513551Sjavier.bueno@metempsy.com
8611439SRekai.GonzalezAlberquilla@arm.com        bool operator>(const DeferredPacket& that) const
8711439SRekai.GonzalezAlberquilla@arm.com        {
8811439SRekai.GonzalezAlberquilla@arm.com            return priority > that.priority;
8911439SRekai.GonzalezAlberquilla@arm.com        }
9011439SRekai.GonzalezAlberquilla@arm.com        bool operator<(const DeferredPacket& that) const
9111439SRekai.GonzalezAlberquilla@arm.com        {
9211439SRekai.GonzalezAlberquilla@arm.com            return priority < that.priority;
9311439SRekai.GonzalezAlberquilla@arm.com        }
9411439SRekai.GonzalezAlberquilla@arm.com        bool operator<=(const DeferredPacket& that) const
9511439SRekai.GonzalezAlberquilla@arm.com        {
9611439SRekai.GonzalezAlberquilla@arm.com            return !(*this > that);
9711439SRekai.GonzalezAlberquilla@arm.com        }
9814013Sjavier.bueno@metempsy.com
9914013Sjavier.bueno@metempsy.com        /**
10014013Sjavier.bueno@metempsy.com         * Create the associated memory packet
10114013Sjavier.bueno@metempsy.com         * @param paddr physical address of this packet
10214013Sjavier.bueno@metempsy.com         * @param blk_size block size used by the prefetcher
10314013Sjavier.bueno@metempsy.com         * @param mid Requester ID of the access that generated this prefetch
10414013Sjavier.bueno@metempsy.com         * @param tag_prefetch flag to indicate if the packet needs to be
10514013Sjavier.bueno@metempsy.com         *        tagged
10614013Sjavier.bueno@metempsy.com         * @param t time when the prefetch becomes ready
10714013Sjavier.bueno@metempsy.com         */
10814013Sjavier.bueno@metempsy.com        void createPkt(Addr paddr, unsigned blk_size, MasterID mid,
10914013Sjavier.bueno@metempsy.com                       bool tag_prefetch, Tick t);
11014013Sjavier.bueno@metempsy.com
11114013Sjavier.bueno@metempsy.com        /**
11214013Sjavier.bueno@metempsy.com         * Sets the translation request needed to obtain the physical address
11314013Sjavier.bueno@metempsy.com         * of this request.
11414013Sjavier.bueno@metempsy.com         * @param req The Request with the virtual address of this request
11514013Sjavier.bueno@metempsy.com         */
11614013Sjavier.bueno@metempsy.com        void setTranslationRequest(const RequestPtr &req)
11714013Sjavier.bueno@metempsy.com        {
11814013Sjavier.bueno@metempsy.com            translationRequest = req;
11914013Sjavier.bueno@metempsy.com        }
12014013Sjavier.bueno@metempsy.com
12114013Sjavier.bueno@metempsy.com        void markDelayed() override
12214013Sjavier.bueno@metempsy.com        {}
12314013Sjavier.bueno@metempsy.com
12414013Sjavier.bueno@metempsy.com        void finish(const Fault &fault, const RequestPtr &req,
12514013Sjavier.bueno@metempsy.com                            ThreadContext *tc, BaseTLB::Mode mode) override;
12614013Sjavier.bueno@metempsy.com
12714013Sjavier.bueno@metempsy.com        /**
12814013Sjavier.bueno@metempsy.com         * Issues the translation request to the provided TLB
12914013Sjavier.bueno@metempsy.com         * @param tlb the tlb that has to translate the address
13014013Sjavier.bueno@metempsy.com         */
13114013Sjavier.bueno@metempsy.com        void startTranslation(BaseTLB *tlb);
13210623Smitch.hayenga@arm.com    };
13310623Smitch.hayenga@arm.com
13410623Smitch.hayenga@arm.com    std::list<DeferredPacket> pfq;
13514013Sjavier.bueno@metempsy.com    std::list<DeferredPacket> pfqMissingTranslation;
13614013Sjavier.bueno@metempsy.com
13714013Sjavier.bueno@metempsy.com    using const_iterator = std::list<DeferredPacket>::const_iterator;
13814013Sjavier.bueno@metempsy.com    using iterator = std::list<DeferredPacket>::iterator;
13910623Smitch.hayenga@arm.com
14010623Smitch.hayenga@arm.com    // PARAMETERS
14110623Smitch.hayenga@arm.com
14210623Smitch.hayenga@arm.com    /** Maximum size of the prefetch queue */
14310623Smitch.hayenga@arm.com    const unsigned queueSize;
14410623Smitch.hayenga@arm.com
14514013Sjavier.bueno@metempsy.com    /**
14614013Sjavier.bueno@metempsy.com     * Maximum size of the queue holding prefetch requests with missing
14714013Sjavier.bueno@metempsy.com     * address translations
14814013Sjavier.bueno@metempsy.com     */
14914013Sjavier.bueno@metempsy.com    const unsigned missingTranslationQueueSize;
15014013Sjavier.bueno@metempsy.com
15110623Smitch.hayenga@arm.com    /** Cycles after generation when a prefetch can first be issued */
15210623Smitch.hayenga@arm.com    const Cycles latency;
15310623Smitch.hayenga@arm.com
15410623Smitch.hayenga@arm.com    /** Squash queued prefetch if demand access observed */
15510623Smitch.hayenga@arm.com    const bool queueSquash;
15610623Smitch.hayenga@arm.com
15710623Smitch.hayenga@arm.com    /** Filter prefetches if already queued */
15810623Smitch.hayenga@arm.com    const bool queueFilter;
15910623Smitch.hayenga@arm.com
16010623Smitch.hayenga@arm.com    /** Snoop the cache before generating prefetch (cheating basically) */
16110623Smitch.hayenga@arm.com    const bool cacheSnoop;
16210623Smitch.hayenga@arm.com
16310623Smitch.hayenga@arm.com    /** Tag prefetch with PC of generating access? */
16410623Smitch.hayenga@arm.com    const bool tagPrefetch;
16510623Smitch.hayenga@arm.com
16614015Sjavier.bueno@metempsy.com    /** Percentage of requests that can be throttled */
16714015Sjavier.bueno@metempsy.com    const unsigned int throttleControlPct;
16814015Sjavier.bueno@metempsy.com
16910623Smitch.hayenga@arm.com    // STATS
17010623Smitch.hayenga@arm.com    Stats::Scalar pfIdentified;
17110623Smitch.hayenga@arm.com    Stats::Scalar pfBufferHit;
17210623Smitch.hayenga@arm.com    Stats::Scalar pfInCache;
17310623Smitch.hayenga@arm.com    Stats::Scalar pfRemovedFull;
17410623Smitch.hayenga@arm.com    Stats::Scalar pfSpanPage;
17510623Smitch.hayenga@arm.com
17610623Smitch.hayenga@arm.com  public:
17713667Sjavier.bueno@metempsy.com    using AddrPriority = std::pair<Addr, int32_t>;
17813667Sjavier.bueno@metempsy.com
17910623Smitch.hayenga@arm.com    QueuedPrefetcher(const QueuedPrefetcherParams *p);
18010623Smitch.hayenga@arm.com    virtual ~QueuedPrefetcher();
18110623Smitch.hayenga@arm.com
18213551Sjavier.bueno@metempsy.com    void notify(const PacketPtr &pkt, const PrefetchInfo &pfi) override;
18313422Sodanrc@yahoo.com.br
18413551Sjavier.bueno@metempsy.com    void insert(const PacketPtr &pkt, PrefetchInfo &new_pfi, int32_t priority);
18510623Smitch.hayenga@arm.com
18613551Sjavier.bueno@metempsy.com    virtual void calculatePrefetch(const PrefetchInfo &pfi,
18711439SRekai.GonzalezAlberquilla@arm.com                                   std::vector<AddrPriority> &addresses) = 0;
18813422Sodanrc@yahoo.com.br    PacketPtr getPacket() override;
18910623Smitch.hayenga@arm.com
19013422Sodanrc@yahoo.com.br    Tick nextPrefetchReadyTime() const override
19110623Smitch.hayenga@arm.com    {
19210623Smitch.hayenga@arm.com        return pfq.empty() ? MaxTick : pfq.front().tick;
19310623Smitch.hayenga@arm.com    }
19410623Smitch.hayenga@arm.com
19513422Sodanrc@yahoo.com.br    void regStats() override;
19614013Sjavier.bueno@metempsy.com
19714013Sjavier.bueno@metempsy.com  private:
19814013Sjavier.bueno@metempsy.com
19914013Sjavier.bueno@metempsy.com    /**
20014013Sjavier.bueno@metempsy.com     * Adds a DeferredPacket to the specified queue
20114013Sjavier.bueno@metempsy.com     * @param queue selected queue to use
20214013Sjavier.bueno@metempsy.com     * @param dpp DeferredPacket to add
20314013Sjavier.bueno@metempsy.com     */
20414013Sjavier.bueno@metempsy.com    void addToQueue(std::list<DeferredPacket> &queue, DeferredPacket &dpp);
20514013Sjavier.bueno@metempsy.com
20614013Sjavier.bueno@metempsy.com    /**
20714013Sjavier.bueno@metempsy.com     * Starts the translations of the queued prefetches with a
20814013Sjavier.bueno@metempsy.com     * missing translation. It performs a maximum specified number of
20914013Sjavier.bueno@metempsy.com     * translations. Successful translations cause the prefetch request to be
21014013Sjavier.bueno@metempsy.com     * queued in the queue of ready requests.
21114013Sjavier.bueno@metempsy.com     * @param max maximum number of translations to perform
21214013Sjavier.bueno@metempsy.com     */
21314013Sjavier.bueno@metempsy.com    void processMissingTranslations(unsigned max);
21414013Sjavier.bueno@metempsy.com
21514013Sjavier.bueno@metempsy.com    /**
21614013Sjavier.bueno@metempsy.com     * Indicates that the translation of the address of the provided  deferred
21714013Sjavier.bueno@metempsy.com     * packet has been successfully completed, and it can be enqueued as a
21814013Sjavier.bueno@metempsy.com     * new prefetch request.
21914013Sjavier.bueno@metempsy.com     * @param dp the deferred packet that has completed the translation request
22014013Sjavier.bueno@metempsy.com     * @param failed whether the translation was successful
22114013Sjavier.bueno@metempsy.com     */
22214013Sjavier.bueno@metempsy.com    void translationComplete(DeferredPacket *dp, bool failed);
22314013Sjavier.bueno@metempsy.com
22414013Sjavier.bueno@metempsy.com    /**
22514013Sjavier.bueno@metempsy.com     * Checks whether the specified prefetch request is already in the
22614013Sjavier.bueno@metempsy.com     * specified queue. If the request is found, its priority is updated.
22714013Sjavier.bueno@metempsy.com     * @param queue selected queue to check
22814013Sjavier.bueno@metempsy.com     * @param pfi information of the prefetch request to be added
22914013Sjavier.bueno@metempsy.com     * @param priority priority of the prefetch request to be added
23014013Sjavier.bueno@metempsy.com     * @return True if the prefetch request was found in the queue
23114013Sjavier.bueno@metempsy.com     */
23214013Sjavier.bueno@metempsy.com    bool alreadyInQueue(std::list<DeferredPacket> &queue,
23314013Sjavier.bueno@metempsy.com                        const PrefetchInfo &pfi, int32_t priority);
23414013Sjavier.bueno@metempsy.com
23514015Sjavier.bueno@metempsy.com    /**
23614015Sjavier.bueno@metempsy.com     * Returns the maxmimum number of prefetch requests that are allowed
23714015Sjavier.bueno@metempsy.com     * to be created from the number of prefetch candidates provided.
23814015Sjavier.bueno@metempsy.com     * The behavior of this service is controlled with the throttleControlPct
23914015Sjavier.bueno@metempsy.com     * parameter.
24014015Sjavier.bueno@metempsy.com     * @param total number of prefetch candidates generated by the prefetcher
24114015Sjavier.bueno@metempsy.com     * @return the number of these request candidates are allowed to be created
24214015Sjavier.bueno@metempsy.com     */
24314015Sjavier.bueno@metempsy.com    size_t getMaxPermittedPrefetches(size_t total) const;
24414015Sjavier.bueno@metempsy.com
24514013Sjavier.bueno@metempsy.com    RequestPtr createPrefetchRequest(Addr addr, PrefetchInfo const &pfi,
24614013Sjavier.bueno@metempsy.com                                        PacketPtr pkt);
24710623Smitch.hayenga@arm.com};
24810623Smitch.hayenga@arm.com
24910623Smitch.hayenga@arm.com#endif //__MEM_CACHE_PREFETCH_QUEUED_HH__
25010623Smitch.hayenga@arm.com
251