libanemo/include/libcpu/memory.hh

162 lines
5.3 KiB
C++

#ifndef LIBCPU_MEMORY_HH
#define LIBCPU_MEMORY_HH
#include <cstddef>
#include <cstdint>
#include <istream>
#include <ostream>
#include <libanemo/width.hh>
#include <memory>
#include <optional>
namespace libcpu {
/**
* @brief Abstract base class representing a view into memory.
*
* Provides read/write operations and memory management utilities for a specific
* memory region. Derived classes implement the actual storage mechanism.
*/
class memory_view {
public:
/**
* @brief Construct a memory view from another memory view.
*
* This class will map the memory in `src`, from `src_base` with the size of `view_size`
* to the address space of the new memory view from `view_base`.
*
* @param src The source memory view to create a view into
* @param src_base Base address of the new view (in the address space of source memory)
* @param view_base Base address of the new view (in the address space of new memory view)
* @param view_size Size of the new view in bytes
*/
memory_view(const memory_view &src, uint64_t src_base, uint64_t view_base, uint64_t view_size);
/**
* @brief Read data from memory.
*
* @param addr The memory address to read from
* @param width The width of the data to read
* @param little_endian Byte ordering (true for little-endian, false for big-endian)
* @return The read value, or std::nullopt if read failed
*/
std::optional<uint64_t> read(uint64_t addr, libanemo::width_t width, bool little_endian = true);
/**
* @brief Write data to memory.
*
* @param addr The memory address to write to
* @param width The width of the data to write (1-8 bytes)
* @param value The value to write
* @param little_endian Byte ordering (true for little-endian, false for big-endian)
* @return true if write succeeded, false if failed
*/
bool write(uint64_t addr, libanemo::width_t width, uint64_t value, bool little_endian = true);
/**
* @brief Get a direct pointer to host memory.
*
* @param addr Memory address to access
* @return Pointer to host memory at the specified address,
* or nullptr if address is invalid
*/
uint8_t* host_addr(uint64_t addr);
/**
* @brief Save memory contents to a file.
*
* @param filename Path to the output file
*/
void save(const char* filename) const;
/**
* @brief Save memory contents to an output stream.
*
* @param out Output stream to write to
*/
void save(std::ostream& out) const;
/**
* @brief Restore memory contents from a file.
*
* @param filename Path to the input file
* @return Number of bytes successfully loaded
*/
uint64_t restore(const char* filename);
/**
* @brief Restore memory contents from an input stream.
*
* @param in Input stream to read from
* @return Number of bytes successfully loaded
*/
uint64_t restore(std::istream& in);
/**
* @brief Load an ELF binary into memory (auto-detects 32/64-bit format).
*
* @param buffer Pointer to the ELF file data in memory
* @return The entry point address of the loaded ELF
*/
uint64_t load_elf(const uint8_t* buffer);
/**
* @brief Load an ELF file into memory (auto-detects 32/64-bit format).
*
* @param filename Path to the ELF file
* @return The entry point address of the loaded ELF
*/
uint64_t load_elf_from_file(const char* filename);
/**
* @brief Get the size of the memory region.
*
* @return uint64_t Size of the memory region in bytes
*/
uint64_t get_size() const;
/**
* @brief Check if a memory access would be out of bounds.
*
* @param addr The address to check
* @param width The width of the memory access
* @return bool True if the address range [addr, addr+width-1] is invalid,
* false otherwise
*/
bool out_of_bound(uint64_t addr, libanemo::width_t width) const;
protected:
uint64_t offset; ///< Pointer to the memory storage
uint64_t addr_lb; ///< Lowest address (inclusive)
uint64_t addr_ub; ///< Highest address (exclusive)
/**
* @brief Protected default constructor for derived classes.
*/
memory_view();
};
/**
* @brief Concrete memory implementation using contiguous storage.
*
* This class provides memory operations with 64-bit addressing using a
* contiguous block of memory. All methods are non-virtual for performance.
*/
class memory: public memory_view {
public:
/**
* @brief Construct a new memory object with contiguous storage.
*
* @param mem_base Base address of the memory region
* @param mem_size Size of memory region in bytes
*/
memory(uint64_t mem_base, size_t mem_size);
protected:
std::unique_ptr<uint8_t[]> mem; ///< Contiguous memory storage
};
} // namespace libcpu
#endif