system.hh revision 8460
12SN/A/*
21762SN/A * Copyright (c) 2002-2005 The Regents of The University of Michigan
37897Shestness@cs.utexas.edu * Copyright (c) 2011 Regents of the University of California
42SN/A * All rights reserved.
52SN/A *
62SN/A * Redistribution and use in source and binary forms, with or without
72SN/A * modification, are permitted provided that the following conditions are
82SN/A * met: redistributions of source code must retain the above copyright
92SN/A * notice, this list of conditions and the following disclaimer;
102SN/A * redistributions in binary form must reproduce the above copyright
112SN/A * notice, this list of conditions and the following disclaimer in the
122SN/A * documentation and/or other materials provided with the distribution;
132SN/A * neither the name of the copyright holders nor the names of its
142SN/A * contributors may be used to endorse or promote products derived from
152SN/A * this software without specific prior written permission.
162SN/A *
172SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
182SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
192SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
202SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
212SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
222SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
232SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
242SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
252SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
262SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
272SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
282665Ssaidi@eecs.umich.edu *
292665Ssaidi@eecs.umich.edu * Authors: Steve Reinhardt
302665Ssaidi@eecs.umich.edu *          Lisa Hsu
312665Ssaidi@eecs.umich.edu *          Nathan Binkert
327897Shestness@cs.utexas.edu *          Rick Strong
332SN/A */
342SN/A
352SN/A#ifndef __SYSTEM_HH__
362SN/A#define __SYSTEM_HH__
372SN/A
382SN/A#include <string>
3975SN/A#include <vector>
402SN/A
412439SN/A#include "base/loader/symtab.hh"
422439SN/A#include "base/misc.hh"
43603SN/A#include "base/statistics.hh"
442986Sgblack@eecs.umich.edu#include "config/full_system.hh"
45603SN/A#include "cpu/pc_event.hh"
464762Snate@binkert.org#include "enums/MemoryMode.hh"
472520SN/A#include "mem/port.hh"
484762Snate@binkert.org#include "params/System.hh"
492378SN/A#include "sim/sim_object.hh"
506658Snate@binkert.org
512378SN/A#if FULL_SYSTEM
52722SN/A#include "kern/system_events.hh"
532378SN/A#endif
54312SN/A
551634SN/Aclass BaseCPU;
562680Sktlim@umich.educlass ThreadContext;
571634SN/Aclass ObjectFile;
582521SN/Aclass PhysicalMemory;
592378SN/A
602378SN/A#if FULL_SYSTEM
61803SN/Aclass Platform;
627723SAli.Saidi@ARM.comclass FunctionalPort;
637723SAli.Saidi@ARM.comclass VirtualPort;
643960Sgblack@eecs.umich.edu#endif
652378SN/Aclass GDBListener;
666658Snate@binkert.orgclass BaseRemoteGDB;
672SN/A
682SN/Aclass System : public SimObject
692SN/A{
70603SN/A  public:
712901Ssaidi@eecs.umich.edu
722902Ssaidi@eecs.umich.edu    static const char *MemoryModeStrings[3];
732902Ssaidi@eecs.umich.edu
744762Snate@binkert.org    Enums::MemoryMode
754762Snate@binkert.org    getMemoryMode()
764762Snate@binkert.org    {
774762Snate@binkert.org        assert(memoryMode);
784762Snate@binkert.org        return memoryMode;
794762Snate@binkert.org    }
802901Ssaidi@eecs.umich.edu
812901Ssaidi@eecs.umich.edu    /** Change the memory mode of the system. This should only be called by the
822901Ssaidi@eecs.umich.edu     * python!!
832901Ssaidi@eecs.umich.edu     * @param mode Mode to change to (atomic/timing)
842901Ssaidi@eecs.umich.edu     */
854762Snate@binkert.org    void setMemoryMode(Enums::MemoryMode mode);
862901Ssaidi@eecs.umich.edu
872521SN/A    PhysicalMemory *physmem;
882SN/A    PCEventQueue pcEventQueue;
892SN/A
902680Sktlim@umich.edu    std::vector<ThreadContext *> threadContexts;
915714Shsul@eecs.umich.edu    int _numContexts;
921806SN/A
936221Snate@binkert.org    ThreadContext *getThreadContext(ThreadID tid)
945713Shsul@eecs.umich.edu    {
955713Shsul@eecs.umich.edu        return threadContexts[tid];
965713Shsul@eecs.umich.edu    }
975713Shsul@eecs.umich.edu
985714Shsul@eecs.umich.edu    int numContexts()
991806SN/A    {
1006227Snate@binkert.org        assert(_numContexts == (int)threadContexts.size());
1015714Shsul@eecs.umich.edu        return _numContexts;
1021806SN/A    }
103180SN/A
1046029Ssteve.reinhardt@amd.com    /** Return number of running (non-halted) thread contexts in
1056029Ssteve.reinhardt@amd.com     * system.  These threads could be Active or Suspended. */
1066029Ssteve.reinhardt@amd.com    int numRunningContexts();
1076029Ssteve.reinhardt@amd.com
1088460SAli.Saidi@ARM.com    /** List to store ranges of memories in this system */
1098460SAli.Saidi@ARM.com    AddrRangeList memRanges;
1108460SAli.Saidi@ARM.com
1118460SAli.Saidi@ARM.com    /** check if an address points to valid system memory
1128460SAli.Saidi@ARM.com     * and thus we can fetch instructions out of it
1138460SAli.Saidi@ARM.com     */
1148460SAli.Saidi@ARM.com    bool isMemory(const Addr addr) const;
1158460SAli.Saidi@ARM.com
1162378SN/A#if FULL_SYSTEM
1172378SN/A    Platform *platform;
1182378SN/A    uint64_t init_param;
1192378SN/A
1202520SN/A    /** Port to physical memory used for writing object files into ram at
1212520SN/A     * boot.*/
1227723SAli.Saidi@ARM.com    FunctionalPort *functionalPort;
1237723SAli.Saidi@ARM.com    VirtualPort *virtPort;
1242520SN/A
1251885SN/A    /** kernel symbol table */
1261070SN/A    SymbolTable *kernelSymtab;
127954SN/A
1281070SN/A    /** Object pointer for the kernel code */
1291070SN/A    ObjectFile *kernel;
1301070SN/A
1311070SN/A    /** Begining of kernel code */
1321070SN/A    Addr kernelStart;
1331070SN/A
1341070SN/A    /** End of kernel code */
1351070SN/A    Addr kernelEnd;
1361070SN/A
1371070SN/A    /** Entry point in the kernel to start at */
1381070SN/A    Addr kernelEntry;
1391070SN/A
1407580SAli.Saidi@arm.com    /** Mask that should be anded for binary/symbol loading.
1417580SAli.Saidi@arm.com     * This allows one two different OS requirements for the same ISA to be
1427580SAli.Saidi@arm.com     * handled.  Some OSes are compiled for a virtual address and need to be
1437580SAli.Saidi@arm.com     * loaded into physical memory that starts at address 0, while other
1447580SAli.Saidi@arm.com     * bare metal tools generate images that start at address 0.
1457580SAli.Saidi@arm.com     */
1467580SAli.Saidi@arm.com    Addr loadAddrMask;
1477580SAli.Saidi@arm.com
1482378SN/A#else
1492378SN/A
1507770SAli.Saidi@ARM.com    Addr pagePtr;
1512378SN/A
1524997Sgblack@eecs.umich.edu  protected:
1537770SAli.Saidi@ARM.com    uint64_t nextPID;
1544997Sgblack@eecs.umich.edu
1554997Sgblack@eecs.umich.edu  public:
1564997Sgblack@eecs.umich.edu    uint64_t allocatePID()
1574997Sgblack@eecs.umich.edu    {
1587770SAli.Saidi@ARM.com        return nextPID++;
1594997Sgblack@eecs.umich.edu    }
1604997Sgblack@eecs.umich.edu
1615795Ssaidi@eecs.umich.edu    /** Amount of physical memory that is still free */
1625795Ssaidi@eecs.umich.edu    Addr freeMemSize();
1635795Ssaidi@eecs.umich.edu
1645795Ssaidi@eecs.umich.edu    /** Amount of physical memory that exists */
1655795Ssaidi@eecs.umich.edu    Addr memSize();
1665795Ssaidi@eecs.umich.edu
1672378SN/A
1682378SN/A#endif // FULL_SYSTEM
1692378SN/A
1701885SN/A  protected:
1714762Snate@binkert.org    Enums::MemoryMode memoryMode;
1727914SBrad.Beckmann@amd.com    uint64_t workItemsBegin;
1737914SBrad.Beckmann@amd.com    uint64_t workItemsEnd;
1747914SBrad.Beckmann@amd.com    std::vector<bool> activeCpus;
1757914SBrad.Beckmann@amd.com
1767914SBrad.Beckmann@amd.com  public:
1777914SBrad.Beckmann@amd.com    /**
1787914SBrad.Beckmann@amd.com     * Called by pseudo_inst to track the number of work items started by this
1797914SBrad.Beckmann@amd.com     * system.
1807914SBrad.Beckmann@amd.com     */
1817914SBrad.Beckmann@amd.com    uint64_t
1827914SBrad.Beckmann@amd.com    incWorkItemsBegin()
1837914SBrad.Beckmann@amd.com    {
1847914SBrad.Beckmann@amd.com        return ++workItemsBegin;
1857914SBrad.Beckmann@amd.com    }
1867914SBrad.Beckmann@amd.com
1877914SBrad.Beckmann@amd.com    /**
1887914SBrad.Beckmann@amd.com     * Called by pseudo_inst to track the number of work items completed by
1897914SBrad.Beckmann@amd.com     * this system.
1907914SBrad.Beckmann@amd.com     */
1917914SBrad.Beckmann@amd.com    uint64_t
1927914SBrad.Beckmann@amd.com    incWorkItemsEnd()
1937914SBrad.Beckmann@amd.com    {
1947914SBrad.Beckmann@amd.com        return ++workItemsEnd;
1957914SBrad.Beckmann@amd.com    }
1967914SBrad.Beckmann@amd.com
1977914SBrad.Beckmann@amd.com    /**
1987914SBrad.Beckmann@amd.com     * Called by pseudo_inst to mark the cpus actively executing work items.
1997914SBrad.Beckmann@amd.com     * Returns the total number of cpus that have executed work item begin or
2007914SBrad.Beckmann@amd.com     * ends.
2017914SBrad.Beckmann@amd.com     */
2027914SBrad.Beckmann@amd.com    int
2037914SBrad.Beckmann@amd.com    markWorkItem(int index)
2047914SBrad.Beckmann@amd.com    {
2057914SBrad.Beckmann@amd.com        int count = 0;
2067914SBrad.Beckmann@amd.com        assert(index < activeCpus.size());
2077914SBrad.Beckmann@amd.com        activeCpus[index] = true;
2087914SBrad.Beckmann@amd.com        for (std::vector<bool>::iterator i = activeCpus.begin();
2097914SBrad.Beckmann@amd.com             i < activeCpus.end(); i++) {
2107914SBrad.Beckmann@amd.com            if (*i) count++;
2117914SBrad.Beckmann@amd.com        }
2127914SBrad.Beckmann@amd.com        return count;
2137914SBrad.Beckmann@amd.com    }
2142901Ssaidi@eecs.umich.edu
2152424SN/A#if FULL_SYSTEM
2161885SN/A    /**
2171885SN/A     * Fix up an address used to match PCs for hooking simulator
2181885SN/A     * events on to target function executions.  See comment in
2191885SN/A     * system.cc for details.
2201885SN/A     */
2212158SN/A    virtual Addr fixFuncEventAddr(Addr addr) = 0;
2221885SN/A
2231885SN/A    /**
2241885SN/A     * Add a function-based event to the given function, to be looked
2251885SN/A     * up in the specified symbol table.
2261885SN/A     */
2271885SN/A    template <class T>
2282989Ssaidi@eecs.umich.edu    T *addFuncEvent(SymbolTable *symtab, const char *lbl)
2291885SN/A    {
2301913SN/A        Addr addr = 0; // initialize only to avoid compiler warning
2311885SN/A
2321885SN/A        if (symtab->findAddress(lbl, addr)) {
2331885SN/A            T *ev = new T(&pcEventQueue, lbl, fixFuncEventAddr(addr));
2341885SN/A            return ev;
2351885SN/A        }
2361885SN/A
2371885SN/A        return NULL;
2381885SN/A    }
2391885SN/A
2401885SN/A    /** Add a function-based event to kernel code. */
2411885SN/A    template <class T>
2422989Ssaidi@eecs.umich.edu    T *addKernelFuncEvent(const char *lbl)
2431885SN/A    {
2441885SN/A        return addFuncEvent<T>(kernelSymtab, lbl);
2451885SN/A    }
2461885SN/A
2472378SN/A#endif
24877SN/A  public:
2496658Snate@binkert.org    std::vector<BaseRemoteGDB *> remoteGDB;
2501070SN/A    std::vector<GDBListener *> gdbListen;
2513960Sgblack@eecs.umich.edu    bool breakpoint();
2521070SN/A
2531070SN/A  public:
2544762Snate@binkert.org    typedef SystemParams Params;
2551070SN/A
2562158SN/A  protected:
2572158SN/A    Params *_params;
2581070SN/A
2592158SN/A  public:
2601070SN/A    System(Params *p);
2612SN/A    ~System();
2622SN/A
2637733SAli.Saidi@ARM.com    void initState();
2641129SN/A
2652158SN/A    const Params *params() const { return (const Params *)_params; }
2662158SN/A
2671070SN/A  public:
2682378SN/A
2692378SN/A#if FULL_SYSTEM
2701070SN/A    /**
2711070SN/A     * Returns the addess the kernel starts at.
2721070SN/A     * @return address the kernel starts at
2731070SN/A     */
2741070SN/A    Addr getKernelStart() const { return kernelStart; }
2751070SN/A
2761070SN/A    /**
2771070SN/A     * Returns the addess the kernel ends at.
2781070SN/A     * @return address the kernel ends at
2791070SN/A     */
2801070SN/A    Addr getKernelEnd() const { return kernelEnd; }
2811070SN/A
2821070SN/A    /**
2831070SN/A     * Returns the addess the entry point to the kernel code.
2841070SN/A     * @return entry point of the kernel code
2851070SN/A     */
2861070SN/A    Addr getKernelEntry() const { return kernelEntry; }
2871070SN/A
2882378SN/A#else
2892378SN/A
2902378SN/A    Addr new_page();
2912378SN/A
2922378SN/A#endif // FULL_SYSTEM
2932378SN/A
2945718Shsul@eecs.umich.edu    int registerThreadContext(ThreadContext *tc, int assigned=-1);
2955713Shsul@eecs.umich.edu    void replaceThreadContext(ThreadContext *tc, int context_id);
2961070SN/A
2971070SN/A    void serialize(std::ostream &os);
2981070SN/A    void unserialize(Checkpoint *cp, const std::string &section);
2997897Shestness@cs.utexas.edu    virtual void resume();
3002SN/A
30177SN/A  public:
3027897Shestness@cs.utexas.edu    Counter totalNumInsts;
3037897Shestness@cs.utexas.edu    EventQueue instEventQueue;
3047897Shestness@cs.utexas.edu
3052SN/A    ////////////////////////////////////////////
3062SN/A    //
3072SN/A    // STATIC GLOBAL SYSTEM LIST
3082SN/A    //
3092SN/A    ////////////////////////////////////////////
3102SN/A
3112SN/A    static std::vector<System *> systemList;
3122SN/A    static int numSystemsRunning;
3132SN/A
3142SN/A    static void printSystems();
3152158SN/A
3162158SN/A
3172SN/A};
3182SN/A
3192SN/A#endif // __SYSTEM_HH__
320