#include <cstdint>
#include <ipmiblob/blob_handler.hpp>
#include <ipmiblob/test/crc_mock.hpp>
#include <ipmiblob/test/ipmi_interface_mock.hpp>
#include <memory>
#include <vector>

#include <gtest/gtest.h>

namespace ipmiblob
{
CrcInterface* crcIntf = nullptr;

std::uint16_t generateCrc(const std::vector<std::uint8_t>& data)
{
    return (crcIntf) ? crcIntf->generateCrc(data) : 0x00;
}

using ::testing::ContainerEq;
using ::testing::Eq;
using ::testing::Return;

class BlobHandlerTest : public ::testing::Test
{
  protected:
    void SetUp() override
    {
        crcIntf = &crcMock;
    }

    CrcMock crcMock;

    std::unique_ptr<IpmiInterface> CreateIpmiMock()
    {
        return std::make_unique<IpmiInterfaceMock>();
    }
};

TEST_F(BlobHandlerTest, getCountIpmiHappy)
{
    /* Verify returns the value specified by the IPMI response. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2, 0x00,
        static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobGetCount)};

    /* return 1 blob count. */
    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00, 0x00, 0x00,
                                      0x01, 0x00, 0x00, 0x00};

    std::vector<std::uint8_t> bytes = {0x01, 0x00, 0x00, 0x00};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(bytes)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));
    EXPECT_EQ(1, blob.getBlobCount());
}

TEST_F(BlobHandlerTest, enumerateBlobIpmiHappy)
{
    /* Verify returns the name specified by the IPMI response. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobEnumerate),
        0x00, 0x00,
        0x01, 0x00,
        0x00, 0x00};

    /* return value. */
    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00, 0x00, 0x00,
                                      'a',  'b',  'c',  'd',  0x00};

    std::vector<std::uint8_t> bytes = {'a', 'b', 'c', 'd', 0x00};
    std::vector<std::uint8_t> reqCrc = {0x01, 0x00, 0x00, 0x00};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(bytes)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));
    EXPECT_STREQ("abcd", blob.enumerateBlob(1).c_str());
}

TEST_F(BlobHandlerTest, enumerateBlobIpmiNoBytes)
{
    /* Simulate a case where the IPMI command returns no data. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobEnumerate),
        0x00, 0x00,
        0x01, 0x00,
        0x00, 0x00};

    /* return value. */
    std::vector<std::uint8_t> resp = {};

    std::vector<std::uint8_t> reqCrc = {0x01, 0x00, 0x00, 0x00};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));
    EXPECT_STREQ("", blob.enumerateBlob(1).c_str());
}

TEST_F(BlobHandlerTest, getBlobListIpmiHappy)
{
    /* Verify returns the list built via the above two commands. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request1 = {
        0xcf, 0xc2, 0x00,
        static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobGetCount)};

    /* return 1 blob count. */
    std::vector<std::uint8_t> resp1 = {0xcf, 0xc2, 0x00, 0x00, 0x00,
                                       0x01, 0x00, 0x00, 0x00};

    std::vector<std::uint8_t> bytes1 = {0x01, 0x00, 0x00, 0x00};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(bytes1)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request1)))
        .WillOnce(Return(resp1));

    std::vector<std::uint8_t> request2 = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobEnumerate),
        0x00, 0x00,
        0x00, 0x00,
        0x00, 0x00};

    /* return value. */
    std::vector<std::uint8_t> resp2 = {0xcf, 0xc2, 0x00, 0x00, 0x00,
                                       'a',  'b',  'c',  'd',  0x00};

    std::vector<std::uint8_t> reqCrc = {0x00, 0x00, 0x00, 0x00};
    std::vector<std::uint8_t> bytes2 = {'a', 'b', 'c', 'd', 0x00};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(bytes2)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request2)))
        .WillOnce(Return(resp2));

    /* A std::string is not nul-terminated by default. */
    std::vector<std::string> expectedList = {std::string{"abcd"}};

    EXPECT_EQ(expectedList, blob.getBlobList());
}

TEST_F(BlobHandlerTest, getStatWithMetadata)
{
    /* Stat received metadata. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobStat),
        0x00, 0x00,
        'a',  'b',
        'c',  'd',
        0x00};

    /* return blob_state: 0xffff, size: 0x00, metadata 0x3445 */
    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00, 0x00, 0x00, 0xff, 0xff,
                                      0x00, 0x00, 0x00, 0x00, 0x02, 0x34, 0x45};

    std::vector<std::uint8_t> reqCrc = {'a', 'b', 'c', 'd', 0x00};
    std::vector<std::uint8_t> respCrc = {0xff, 0xff, 0x00, 0x00, 0x00,
                                         0x00, 0x02, 0x34, 0x45};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(respCrc)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));

    auto meta = blob.getStat("abcd");
    EXPECT_EQ(meta.blob_state, 0xffff);
    EXPECT_EQ(meta.size, 0x00);
    std::vector<std::uint8_t> metadata = {0x34, 0x45};
    EXPECT_EQ(metadata, meta.metadata);
}

TEST_F(BlobHandlerTest, getStatNoMetadata)
{
    /* Stat received no metadata. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobStat),
        0x00, 0x00,
        'a',  'b',
        'c',  'd',
        0x00};

    /* return blob_state: 0xffff, size: 0x00, metadata 0x3445 */
    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00, 0x00, 0x00, 0xff,
                                      0xff, 0x00, 0x00, 0x00, 0x00, 0x00};

    std::vector<std::uint8_t> reqCrc = {'a', 'b', 'c', 'd', 0x00};
    std::vector<std::uint8_t> respCrc = {0xff, 0xff, 0x00, 0x00,
                                         0x00, 0x00, 0x00};

    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(respCrc)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));

    auto meta = blob.getStat("abcd");
    EXPECT_EQ(meta.blob_state, 0xffff);
    EXPECT_EQ(meta.size, 0x00);
    std::vector<std::uint8_t> metadata = {};
    EXPECT_EQ(metadata, meta.metadata);
}

TEST_F(BlobHandlerTest, getSessionStatNoMetadata)
{
    /* The get session stat succeeds. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobSessionStat),
        0x00, 0x00,
        0x01, 0x00};

    /* return blob_state: 0xffff, size: 0x00, metadata 0x3445 */
    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00, 0x00, 0x00, 0xff,
                                      0xff, 0x00, 0x00, 0x00, 0x00, 0x00};

    std::vector<std::uint8_t> reqCrc = {0x01, 0x00};
    std::vector<std::uint8_t> respCrc = {0xff, 0xff, 0x00, 0x00,
                                         0x00, 0x00, 0x00};

    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(respCrc)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));

    auto meta = blob.getStat(0x0001);
    EXPECT_EQ(meta.blob_state, 0xffff);
    EXPECT_EQ(meta.size, 0x00);
    std::vector<std::uint8_t> metadata = {};
    EXPECT_EQ(metadata, meta.metadata);
}

TEST_F(BlobHandlerTest, openBlobSucceeds)
{
    /* The open blob succeeds. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobOpen),
        0x00, 0x00,
        0x02, 0x04,
        'a',  'b',
        'c',  'd',
        0x00};

    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00, 0x00, 0x00, 0xfe, 0xed};

    std::vector<std::uint8_t> reqCrc = {0x02, 0x04, 'a', 'b', 'c', 'd', 0x00};
    std::vector<std::uint8_t> respCrc = {0xfe, 0xed};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(respCrc)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));

    const int writeBit = (1 << 1);
    const int lpcBit = (1 << 10);

    auto session = blob.openBlob("abcd", writeBit | lpcBit);
    EXPECT_EQ(0xedfe, session);
}

TEST_F(BlobHandlerTest, closeBlobSucceeds)
{
    /* The close succeeds. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobClose),
        0x00, 0x00,
        0x01, 0x00};
    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00};
    std::vector<std::uint8_t> reqCrc = {0x01, 0x00};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));

    blob.closeBlob(0x0001);
}

TEST_F(BlobHandlerTest, commitSucceedsNoData)
{
    /* The commit succeeds. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobCommit),
        0x00, 0x00,
        0x01, 0x00,
        0x00};

    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00};
    std::vector<std::uint8_t> reqCrc = {0x01, 0x00, 0x00};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));

    blob.commit(0x0001, {});
}

TEST_F(BlobHandlerTest, writeBytesSucceeds)
{
    /* The write bytes succeeds. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobWrite),
        0x00, 0x00,
        0x01, 0x00,
        0x00, 0x00,
        0x00, 0x00,
        'a',  'b',
        'c',  'd'};

    std::vector<std::uint8_t> bytes = {'a', 'b', 'c', 'd'};
    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00};
    std::vector<std::uint8_t> reqCrc = {0x01, 0x00, 0x00, 0x00, 0x00,
                                        0x00, 'a',  'b',  'c',  'd'};
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));

    blob.writeBytes(0x0001, 0, bytes);
}

TEST_F(BlobHandlerTest, readBytesSucceeds)
{
    /* The reading of bytes succeeds. */
    auto ipmi = CreateIpmiMock();
    IpmiInterfaceMock* ipmiMock =
        reinterpret_cast<IpmiInterfaceMock*>(ipmi.get());
    BlobHandler blob(std::move(ipmi));

    std::vector<std::uint8_t> request = {
        0xcf, 0xc2,
        0x00, static_cast<std::uint8_t>(BlobOEMCommands::bmcBlobRead),
        0x00, 0x00,
        0x01, 0x00,
        0x00, 0x00,
        0x00, 0x00,
        0x04, 0x00,
        0x00, 0x00};

    std::vector<std::uint8_t> expectedBytes = {'a', 'b', 'c', 'd'};
    std::vector<std::uint8_t> resp = {0xcf, 0xc2, 0x00, 0x00, 0x00,
                                      'a',  'b',  'c',  'd'};
    std::vector<std::uint8_t> reqCrc = {0x01, 0x00, 0x00, 0x00, 0x00,
                                        0x00, 0x04, 0x00, 0x00, 0x00};
    std::vector<std::uint8_t> respCrc = {'a', 'b', 'c', 'd'};

    EXPECT_CALL(crcMock, generateCrc(ContainerEq(reqCrc)))
        .WillOnce(Return(0x00));
    EXPECT_CALL(crcMock, generateCrc(ContainerEq(respCrc)))
        .WillOnce(Return(0x00));

    EXPECT_CALL(*ipmiMock,
                sendPacket(ipmiOEMNetFn, ipmiOEMBlobCmd, ContainerEq(request)))
        .WillOnce(Return(resp));

    EXPECT_EQ(blob.readBytes(0x0001, 0, 4), expectedBytes);
}

} // namespace ipmiblob
