physical.hh revision 6227
12914SN/A/*
210713Sandreas.hansson@arm.com * Copyright (c) 2001-2005 The Regents of The University of Michigan
38856SN/A * All rights reserved.
48856SN/A *
58856SN/A * Redistribution and use in source and binary forms, with or without
68856SN/A * modification, are permitted provided that the following conditions are
78856SN/A * met: redistributions of source code must retain the above copyright
88856SN/A * notice, this list of conditions and the following disclaimer;
98856SN/A * redistributions in binary form must reproduce the above copyright
108856SN/A * notice, this list of conditions and the following disclaimer in the
118856SN/A * documentation and/or other materials provided with the distribution;
128856SN/A * neither the name of the copyright holders nor the names of its
138856SN/A * contributors may be used to endorse or promote products derived from
142914SN/A * this software without specific prior written permission.
152914SN/A *
162914SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
172914SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
182914SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
192914SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
202914SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
212914SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
222914SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
232914SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
242914SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
252914SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
262914SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
272914SN/A *
282914SN/A * Authors: Ron Dreslinski
292914SN/A */
302914SN/A
312914SN/A/* @file
322914SN/A */
332914SN/A
342914SN/A#ifndef __PHYSICAL_MEMORY_HH__
352914SN/A#define __PHYSICAL_MEMORY_HH__
362914SN/A
372914SN/A#include <map>
382914SN/A#include <string>
392914SN/A
402914SN/A#include "base/range.hh"
418856SN/A#include "mem/mem_object.hh"
422914SN/A#include "mem/packet.hh"
432914SN/A#include "mem/tport.hh"
4411793Sbrandon.potter@amd.com#include "params/PhysicalMemory.hh"
4511793Sbrandon.potter@amd.com#include "sim/eventq.hh"
469356Snilay@cs.wisc.edu
479152Satgutier@umich.edu//
488914Sandreas.hansson@arm.com// Functional model for a contiguous block of physical memory. (i.e. RAM)
492914SN/A//
505740SN/Aclass PhysicalMemory : public MemObject
515740SN/A{
5211207SBrad.Beckmann@amd.com  protected:
5311207SBrad.Beckmann@amd.com
5411207SBrad.Beckmann@amd.com    class MemoryPort : public SimpleTimingPort
5511207SBrad.Beckmann@amd.com    {
565740SN/A        PhysicalMemory *memory;
575740SN/A
585740SN/A      public:
598914Sandreas.hansson@arm.com
605740SN/A        MemoryPort(const std::string &_name, PhysicalMemory *_memory);
615740SN/A
625740SN/A      protected:
638914Sandreas.hansson@arm.com
648914Sandreas.hansson@arm.com        virtual Tick recvAtomic(PacketPtr pkt);
658914Sandreas.hansson@arm.com
668914Sandreas.hansson@arm.com        virtual void recvFunctional(PacketPtr pkt);
678914Sandreas.hansson@arm.com
6810713Sandreas.hansson@arm.com        virtual void recvStatusChange(Status status);
698914Sandreas.hansson@arm.com
708914Sandreas.hansson@arm.com        virtual void getDeviceAddressRanges(AddrRangeList &resp,
718914Sandreas.hansson@arm.com                                            bool &snoop);
724929SN/A
7310713Sandreas.hansson@arm.com        virtual unsigned deviceBlockSize() const;
7410713Sandreas.hansson@arm.com    };
7510713Sandreas.hansson@arm.com
7610713Sandreas.hansson@arm.com    int numPorts;
7710713Sandreas.hansson@arm.com
7810713Sandreas.hansson@arm.com
7910713Sandreas.hansson@arm.com  private:
8010713Sandreas.hansson@arm.com    // prevent copying of a MainMemory object
8110713Sandreas.hansson@arm.com    PhysicalMemory(const PhysicalMemory &specmem);
8210713Sandreas.hansson@arm.com    const PhysicalMemory &operator=(const PhysicalMemory &specmem);
8310713Sandreas.hansson@arm.com
8410713Sandreas.hansson@arm.com  protected:
858914Sandreas.hansson@arm.com
863091SN/A    class LockedAddr {
878856SN/A      public:
888856SN/A        // on alpha, minimum LL/SC granularity is 16 bytes, so lower
8910322Sandreas.hansson@arm.com        // bits need to masked off.
908856SN/A        static const Addr Addr_Mask = 0xf;
913296SN/A
9210322Sandreas.hansson@arm.com        static Addr mask(Addr paddr) { return (paddr & ~Addr_Mask); }
938856SN/A
948856SN/A        Addr addr;      // locked address
958856SN/A        int contextId;     // locking hw context
968856SN/A
973284SN/A        // check for matching execution context
984929SN/A        bool matchesContext(Request *req)
998856SN/A        {
1008856SN/A            return (contextId == req->contextId());
1018856SN/A        }
1024490SN/A
1033342SN/A        LockedAddr(Request *req)
1044490SN/A            : addr(mask(req->getPaddr())),
10510722Sstephan.diestelhorst@arm.com              contextId(req->contextId())
1063403SN/A        {
10710722Sstephan.diestelhorst@arm.com        }
10810722Sstephan.diestelhorst@arm.com    };
10910722Sstephan.diestelhorst@arm.com
11010713Sandreas.hansson@arm.com    std::list<LockedAddr> lockedAddrList;
1119160Sandreas.hansson@arm.com
1129160Sandreas.hansson@arm.com    // helper function for checkLockedAddrs(): we really want to
1134492SN/A    // inline a quick check for an empty locked addr list (hopefully
1149163Sandreas.hansson@arm.com    // the common case), and do the full list search (if necessary) in
1159163Sandreas.hansson@arm.com    // this out-of-line function
1169163Sandreas.hansson@arm.com    bool checkLockedAddrList(PacketPtr pkt);
1179390Sandreas.hansson@arm.com
1189390Sandreas.hansson@arm.com    // Record the address of a load-locked operation so that we can
11911207SBrad.Beckmann@amd.com    // clear the execution context's lock flag if a matching store is
1209390Sandreas.hansson@arm.com    // performed
1219390Sandreas.hansson@arm.com    void trackLoadLocked(PacketPtr pkt);
1229390Sandreas.hansson@arm.com
1239390Sandreas.hansson@arm.com    // Compare a store address with any locked addresses so we can
12411195Sandreas.hansson@arm.com    // clear the lock flag appropriately.  Return value set to 'false'
12511195Sandreas.hansson@arm.com    // if store operation should be suppressed (because it was a
12610922Sandreas.hansson@arm.com    // conditional store and the address was no longer locked by the
1274666SN/A    // requesting execution context), 'true' otherwise.  Note that
1284666SN/A    // this method must be called on *all* stores since even
1294666SN/A    // non-conditional stores must clear any matching lock addresses.
1304666SN/A    bool writeOK(PacketPtr pkt) {
13110713Sandreas.hansson@arm.com        Request *req = pkt->req;
13210713Sandreas.hansson@arm.com        if (lockedAddrList.empty()) {
13310713Sandreas.hansson@arm.com            // no locked addrs: nothing to check, store_conditional fails
13410713Sandreas.hansson@arm.com            bool isLLSC = pkt->isLLSC();
13510713Sandreas.hansson@arm.com            if (isLLSC) {
13610713Sandreas.hansson@arm.com                req->setExtraData(0);
13710713Sandreas.hansson@arm.com            }
13810713Sandreas.hansson@arm.com            return !isLLSC; // only do write if not an sc
13911195Sandreas.hansson@arm.com        } else {
14011195Sandreas.hansson@arm.com            // iterate over list...
14111195Sandreas.hansson@arm.com            return checkLockedAddrList(pkt);
14211195Sandreas.hansson@arm.com        }
14311195Sandreas.hansson@arm.com    }
14411195Sandreas.hansson@arm.com
14511195Sandreas.hansson@arm.com    uint8_t *pmemAddr;
14611195Sandreas.hansson@arm.com    int pagePtr;
14711195Sandreas.hansson@arm.com    Tick lat;
1483450SN/A    Tick lat_var;
14911195Sandreas.hansson@arm.com    std::vector<MemoryPort*> ports;
15011195Sandreas.hansson@arm.com    typedef std::vector<MemoryPort*>::iterator PortIterator;
15111195Sandreas.hansson@arm.com
1528856SN/A    uint64_t cachedSize;
1538856SN/A    uint64_t cachedStart;
1548856SN/A  public:
15510713Sandreas.hansson@arm.com    Addr new_page();
1568856SN/A    uint64_t size() { return cachedSize; }
15710713Sandreas.hansson@arm.com    uint64_t start() { return cachedStart; }
15810713Sandreas.hansson@arm.com
15910713Sandreas.hansson@arm.com  public:
16010713Sandreas.hansson@arm.com    typedef PhysicalMemoryParams Params;
16110713Sandreas.hansson@arm.com    PhysicalMemory(const Params *p);
16210713Sandreas.hansson@arm.com    virtual ~PhysicalMemory();
1638914Sandreas.hansson@arm.com
16410713Sandreas.hansson@arm.com    const Params *
16510713Sandreas.hansson@arm.com    params() const
16610713Sandreas.hansson@arm.com    {
16710713Sandreas.hansson@arm.com        return dynamic_cast<const Params *>(_params);
16810713Sandreas.hansson@arm.com    }
16910713Sandreas.hansson@arm.com
17010423Sandreas.hansson@arm.com  public:
17110713Sandreas.hansson@arm.com    unsigned deviceBlockSize() const;
17210713Sandreas.hansson@arm.com    void getAddressRanges(AddrRangeList &resp, bool &snoop);
17310423Sandreas.hansson@arm.com    virtual Port *getPort(const std::string &if_name, int idx = -1);
17410423Sandreas.hansson@arm.com    void virtual init();
17510713Sandreas.hansson@arm.com    unsigned int drain(Event *de);
17610423Sandreas.hansson@arm.com
1778856SN/A  protected:
17810713Sandreas.hansson@arm.com    Tick doAtomicAccess(PacketPtr pkt);
17910713Sandreas.hansson@arm.com    void doFunctionalAccess(PacketPtr pkt);
18010913Sandreas.sandberg@arm.com    virtual Tick calculateLatency(PacketPtr pkt);
18110913Sandreas.sandberg@arm.com    void recvStatusChange(Port::Status status);
18210913Sandreas.sandberg@arm.com
1839152Satgutier@umich.edu  public:
1849152Satgutier@umich.edu    virtual void serialize(std::ostream &os);
18510913Sandreas.sandberg@arm.com    virtual void unserialize(Checkpoint *cp, const std::string &section);
1868856SN/A
1878856SN/A};
1888856SN/A
1894492SN/A#endif //__PHYSICAL_MEMORY_HH__
1903403SN/A