/*
 * Copyright (c) 2012 ARM Limited
 * All rights reserved
 *
 * The license below extends only to copyright in the software and shall
 * not be construed as granting a license to any other intellectual
 * property including but not limited to intellectual property relating
 * to a hardware implementation of the functionality of the software
 * licensed hereunder.  You may use the software subject to the license
 * terms below provided that you ensure that this notice is replicated
 * unmodified and in its entirety in all distributions of the software,
 * modified or unmodified, in source code or in binary form.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are
 * met: redistributions of source code must retain the above copyright
 * notice, this list of conditions and the following disclaimer;
 * redistributions in binary form must reproduce the above copyright
 * notice, this list of conditions and the following disclaimer in the
 * documentation and/or other materials provided with the distribution;
 * neither the name of the copyright holders nor the names of its
 * contributors may be used to endorse or promote products derived from
 * this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */

#ifndef __MEM_PHYSICAL_HH__
#define __MEM_PHYSICAL_HH__

#include <cstdint>
#include <string>
#include <vector>

#include "base/addr_range.hh"
#include "base/addr_range_map.hh"
#include "mem/packet.hh"
#include "sim/serialize.hh"

/**
 * Forward declaration to avoid header dependencies.
 */
class AbstractMemory;

/**
 * A single entry for the backing store.
 */
class BackingStoreEntry
{
  public:

    /**
     * Create a backing store entry. Don't worry about managing the memory
     * pointers, because PhysicalMemory is responsible for that.
     */
    BackingStoreEntry(AddrRange range, uint8_t* pmem,
                      bool conf_table_reported, bool in_addr_map, bool kvm_map)
        : range(range), pmem(pmem), confTableReported(conf_table_reported),
          inAddrMap(in_addr_map), kvmMap(kvm_map)
        {}

    /**
     * The address range covered in the guest.
     */
     AddrRange range;

    /**
     * Pointer to the host memory this range maps to. This memory is the same
     * size as the range field.
     */
     uint8_t* pmem;

     /**
      * Whether this memory should be reported to the configuration table
      */
     bool confTableReported;

     /**
      * Whether this memory should appear in the global address map
      */
     bool inAddrMap;

     /**
      * Whether KVM should map this memory into the guest address space during
      * acceleration.
      */
     bool kvmMap;
};

/**
 * The physical memory encapsulates all memories in the system and
 * provides basic functionality for accessing those memories without
 * going through the memory system and interconnect.
 *
 * The physical memory is also responsible for providing the host
 * system backingstore used by the memories in the simulated guest
 * system. When the system is created, the physical memory allocates
 * the backing store based on the address ranges that are populated in
 * the system, and does so independent of how those map to actual
 * memory controllers. Thus, the physical memory completely abstracts
 * the mapping of the backing store of the host system and the address
 * mapping in the guest system. This enables us to arbitrarily change
 * the number of memory controllers, and their address mapping, as
 * long as the ranges stay the same.
 */
class PhysicalMemory : public Serializable
{

  private:

    // Name for debugging
    std::string _name;

    // Global address map
    AddrRangeMap<AbstractMemory*, 1> addrMap;

    // All address-mapped memories
    std::vector<AbstractMemory*> memories;

    // The total memory size
    uint64_t size;

    // Let the user choose if we reserve swap space when calling mmap
    const bool mmapUsingNoReserve;

    const std::string sharedBackstore;

    // The physical memory used to provide the memory in the simulated
    // system
    std::vector<BackingStoreEntry> backingStore;

    // Prevent copying
    PhysicalMemory(const PhysicalMemory&);

    // Prevent assignment
    PhysicalMemory& operator=(const PhysicalMemory&);

    /**
     * Create the memory region providing the backing store for a
     * given address range that corresponds to a set of memories in
     * the simulated system.
     *
     * @param range The address range covered
     * @param memories The memories this range maps to
     * @param kvm_map Should KVM map this memory for the guest
     */
    void createBackingStore(AddrRange range,
                            const std::vector<AbstractMemory*>& _memories,
                            bool conf_table_reported,
                            bool in_addr_map, bool kvm_map);

  public:

    /**
     * Create a physical memory object, wrapping a number of memories.
     */
    PhysicalMemory(const std::string& _name,
                   const std::vector<AbstractMemory*>& _memories,
                   bool mmap_using_noreserve,
                   const std::string& shared_backstore);

    /**
     * Unmap all the backing store we have used.
     */
    ~PhysicalMemory();

    /**
     * Return the name for debugging and for creation of sections for
     * checkpointing.
     */
    const std::string name() const { return _name; }

    /**
     * Check if a physical address is within a range of a memory that
     * is part of the global address map.
     *
     * @param addr A physical address
     * @return Whether the address corresponds to a memory
     */
    bool isMemAddr(Addr addr) const;

    /**
     * Get the memory ranges for all memories that are to be reported
     * to the configuration table. The ranges are merged before they
     * are returned such that any interleaved ranges appear as a
     * single range.
     *
     * @return All configuration table memory ranges
     */
    AddrRangeList getConfAddrRanges() const;

    /**
     * Get the total physical memory size.
     *
     * @return The sum of all memory sizes
     */
    uint64_t totalSize() const { return size; }

     /**
     * Get the pointers to the backing store for external host
     * access. Note that memory in the guest should be accessed using
     * access() or functionalAccess(). This interface is primarily
     * intended for CPU models using hardware virtualization. Note
     * that memories that are null are not present, and that the
     * backing store may also contain memories that are not part of
     * the OS-visible global address map and thus are allowed to
     * overlap.
     *
     * @return Pointers to the memory backing store
     */
    std::vector<BackingStoreEntry> getBackingStore() const
    { return backingStore; }

    /**
     * Perform an untimed memory access and update all the state
     * (e.g. locked addresses) and statistics accordingly. The packet
     * is turned into a response if required.
     *
     * @param pkt Packet performing the access
     */
    void access(PacketPtr pkt);

    /**
     * Perform an untimed memory read or write without changing
     * anything but the memory itself. No stats are affected by this
     * access. In addition to normal accesses this also facilitates
     * print requests.
     *
     * @param pkt Packet performing the access
     */
    void functionalAccess(PacketPtr pkt);

    /**
     * Serialize all the memories in the system. This is independent
     * of the logical memory layout, and the serialization only sees
     * the contigous backing store, independent of how this maps to
     * logical memories in the guest system.
     *
     * @param os stream to serialize to
     */
    void serialize(CheckpointOut &cp) const override;

    /**
     * Serialize a specific store.
     *
     * @param store_id Unique identifier of this backing store
     * @param range The address range of this backing store
     * @param pmem The host pointer to this backing store
     */
    void serializeStore(CheckpointOut &cp, unsigned int store_id,
                        AddrRange range, uint8_t* pmem) const;

    /**
     * Unserialize the memories in the system. As with the
     * serialization, this action is independent of how the address
     * ranges are mapped to logical memories in the guest system.
     */
    void unserialize(CheckpointIn &cp) override;

    /**
     * Unserialize a specific backing store, identified by a section.
     */
    void unserializeStore(CheckpointIn &cp);

};

#endif //__MEM_PHYSICAL_HH__
