fxos/include/fxos/memory.h

110 lines
2.8 KiB
C++

//---
// fxos.memory: Standard memory regions
//---
#ifndef LIBFXOS_MEMORY_H
#define LIBFXOS_MEMORY_H
#include <string>
#include <array>
#include <cstdint>
namespace FxOS {
/* Memory area enumeration with a few tools */
class MemoryArea
{
public:
enum MemoryAreaName: int8_t {
/* Userspace seen from user and privileged mode */
U0, P0,
/* Second half of memory, only for privileged mode */
P1, P2, P3, P4,
};
MemoryArea() = default;
/* Construction from MemoryAreaName */
constexpr MemoryArea(MemoryAreaName name): m_name(name) {}
/* Start, end (last byte in area) and size of area */
uint32_t start() const noexcept;
uint32_t end() const noexcept;
uint32_t size() const noexcept;
/* Conversion to MemoryAreaName for switch */
constexpr operator MemoryAreaName () noexcept { return m_name; }
/* Comparison operators */
constexpr bool operator == (MemoryArea a) const {
return m_name == a.m_name;
}
constexpr bool operator != (MemoryArea a) const {
return m_name != a.m_name;
}
private:
MemoryAreaName m_name;
};
struct MemoryRegion
{
/* Address space regions that correspond to standard (ie. contiguous
multi-addressable) memory */
static MemoryRegion const ROM;
static MemoryRegion const RAM;
static MemoryRegion const ROM_P2;
static MemoryRegion const RAM_P2;
static MemoryRegion const RS;
static MemoryRegion const ILRAM;
static MemoryRegion const XRAM;
static MemoryRegion const YRAM;
/* All standard regions. */
static std::array<MemoryRegion const *, 8> const all();
/* Determine if an address falls into one of the standard regions.
Throws std::out_of_range if none. */
static MemoryRegion const *region_for(uint32_t address);
/* Empty region at 0 */
MemoryRegion();
/* Short constructor which calls guess_flags() */
MemoryRegion(std::string name, uint32_t start, uint32_t end,
bool writable);
/* Short constructor for standard regions only */
MemoryRegion(std::string standard_region_name);
/* Region name */
std::string name {};
/* Start address and end address. Generally the end address has one
additional byte. This is okay since no region is supposed to extend
to the very end of the memory. */
uint32_t start, end;
/* The region is writable under normal conditions */
bool writable;
/* The cache is active in that region (if enabled) */
bool cacheable;
/* The MMU is active in that region (if enabled) */
bool mappable;
/* Returns the size of the region */
uint32_t size() const noexcept;
/* Returns the area associated to the region (assuming it is fully
contained in one, which should always be the case) */
MemoryArea area() const noexcept;
private:
static std::array<MemoryRegion const *, 8> const m_all;
/* Automatically guess the cacheable and mappable flags */
void guess_flags() noexcept;
};
} /* namespace FxOS */
#endif /* LIBFXOS_MEMORY_H */