#pragma once

#include "pci_handler.hpp"

#include <boost/endian/arithmetic.hpp>

#include <array>
#include <cstdint>
#include <memory>
#include <tuple>

namespace bios_bmc_smm_error_logger
{

/* Adding endianness */
using boost::endian::little_uint16_t;
using boost::endian::little_uint32_t;
using boost::endian::little_uint64_t;

// EntryPair.first = QueueEntryHeader
// EntryPair.second = Error entry in vector of bytes
using EntryPair = std::pair<struct QueueEntryHeader, std::vector<uint8_t>>;

struct CircularBufferHeader
{
    little_uint32_t bmcInterfaceVersion;        // Offset 0x0
    little_uint32_t biosInterfaceVersion;       // Offset 0x4
    std::array<little_uint32_t, 4> magicNumber; // Offset 0x8
    little_uint16_t queueSize;                  // Offset 0x18
    little_uint16_t ueRegionSize;               // Offset 0x1a
    little_uint32_t bmcFlags;                   // Offset 0x1c
    little_uint16_t bmcReadPtr;                 // Offset 0x20
    std::array<uint8_t, 6> reserved1;           // Offset 0x22
    little_uint32_t biosFlags;                  // Offset 0x28
    little_uint16_t biosWritePtr;               // Offset 0x2c
    std::array<uint8_t, 2> reserved2;           // Offset 0x2e
    // UE reserved region:                         Offset 0x30
    // Error log queue:       Offset 0x30 + UE reserved region

    bool operator==(const CircularBufferHeader& other) const
    {
        /* Skip comparing reserved1 and reserved2 */
        return std::tie(this->bmcInterfaceVersion, this->biosInterfaceVersion,
                        this->magicNumber, this->queueSize, this->ueRegionSize,
                        this->bmcFlags, this->bmcReadPtr, this->biosFlags,
                        this->biosWritePtr) ==
               std::tie(other.bmcInterfaceVersion, other.biosInterfaceVersion,
                        other.magicNumber, other.queueSize, other.ueRegionSize,
                        other.bmcFlags, other.bmcReadPtr, other.biosFlags,
                        other.biosWritePtr);
    }
};
static_assert(sizeof(CircularBufferHeader) == 0x30,
              "Size of CircularBufferHeader struct is incorrect.");

struct QueueEntryHeader
{
    little_uint16_t sequenceId; // Offset 0x0
    little_uint16_t entrySize;  // Offset 0x2
    uint8_t checksum;           // Offset 0x4
    uint8_t rdeCommandType;     // Offset 0x5
    // RDE Command                 Offset 0x6
    bool operator==(const QueueEntryHeader& other) const
    {
        return std::tie(this->sequenceId, this->entrySize, this->checksum,
                        this->rdeCommandType) ==
               std::tie(other.sequenceId, other.entrySize, other.checksum,
                        other.rdeCommandType);
    }
};
static_assert(sizeof(QueueEntryHeader) == 0x6,
              "Size of QueueEntryHeader struct is incorrect.");

/**
 * An interface class for the buffer helper APIs
 */
class BufferInterface
{
  public:
    virtual ~BufferInterface() = default;

    /**
     * Zero out the buffer first before populating the header
     *
     * @param[in] bmcInterfaceVersion - Used to initialize the header
     * @param[in] queueSize - Used to initialize the header
     * @param[in] ueRegionSize - Used to initialize the header
     * @param[in] magicNumber - Used to initialize the header
     * @return true if successful
     */
    virtual void initialize(uint32_t bmcInterfaceVersion, uint16_t queueSize,
                            uint16_t ueRegionSize,
                            const std::array<uint32_t, 4>& magicNumber) = 0;

    /**
     * Read the buffer header from shared buffer
     */
    virtual void readBufferHeader() = 0;

    /**
     * Getter API for the cached buffer header
     * @return cached CircularBufferHeader
     */
    virtual struct CircularBufferHeader getCachedBufferHeader() const = 0;

    /**
     * Write to the bufferHeader and update the read pointer
     * @param[in] newReadPtr - read pointer to update to.
     *  "readPtr"s (including this one) are offset relative to the "Error Log
     *  Queue region" = (sizeof(CircularBufferHeader) + UE reserved region)
     */
    virtual void updateReadPtr(const uint32_t newReadPtr) = 0;

    /**
     * Wrapper for the dataInterface->read, performs wraparound read
     *
     * @param[in] offset - offset relative to the beginning of MMIO space
     * @param[in] length - bytes to read
     * @param[in] additionalBoundaryCheck - bytes to add to the boundary check
     * for added restriction
     * @return the bytes read
     */
    virtual std::vector<uint8_t>
        wraparoundRead(const uint32_t offset, const uint32_t length,
                       const uint32_t additionalBoundaryCheck) = 0;
    /**
     * Read the entry header from shared buffer
     *
     * @param[in] offset - offset relative to the beginning of MMIO space
     * @return the entry header
     */
    virtual struct QueueEntryHeader readEntryHeader(size_t offset) = 0;

    /**
     * Read the queue entry from the error log queue
     *
     * @param[in] offset - offset relative to the beginning of MMIO space
     * @return entry header and entry pair read from buffer
     */
    virtual EntryPair readEntry(size_t offset) = 0;
};

/**
 * Buffer implementation class
 */
class BufferImpl : public BufferInterface
{
  public:
    /** @brief Constructor for BufferImpl
     *  @param[in] dataInterface     - DataInterface for this object
     */
    explicit BufferImpl(std::unique_ptr<DataInterface> dataInterface);
    void initialize(uint32_t bmcInterfaceVersion, uint16_t queueSize,
                    uint16_t ueRegionSize,
                    const std::array<uint32_t, 4>& magicNumber) override;
    void readBufferHeader() override;
    struct CircularBufferHeader getCachedBufferHeader() const override;
    void updateReadPtr(const uint32_t newReadPtr) override;
    std::vector<uint8_t>
        wraparoundRead(const uint32_t offset, const uint32_t length,
                       const uint32_t additionalBoundaryCheck = 0) override;
    struct QueueEntryHeader readEntryHeader(size_t offset) override;
    EntryPair readEntry(size_t offset) override;

  private:
    /** @brief The Error log queue starts after the UE region, which is where
     * the read and write pointers are offset from relatively
     *  @return relative offset for read and write pointers
     */
    size_t getQueueOffset();

    std::unique_ptr<DataInterface> dataInterface;
    struct CircularBufferHeader cachedBufferHeader = {};
};

} // namespace bios_bmc_smm_error_logger
