/*
// Copyright (c) 2019 Intel Corporation
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
*/
#include <errno.h>
#include <fcntl.h>
#include <peci.h>
#include <stdlib.h>
#include <string.h>
#include <sys/ioctl.h>
#include <syslog.h>
#include <time.h>
#include <unistd.h>
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wcpp"
#pragma GCC diagnostic ignored "-Wvariadic-macros"
#include <linux/peci-ioctl.h>
#pragma GCC diagnostic pop

EPECIStatus peci_GetDIB_seq(uint8_t target, uint64_t* dib, int peci_fd);

char* peci_device_list[2];
#define DEV_NAME_SIZE 64
/*-------------------------------------------------------------------------
 * This funcion sets the name of the PECI device file to use.
 * If the PECI device name is null try "/dev/peci-default",
 * if "/dev/peci-default" does not exist, fall back to "/dev/peci-0"
 *------------------------------------------------------------------------*/
void peci_SetDevName(char* peci_dev)
{
    static char peci_name_new[DEV_NAME_SIZE] = {0};

    if (peci_dev)
    {
        strncpy(peci_name_new, peci_dev, sizeof(peci_name_new));
        peci_name_new[DEV_NAME_SIZE - 1] = '\0';
        peci_device_list[0] = peci_name_new;
        peci_device_list[1] = NULL;
        syslog(LOG_INFO, "PECI set dev name to %s\n", peci_device_list[0]);
    }
    else
    {
        peci_device_list[0] = "/dev/peci-default";
        peci_device_list[1] = "/dev/peci-0";
        syslog(LOG_INFO, "PECI set dev names to %s, %s\n", peci_device_list[0],
               peci_device_list[1]);
    }
}

/*-------------------------------------------------------------------------
 * This function initializes PECI device name when a shared library
 * is loaded, typically during program startup.
 *------------------------------------------------------------------------*/
static void init() __attribute__((constructor));
static void init()
{
    // By default PECI_DEV is not defined in the environment,
    // so this will call peci_SetDevName(NULL) and initialize
    // PECI device name to defaults.
    peci_SetDevName(getenv("PECI_DEV"));
}

/*-------------------------------------------------------------------------
 * This function unlocks the peci interface
 *------------------------------------------------------------------------*/
void peci_Unlock(int peci_fd)
{
    if (close(peci_fd) != 0)
    {
        syslog(LOG_ERR, "PECI device failed to unlock.\n");
    }
}

/*-------------------------------------------------------------------------
 * This function attempts to lock the peci interface with the specified
 * timeout and returns a file descriptor if successful.
 *------------------------------------------------------------------------*/
EPECIStatus peci_Lock(int* peci_fd, int timeout_ms)
{
    struct timespec sRequest = {0};
    sRequest.tv_sec = 0;
    sRequest.tv_nsec = PECI_TIMEOUT_RESOLUTION_MS * 1000 * 1000;
    int timeout_count = 0;
    char* peci_device = peci_device_list[0];

    if (NULL == peci_fd)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Open the PECI driver with the specified timeout
    *peci_fd = open(peci_device, O_RDWR | O_CLOEXEC);
    if (*peci_fd == -1 && errno == ENOENT && peci_device_list[1])
    {
        peci_device = peci_device_list[1];
        *peci_fd = open(peci_device, O_RDWR | O_CLOEXEC);
    }
    switch (timeout_ms)
    {
        case PECI_NO_WAIT:
            break;
        case PECI_WAIT_FOREVER:
            while (-1 == *peci_fd)
            {
                nanosleep(&sRequest, NULL);
                *peci_fd = open(peci_device, O_RDWR | O_CLOEXEC);
            }
        default:
            while (-1 == *peci_fd && timeout_count < timeout_ms)
            {
                nanosleep(&sRequest, NULL);
                timeout_count += PECI_TIMEOUT_RESOLUTION_MS;
                *peci_fd = open(peci_device, O_RDWR | O_CLOEXEC);
            }
    }
    if (-1 == *peci_fd)
    {
        syslog(LOG_ERR, " >>> PECI Device Busy <<< \n");
        return PECI_CC_DRIVER_ERR;
    }
    return PECI_CC_SUCCESS;
}

/*-------------------------------------------------------------------------
 * This function closes the peci interface
 *------------------------------------------------------------------------*/
static void peci_Close(int peci_fd)
{
    peci_Unlock(peci_fd);
}

/*-------------------------------------------------------------------------
 * This function opens the peci interface and returns a file descriptor
 *------------------------------------------------------------------------*/
static EPECIStatus peci_Open(int* peci_fd)
{
    if (NULL == peci_fd)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Lock the PECI driver with a default timeout
    return peci_Lock(peci_fd, PECI_TIMEOUT_MS);
}

/*-------------------------------------------------------------------------
 * This function issues peci commands to peci driver
 *------------------------------------------------------------------------*/
static EPECIStatus HW_peci_issue_cmd(unsigned int cmd, char* cmdPtr,
                                     int peci_fd)
{
    if (cmdPtr == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (ioctl(peci_fd, cmd, cmdPtr) != 0)
    {
        if (errno == ETIMEDOUT)
        {
            return PECI_CC_TIMEOUT;
        }
        return PECI_CC_DRIVER_ERR;
    }

    return PECI_CC_SUCCESS;
}

/*-------------------------------------------------------------------------
 * Find the specified PCI bus number value
 *------------------------------------------------------------------------*/
EPECIStatus FindBusNumber(uint8_t u8Bus, uint8_t u8Cpu, uint8_t* pu8BusValue)
{
    uint8_t u8CpuBus0[] = {
        PECI_PCI_BUS0_CPU0,
        PECI_PCI_BUS0_CPU1,
    };
    uint8_t u8Bus0 = 0;
    uint8_t u8Offset = 0;
    EPECIStatus ret = PECI_CC_SUCCESS;
    uint8_t u8Reg[4] = {0};
    uint8_t cc = 0;

    // First check for valid inputs
    // Check cpu and bus numbers, only support buses [5:0]
    if ((u8Bus > 5) || (u8Cpu >= (sizeof(u8CpuBus0) / sizeof(uint8_t))) ||
        (pu8BusValue == NULL))
    {
        return PECI_CC_INVALID_REQ;
    }

    // Get the Bus 0 value for the requested CPU
    u8Bus0 = u8CpuBus0[u8Cpu];

    // Next check that the bus numbers are valid
    // CPUBUSNO_VALID register - Above registers valid? - B(0) D5 F0 offset
    // D4h
    ret = peci_RdPCIConfig(u8Cpu, u8Bus0, PECI_PCI_CPUBUSNO_DEV,
                           PECI_PCI_CPUBUSNO_FUNC, PECI_PCI_CPUBUSNO_VALID,
                           u8Reg, &cc);
    if (ret != PECI_CC_SUCCESS)
    {
        return ret;
    }
    // BIOS will set bit 31 of CPUBUSNO_VALID when the bus numbers are valid
    if ((u8Reg[3] & 0x80) == 0)
    {
        return PECI_CC_HW_ERR;
    }

    // Bus numbers are valid so read the correct offset for the requested
    // bus CPUBUSNO register - CPU Internal Bus Numbers [3:0] - B(0) D5 F0
    // offset CCh CPUBUSNO_1 register - CPU Internal Bus Numbers [5:4] -
    // B(0) D5 F0 offset D0h
    u8Offset = u8Bus <= 3 ? PECI_PCI_CPUBUSNO : PECI_PCI_CPUBUSNO_1;
    ret = peci_RdPCIConfig(u8Cpu, u8Bus0, PECI_PCI_CPUBUSNO_DEV,
                           PECI_PCI_CPUBUSNO_FUNC, u8Offset, u8Reg, &cc);
    if (ret != PECI_CC_SUCCESS)
    {
        return ret;
    }

    // Now return the bus value for the requested bus
    *pu8BusValue = u8Reg[u8Bus % 4];

    // Unused bus numbers are set to zero which is only valid for bus 0
    // so, return an error for any other bus set to zero
    if (*pu8BusValue == 0 && u8Bus != 0)
    {
        return PECI_CC_CPU_NOT_PRESENT;
    }

    return PECI_CC_SUCCESS;
}

/*-------------------------------------------------------------------------
 * This function checks the CPU PECI interface
 *------------------------------------------------------------------------*/
EPECIStatus peci_Ping(uint8_t target)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_Ping_seq(target, peci_fd);

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential Ping with the provided
 * peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_Ping_seq(uint8_t target, int peci_fd)
{
    EPECIStatus ret = PECI_CC_SUCCESS;
    struct peci_ping_msg cmd = {0};

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    ret = HW_peci_issue_cmd(PECI_IOC_PING, (char*)&cmd, peci_fd);

    return ret;
}

/*-------------------------------------------------------------------------
 * This function gets PECI device information
 *------------------------------------------------------------------------*/
EPECIStatus peci_GetDIB(uint8_t target, uint64_t* dib)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (dib == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_GetDIB_seq(target, dib, peci_fd);

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential GetDIB with the provided
 * peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_GetDIB_seq(uint8_t target, uint64_t* dib, int peci_fd)
{
    struct peci_get_dib_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;
    cmd.addr = target;

    if (dib == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    ret = HW_peci_issue_cmd(PECI_IOC_GET_DIB, (char*)&cmd, peci_fd);

    if (ret == PECI_CC_SUCCESS)
    {
        *dib = cmd.dib;
    }

    return ret;
}

/*-------------------------------------------------------------------------
 * This function get PECI Thermal temperature
 * Expressed in signed fixed point value of 1/64 degrees celsius
 *------------------------------------------------------------------------*/
EPECIStatus peci_GetTemp(uint8_t target, int16_t* temperature)
{
    int peci_fd = -1;
    struct peci_get_temp_msg cmd = {0};

    if (temperature == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }

    cmd.addr = target;

    EPECIStatus ret =
        HW_peci_issue_cmd(PECI_IOC_GET_TEMP, (char*)&cmd, peci_fd);

    if (ret == PECI_CC_SUCCESS)
    {
        *temperature = cmd.temp_raw;
    }

    peci_Close(peci_fd);

    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides read access to the package configuration
 * space within the processor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPkgConfig(uint8_t target, uint8_t u8Index, uint16_t u16Value,
                             uint8_t u8ReadLen, uint8_t* pPkgConfig,
                             uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdPkgConfig_dom(target, 0, u8Index, u16Value, u8ReadLen,
                                pPkgConfig, cc);
}

/*-------------------------------------------------------------------------
 * This function provides read access to the package configuration
 * space within the processor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPkgConfig_dom(uint8_t target, uint8_t domainId,
                                 uint8_t u8Index, uint16_t u16Value,
                                 uint8_t u8ReadLen, uint8_t* pPkgConfig,
                                 uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pPkgConfig == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_RdPkgConfig_seq_dom(target, domainId, u8Index, u16Value,
                                   u8ReadLen, pPkgConfig, peci_fd, cc);

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdPkgConfig with the provided
 * peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPkgConfig_seq(uint8_t target, uint8_t u8Index,
                                 uint16_t u16Value, uint8_t u8ReadLen,
                                 uint8_t* pPkgConfig, int peci_fd, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdPkgConfig_seq_dom(target, 0, u8Index, u16Value, u8ReadLen,
                                    pPkgConfig, peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdPkgConfig with the provided
 * peci file descriptor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPkgConfig_seq_dom(uint8_t target, uint8_t domainId,
                                     uint8_t u8Index, uint16_t u16Value,
                                     uint8_t u8ReadLen, uint8_t* pPkgConfig,
                                     int peci_fd, uint8_t* cc)
{
    struct peci_rd_pkg_cfg_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pPkgConfig == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the write length must be a byte, word, or dword
    if (u8ReadLen != 1 && u8ReadLen != 2 && u8ReadLen != 4)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The PECI buffer must be large enough to hold the requested data
    if (sizeof(cmd.pkg_config) < u8ReadLen)
    {
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.index = u8Index;  // RdPkgConfig index
    cmd.param = u16Value; // Config parameter value
    cmd.rx_len = u8ReadLen;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_RD_PKG_CFG, (char*)&cmd, peci_fd);
    *cc = cmd.cc;
    if (ret == PECI_CC_SUCCESS)
    {
        memcpy(pPkgConfig, cmd.pkg_config, u8ReadLen);
    }

    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides write access to the package configuration
 * space within the processor
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrPkgConfig(uint8_t target, uint8_t u8Index, uint16_t u16Param,
                             uint32_t u32Value, uint8_t u8WriteLen, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_WrPkgConfig_dom(target, 0, u8Index, u16Param, u32Value,
                                u8WriteLen, cc);
}

/*-------------------------------------------------------------------------
 * This function provides write access to the package configuration
 * space within the processor in the specified domain
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrPkgConfig_dom(uint8_t target, uint8_t domainId,
                                 uint8_t u8Index, uint16_t u16Param,
                                 uint32_t u32Value, uint8_t u8WriteLen,
                                 uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_WrPkgConfig_seq_dom(target, domainId, u8Index, u16Param,
                                   u32Value, u8WriteLen, peci_fd, cc);

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential WrPkgConfig with the provided
 * peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrPkgConfig_seq(uint8_t target, uint8_t u8Index,
                                 uint16_t u16Param, uint32_t u32Value,
                                 uint8_t u8WriteLen, int peci_fd, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_WrPkgConfig_seq_dom(target, 0, u8Index, u16Param, u32Value,
                                    u8WriteLen, peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function allows sequential WrPkgConfig with the provided
 * peci file descriptor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrPkgConfig_seq_dom(uint8_t target, uint8_t domainId,
                                     uint8_t u8Index, uint16_t u16Param,
                                     uint32_t u32Value, uint8_t u8WriteLen,
                                     int peci_fd, uint8_t* cc)
{
    struct peci_wr_pkg_cfg_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the write length must be a byte, word, or dword
    if ((u8WriteLen != 1) && (u8WriteLen != 2) && (u8WriteLen != 4))
    {
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.index = u8Index;  // RdPkgConfig index
    cmd.param = u16Param; // parameter value
    cmd.tx_len = u8WriteLen;
    cmd.value = u32Value;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_WR_PKG_CFG, (char*)&cmd, peci_fd);
    *cc = cmd.cc;

    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides read access to Model Specific Registers
 * defined in the processor doc.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdIAMSR(uint8_t target, uint8_t threadID, uint16_t MSRAddress,
                         uint64_t* u64MsrVal, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdIAMSR_dom(target, 0, threadID, MSRAddress, u64MsrVal, cc);
}

/*-------------------------------------------------------------------------
 * This function provides read access to Model Specific Registers
 * defined in the processor doc in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdIAMSR_dom(uint8_t target, uint8_t domainId, uint8_t threadID,
                             uint16_t MSRAddress, uint64_t* u64MsrVal,
                             uint8_t* cc)
{
    int peci_fd = -1;
    struct peci_rd_ia_msr_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (u64MsrVal == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }

    cmd.addr = target;
    cmd.thread_id = threadID; // request byte for thread ID
    cmd.address = MSRAddress; // MSR Address
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_RD_IA_MSR, (char*)&cmd, peci_fd);
    *cc = cmd.cc;
    if (ret == PECI_CC_SUCCESS)
    {
        *u64MsrVal = cmd.value;
    }

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides read access to the PCI configuration space at
 * the requested PCI configuration address.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPCIConfig(uint8_t target, uint8_t u8Bus, uint8_t u8Device,
                             uint8_t u8Fcn, uint16_t u16Reg, uint8_t* pPCIData,
                             uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdPCIConfig_dom(target, 0, u8Bus, u8Device, u8Fcn, u16Reg,
                                pPCIData, cc);
}

/*-------------------------------------------------------------------------
 * This function provides read access to the PCI configuration space at
 * the requested PCI configuration address in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPCIConfig_dom(uint8_t target, uint8_t domainId,
                                 uint8_t u8Bus, uint8_t u8Device, uint8_t u8Fcn,
                                 uint16_t u16Reg, uint8_t* pPCIData,
                                 uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pPCIData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_RdPCIConfig_seq_dom(target, domainId, u8Bus, u8Device, u8Fcn,
                                   u16Reg, pPCIData, peci_fd, cc);

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdPCIConfig with the provided
 * peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPCIConfig_seq(uint8_t target, uint8_t u8Bus,
                                 uint8_t u8Device, uint8_t u8Fcn,
                                 uint16_t u16Reg, uint8_t* pPCIData,
                                 int peci_fd, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdPCIConfig_seq_dom(target, 0, u8Bus, u8Device, u8Fcn, u16Reg,
                                    pPCIData, peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdPCIConfig with the provided
 * peci file descriptor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPCIConfig_seq_dom(uint8_t target, uint8_t domainId,
                                     uint8_t u8Bus, uint8_t u8Device,
                                     uint8_t u8Fcn, uint16_t u16Reg,
                                     uint8_t* pPCIData, int peci_fd,
                                     uint8_t* cc)
{
    struct peci_rd_pci_cfg_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pPCIData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The PECI buffer must be large enough to hold the PCI data
    if (sizeof(cmd.pci_config) < 4)
    {
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.bus = u8Bus;
    cmd.device = u8Device;
    cmd.function = u8Fcn;
    cmd.reg = u16Reg;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_RD_PCI_CFG, (char*)&cmd, peci_fd);
    *cc = cmd.cc;

    if (ret == PECI_CC_SUCCESS)
    {
        memcpy(pPCIData, cmd.pci_config, 4);
    }

    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides read access to the local PCI configuration space
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPCIConfigLocal(uint8_t target, uint8_t u8Bus,
                                  uint8_t u8Device, uint8_t u8Fcn,
                                  uint16_t u16Reg, uint8_t u8ReadLen,
                                  uint8_t* pPCIReg, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdPCIConfigLocal_dom(target, 0, u8Bus, u8Device, u8Fcn, u16Reg,
                                     u8ReadLen, pPCIReg, cc);
}

/*-------------------------------------------------------------------------
 * This function provides read access to the local PCI configuration space in
 * the specified domain
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPCIConfigLocal_dom(uint8_t target, uint8_t domainId,
                                      uint8_t u8Bus, uint8_t u8Device,
                                      uint8_t u8Fcn, uint16_t u16Reg,
                                      uint8_t u8ReadLen, uint8_t* pPCIReg,
                                      uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pPCIReg == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret =
        peci_RdPCIConfigLocal_seq_dom(target, domainId, u8Bus, u8Device, u8Fcn,
                                      u16Reg, u8ReadLen, pPCIReg, peci_fd, cc);

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdPCIConfigLocal with the provided
 * peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPCIConfigLocal_seq(uint8_t target, uint8_t u8Bus,
                                      uint8_t u8Device, uint8_t u8Fcn,
                                      uint16_t u16Reg, uint8_t u8ReadLen,
                                      uint8_t* pPCIReg, int peci_fd,
                                      uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdPCIConfigLocal_seq_dom(target, 0, u8Bus, u8Device, u8Fcn,
                                         u16Reg, u8ReadLen, pPCIReg, peci_fd,
                                         cc);
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdPCIConfigLocal with the provided
 * peci file descriptor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdPCIConfigLocal_seq_dom(uint8_t target, uint8_t domainId,
                                          uint8_t u8Bus, uint8_t u8Device,
                                          uint8_t u8Fcn, uint16_t u16Reg,
                                          uint8_t u8ReadLen, uint8_t* pPCIReg,
                                          int peci_fd, uint8_t* cc)
{
    struct peci_rd_pci_cfg_local_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pPCIReg == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the read length must be a byte, word, or dword
    if (u8ReadLen != 1 && u8ReadLen != 2 && u8ReadLen != 4)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The PECI buffer must be large enough to hold the requested data
    if (sizeof(cmd.pci_config) < u8ReadLen)
    {
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.bus = u8Bus;
    cmd.device = u8Device;
    cmd.function = u8Fcn;
    cmd.reg = u16Reg;
    cmd.rx_len = u8ReadLen;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_RD_PCI_CFG_LOCAL, (char*)&cmd, peci_fd);
    *cc = cmd.cc;

    if (ret == PECI_CC_SUCCESS)
    {
        memcpy(pPCIReg, cmd.pci_config, u8ReadLen);
    }

    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides write access to the local PCI configuration space
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrPCIConfigLocal(uint8_t target, uint8_t u8Bus,
                                  uint8_t u8Device, uint8_t u8Fcn,
                                  uint16_t u16Reg, uint8_t DataLen,
                                  uint32_t DataVal, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_WrPCIConfigLocal_dom(target, 0, u8Bus, u8Device, u8Fcn, u16Reg,
                                     DataLen, DataVal, cc);
}

/*-------------------------------------------------------------------------
 * This function provides write access to the local PCI configuration space in
 * the specified domain
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrPCIConfigLocal_dom(uint8_t target, uint8_t domainId,
                                      uint8_t u8Bus, uint8_t u8Device,
                                      uint8_t u8Fcn, uint16_t u16Reg,
                                      uint8_t DataLen, uint32_t DataVal,
                                      uint8_t* cc)
{
    int peci_fd = -1;
    struct peci_wr_pci_cfg_local_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }

    // Per the PECI spec, the write length must be a byte, word, or dword
    if (DataLen != 1 && DataLen != 2 && DataLen != 4)
    {
        peci_Close(peci_fd);
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.bus = u8Bus;
    cmd.device = u8Device;
    cmd.function = u8Fcn;
    cmd.reg = u16Reg;
    cmd.tx_len = DataLen;
    cmd.value = DataVal;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_WR_PCI_CFG_LOCAL, (char*)&cmd, peci_fd);
    *cc = cmd.cc;

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This internal function is the common interface for RdEndPointConfig to PCI in
 * the specified domain
 *------------------------------------------------------------------------*/
static EPECIStatus peci_RdEndPointConfigPciCommon_dom(
    uint8_t target, uint8_t domainId, uint8_t u8MsgType, uint8_t u8Seg,
    uint8_t u8Bus, uint8_t u8Device, uint8_t u8Fcn, uint16_t u16Reg,
    uint8_t u8ReadLen, uint8_t* pPCIData, int peci_fd, uint8_t* cc)
{
    struct peci_rd_end_pt_cfg_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pPCIData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The PECI buffer must be large enough to hold the requested data
    if (sizeof(cmd.data) < u8ReadLen)
    {
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.msg_type = u8MsgType;
    cmd.params.pci_cfg.seg = u8Seg;
    cmd.params.pci_cfg.bus = u8Bus;
    cmd.params.pci_cfg.device = u8Device;
    cmd.params.pci_cfg.function = u8Fcn;
    cmd.params.pci_cfg.reg = u16Reg;
    cmd.rx_len = u8ReadLen;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_RD_END_PT_CFG, (char*)&cmd, peci_fd);
    *cc = cmd.cc;

    if (ret == PECI_CC_SUCCESS)
    {
        memcpy(pPCIData, cmd.data, u8ReadLen);
    }
    else
    {
        ret = PECI_CC_DRIVER_ERR;
    }

    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides read access to the PCI configuration space at
 * the requested PCI configuration address.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigPci(uint8_t target, uint8_t u8Seg,
                                     uint8_t u8Bus, uint8_t u8Device,
                                     uint8_t u8Fcn, uint16_t u16Reg,
                                     uint8_t u8ReadLen, uint8_t* pPCIData,
                                     uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdEndPointConfigPci_dom(target, 0, u8Seg, u8Bus, u8Device,
                                        u8Fcn, u16Reg, u8ReadLen, pPCIData, cc);
}

/*-------------------------------------------------------------------------
 * This function provides read access to the PCI configuration space at
 * the requested PCI configuration address in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigPci_dom(uint8_t target, uint8_t domainId,
                                         uint8_t u8Seg, uint8_t u8Bus,
                                         uint8_t u8Device, uint8_t u8Fcn,
                                         uint16_t u16Reg, uint8_t u8ReadLen,
                                         uint8_t* pPCIData, uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pPCIData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_RdEndPointConfigPci_seq_dom(target, domainId, u8Seg, u8Bus,
                                           u8Device, u8Fcn, u16Reg, u8ReadLen,
                                           pPCIData, peci_fd, cc);
    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdEndPointConfig to PCI with the provided
 * peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigPci_seq(uint8_t target, uint8_t u8Seg,
                                         uint8_t u8Bus, uint8_t u8Device,
                                         uint8_t u8Fcn, uint16_t u16Reg,
                                         uint8_t u8ReadLen, uint8_t* pPCIData,
                                         int peci_fd, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdEndPointConfigPci_seq_dom(target, 0, u8Seg, u8Bus, u8Device,
                                            u8Fcn, u16Reg, u8ReadLen, pPCIData,
                                            peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdEndPointConfig to PCI with the provided
 * peci file descriptor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigPci_seq_dom(uint8_t target, uint8_t domainId,
                                             uint8_t u8Seg, uint8_t u8Bus,
                                             uint8_t u8Device, uint8_t u8Fcn,
                                             uint16_t u16Reg, uint8_t u8ReadLen,
                                             uint8_t* pPCIData, int peci_fd,
                                             uint8_t* cc)
{
    if (pPCIData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the read length must be a byte, word, or dword
    if (u8ReadLen != 1 && u8ReadLen != 2 && u8ReadLen != 4)
    {
        return PECI_CC_INVALID_REQ;
    }

    return peci_RdEndPointConfigPciCommon_dom(
        target, domainId, PECI_ENDPTCFG_TYPE_PCI, u8Seg, u8Bus, u8Device, u8Fcn,
        u16Reg, u8ReadLen, pPCIData, peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function provides read access to the Local PCI configuration space at
 * the requested PCI configuration address.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigPciLocal(uint8_t target, uint8_t u8Seg,
                                          uint8_t u8Bus, uint8_t u8Device,
                                          uint8_t u8Fcn, uint16_t u16Reg,
                                          uint8_t u8ReadLen, uint8_t* pPCIData,
                                          uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdEndPointConfigPciLocal_dom(target, 0, u8Seg, u8Bus, u8Device,
                                             u8Fcn, u16Reg, u8ReadLen, pPCIData,
                                             cc);
}

/*-------------------------------------------------------------------------
 * This function provides read access to the Local PCI configuration space at
 * the requested PCI configuration address in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigPciLocal_dom(uint8_t target, uint8_t domainId,
                                              uint8_t u8Seg, uint8_t u8Bus,
                                              uint8_t u8Device, uint8_t u8Fcn,
                                              uint16_t u16Reg,
                                              uint8_t u8ReadLen,
                                              uint8_t* pPCIData, uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pPCIData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_RdEndPointConfigPciLocal_seq_dom(
        target, domainId, u8Seg, u8Bus, u8Device, u8Fcn, u16Reg, u8ReadLen,
        pPCIData, peci_fd, cc);
    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdEndPointConfig to PCI Local with the
 * provided peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigPciLocal_seq(uint8_t target, uint8_t u8Seg,
                                              uint8_t u8Bus, uint8_t u8Device,
                                              uint8_t u8Fcn, uint16_t u16Reg,
                                              uint8_t u8ReadLen,
                                              uint8_t* pPCIData, int peci_fd,
                                              uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdEndPointConfigPciLocal_seq_dom(
        target, 0, u8Seg, u8Bus, u8Device, u8Fcn, u16Reg, u8ReadLen, pPCIData,
        peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdEndPointConfig to PCI Local with the
 * provided peci file descriptor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigPciLocal_seq_dom(
    uint8_t target, uint8_t domainId, uint8_t u8Seg, uint8_t u8Bus,
    uint8_t u8Device, uint8_t u8Fcn, uint16_t u16Reg, uint8_t u8ReadLen,
    uint8_t* pPCIData, int peci_fd, uint8_t* cc)
{
    if (pPCIData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the read length must be a byte, word, or dword
    if (u8ReadLen != 1 && u8ReadLen != 2 && u8ReadLen != 4)
    {
        return PECI_CC_INVALID_REQ;
    }

    return peci_RdEndPointConfigPciCommon_dom(
        target, domainId, PECI_ENDPTCFG_TYPE_LOCAL_PCI, u8Seg, u8Bus, u8Device,
        u8Fcn, u16Reg, u8ReadLen, pPCIData, peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function provides read access to PCI MMIO space at
 * the requested PCI configuration address.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigMmio(uint8_t target, uint8_t u8Seg,
                                      uint8_t u8Bus, uint8_t u8Device,
                                      uint8_t u8Fcn, uint8_t u8Bar,
                                      uint8_t u8AddrType, uint64_t u64Offset,
                                      uint8_t u8ReadLen, uint8_t* pMmioData,
                                      uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdEndPointConfigMmio_dom(target, 0, u8Seg, u8Bus, u8Device,
                                         u8Fcn, u8Bar, u8AddrType, u64Offset,
                                         u8ReadLen, pMmioData, cc);
}

/*-------------------------------------------------------------------------
 * This function provides read access to PCI MMIO space at
 * the requested PCI configuration address in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigMmio_dom(uint8_t target, uint8_t domainId,
                                          uint8_t u8Seg, uint8_t u8Bus,
                                          uint8_t u8Device, uint8_t u8Fcn,
                                          uint8_t u8Bar, uint8_t u8AddrType,
                                          uint64_t u64Offset, uint8_t u8ReadLen,
                                          uint8_t* pMmioData, uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pMmioData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_RdEndPointConfigMmio_seq_dom(
        target, domainId, u8Seg, u8Bus, u8Device, u8Fcn, u8Bar, u8AddrType,
        u64Offset, u8ReadLen, pMmioData, peci_fd, cc);
    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdEndPointConfig to PCI MMIO with the
 * provided peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigMmio_seq(
    uint8_t target, uint8_t u8Seg, uint8_t u8Bus, uint8_t u8Device,
    uint8_t u8Fcn, uint8_t u8Bar, uint8_t u8AddrType, uint64_t u64Offset,
    uint8_t u8ReadLen, uint8_t* pMmioData, int peci_fd, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_RdEndPointConfigMmio_seq_dom(
        target, 0, u8Seg, u8Bus, u8Device, u8Fcn, u8Bar, u8AddrType, u64Offset,
        u8ReadLen, pMmioData, peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function allows sequential RdEndPointConfig to PCI MMIO with the
 * provided peci file descriptor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_RdEndPointConfigMmio_seq_dom(
    uint8_t target, uint8_t domainId, uint8_t u8Seg, uint8_t u8Bus,
    uint8_t u8Device, uint8_t u8Fcn, uint8_t u8Bar, uint8_t u8AddrType,
    uint64_t u64Offset, uint8_t u8ReadLen, uint8_t* pMmioData, int peci_fd,
    uint8_t* cc)
{
    struct peci_rd_end_pt_cfg_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pMmioData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the read length must be a byte, word, dword, or qword
    if (u8ReadLen != 1 && u8ReadLen != 2 && u8ReadLen != 4 && u8ReadLen != 8)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The PECI buffer must be large enough to hold the requested data
    if (sizeof(cmd.data) < u8ReadLen)
    {
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.msg_type = PECI_ENDPTCFG_TYPE_MMIO;
    cmd.params.mmio.seg = u8Seg;
    cmd.params.mmio.bus = u8Bus;
    cmd.params.mmio.device = u8Device;
    cmd.params.mmio.function = u8Fcn;
    cmd.params.mmio.bar = u8Bar;
    cmd.params.mmio.addr_type = u8AddrType;
    cmd.params.mmio.offset = u64Offset;
    cmd.rx_len = u8ReadLen;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_RD_END_PT_CFG, (char*)&cmd, peci_fd);
    *cc = cmd.cc;

    if (ret == PECI_CC_SUCCESS)
    {
        memcpy(pMmioData, cmd.data, u8ReadLen);
    }
    else
    {
        ret = PECI_CC_DRIVER_ERR;
    }

    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential peci_WrEndPointConfig to PCI EndPoint with
 * the provided peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointConfig_seq(uint8_t target, uint8_t u8MsgType,
                                      uint8_t u8Seg, uint8_t u8Bus,
                                      uint8_t u8Device, uint8_t u8Fcn,
                                      uint16_t u16Reg, uint8_t DataLen,
                                      uint32_t DataVal, int peci_fd,
                                      uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_WrEndPointConfig_seq_dom(target, 0, u8MsgType, u8Seg, u8Bus,
                                         u8Device, u8Fcn, u16Reg, DataLen,
                                         DataVal, peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function allows sequential peci_WrEndPointConfig to PCI EndPoint with
 * the provided peci file descriptor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointConfig_seq_dom(uint8_t target, uint8_t domainId,
                                          uint8_t u8MsgType, uint8_t u8Seg,
                                          uint8_t u8Bus, uint8_t u8Device,
                                          uint8_t u8Fcn, uint16_t u16Reg,
                                          uint8_t DataLen, uint32_t DataVal,
                                          int peci_fd, uint8_t* cc)
{
    struct peci_wr_end_pt_cfg_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the write length must be a byte, word, or dword
    if (DataLen != 1 && DataLen != 2 && DataLen != 4)
    {
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.msg_type = u8MsgType;
    cmd.params.pci_cfg.seg = u8Seg;
    cmd.params.pci_cfg.bus = u8Bus;
    cmd.params.pci_cfg.device = u8Device;
    cmd.params.pci_cfg.function = u8Fcn;
    cmd.params.pci_cfg.reg = u16Reg;
    cmd.tx_len = DataLen;
    cmd.value = DataVal;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_WR_END_PT_CFG, (char*)&cmd, peci_fd);
    *cc = cmd.cc;

    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides write access to the EP local PCI configuration space
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointPCIConfigLocal(uint8_t target, uint8_t u8Seg,
                                          uint8_t u8Bus, uint8_t u8Device,
                                          uint8_t u8Fcn, uint16_t u16Reg,
                                          uint8_t DataLen, uint32_t DataVal,
                                          uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_WrEndPointPCIConfigLocal_dom(
        target, 0, u8Seg, u8Bus, u8Device, u8Fcn, u16Reg, DataLen, DataVal, cc);
}

/*-------------------------------------------------------------------------
 * This function provides write access to the EP local PCI configuration space
 * in the specified domain
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointPCIConfigLocal_dom(uint8_t target, uint8_t domainId,
                                              uint8_t u8Seg, uint8_t u8Bus,
                                              uint8_t u8Device, uint8_t u8Fcn,
                                              uint16_t u16Reg, uint8_t DataLen,
                                              uint32_t DataVal, uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }

    ret = peci_WrEndPointConfig_seq_dom(
        target, domainId, PECI_ENDPTCFG_TYPE_LOCAL_PCI, u8Seg, u8Bus, u8Device,
        u8Fcn, u16Reg, DataLen, DataVal, peci_fd, cc);
    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides write access to the EP local PCI configuration space
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointPCIConfig(uint8_t target, uint8_t u8Seg,
                                     uint8_t u8Bus, uint8_t u8Device,
                                     uint8_t u8Fcn, uint16_t u16Reg,
                                     uint8_t DataLen, uint32_t DataVal,
                                     uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_WrEndPointPCIConfig_dom(target, 0, u8Seg, u8Bus, u8Device,
                                        u8Fcn, u16Reg, DataLen, DataVal, cc);
}

/*-------------------------------------------------------------------------
 * This function provides write access to the EP local PCI configuration space
 * in the specified domain
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointPCIConfig_dom(uint8_t target, uint8_t domainId,
                                         uint8_t u8Seg, uint8_t u8Bus,
                                         uint8_t u8Device, uint8_t u8Fcn,
                                         uint16_t u16Reg, uint8_t DataLen,
                                         uint32_t DataVal, uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_WrEndPointConfig_seq_dom(
        target, domainId, PECI_ENDPTCFG_TYPE_PCI, u8Seg, u8Bus, u8Device, u8Fcn,
        u16Reg, DataLen, DataVal, peci_fd, cc);
    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides write access to PCI MMIO space at
 * the requested PCI configuration address.
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointConfigMmio(uint8_t target, uint8_t u8Seg,
                                      uint8_t u8Bus, uint8_t u8Device,
                                      uint8_t u8Fcn, uint8_t u8Bar,
                                      uint8_t u8AddrType, uint64_t u64Offset,
                                      uint8_t u8DataLen, uint64_t u64DataVal,
                                      uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_WrEndPointConfigMmio_dom(target, 0, u8Seg, u8Bus, u8Device,
                                         u8Fcn, u8Bar, u8AddrType, u64Offset,
                                         u8DataLen, u64DataVal, cc);
}

/*-------------------------------------------------------------------------
 * This function provides write access to PCI MMIO space at
 * the requested PCI configuration address in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointConfigMmio_dom(uint8_t target, uint8_t domainId,
                                          uint8_t u8Seg, uint8_t u8Bus,
                                          uint8_t u8Device, uint8_t u8Fcn,
                                          uint8_t u8Bar, uint8_t u8AddrType,
                                          uint64_t u64Offset, uint8_t u8DataLen,
                                          uint64_t u64DataVal, uint8_t* cc)
{
    int peci_fd = -1;
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }
    ret = peci_WrEndPointConfigMmio_seq_dom(
        target, domainId, u8Seg, u8Bus, u8Device, u8Fcn, u8Bar, u8AddrType,
        u64Offset, u8DataLen, u64DataVal, peci_fd, cc);
    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function allows sequential WrEndPointConfig to PCI MMIO with the
 * provided peci file descriptor.
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointConfigMmio_seq(
    uint8_t target, uint8_t u8Seg, uint8_t u8Bus, uint8_t u8Device,
    uint8_t u8Fcn, uint8_t u8Bar, uint8_t u8AddrType, uint64_t u64Offset,
    uint8_t u8DataLen, uint64_t u64DataVal, int peci_fd, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_WrEndPointConfigMmio_seq_dom(
        target, 0, u8Seg, u8Bus, u8Device, u8Fcn, u8Bar, u8AddrType, u64Offset,
        u8DataLen, u64DataVal, peci_fd, cc);
}

/*-------------------------------------------------------------------------
 * This function allows sequential WrEndPointConfig to PCI MMIO with the
 * provided peci file descriptor in the specified domain.
 *------------------------------------------------------------------------*/
EPECIStatus peci_WrEndPointConfigMmio_seq_dom(
    uint8_t target, uint8_t domainId, uint8_t u8Seg, uint8_t u8Bus,
    uint8_t u8Device, uint8_t u8Fcn, uint8_t u8Bar, uint8_t u8AddrType,
    uint64_t u64Offset, uint8_t u8DataLen, uint64_t u64DataVal, int peci_fd,
    uint8_t* cc)
{
    struct peci_wr_end_pt_cfg_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the read length must be a byte, word, dword, or qword
    if (u8DataLen != 1 && u8DataLen != 2 && u8DataLen != 4 && u8DataLen != 8)
    {
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.msg_type = PECI_ENDPTCFG_TYPE_MMIO;
    cmd.params.mmio.seg = u8Seg;
    cmd.params.mmio.bus = u8Bus;
    cmd.params.mmio.device = u8Device;
    cmd.params.mmio.function = u8Fcn;
    cmd.params.mmio.bar = u8Bar;
    cmd.params.mmio.addr_type = u8AddrType;
    cmd.params.mmio.offset = u64Offset;
    cmd.tx_len = u8DataLen;
    cmd.value = u64DataVal;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_WR_END_PT_CFG, (char*)&cmd, peci_fd);
    *cc = cmd.cc;

    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides crashdump discovery data over PECI
 *------------------------------------------------------------------------*/
EPECIStatus peci_CrashDump_Discovery(uint8_t target, uint8_t subopcode,
                                     uint8_t param0, uint16_t param1,
                                     uint8_t param2, uint8_t u8ReadLen,
                                     uint8_t* pData, uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_CrashDump_Discovery_dom(target, 0, subopcode, param0, param1,
                                        param2, u8ReadLen, pData, cc);
}

/*-------------------------------------------------------------------------
 * This function provides crashdump discovery data over PECI in the specified
 * domain
 *------------------------------------------------------------------------*/
EPECIStatus peci_CrashDump_Discovery_dom(uint8_t target, uint8_t domainId,
                                         uint8_t subopcode, uint8_t param0,
                                         uint16_t param1, uint8_t param2,
                                         uint8_t u8ReadLen, uint8_t* pData,
                                         uint8_t* cc)
{
    int peci_fd = -1;
    struct peci_crashdump_disc_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the read length must be a byte, word, or qword
    if (u8ReadLen != 1 && u8ReadLen != 2 && u8ReadLen != 8)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The PECI buffer must be large enough to hold the requested data
    if (sizeof(cmd.data) < u8ReadLen)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }

    cmd.addr = target;
    cmd.subopcode = subopcode;
    cmd.param0 = param0;
    cmd.param1 = param1;
    cmd.param2 = param2;
    cmd.rx_len = u8ReadLen;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_CRASHDUMP_DISC, (char*)&cmd, peci_fd);
    *cc = cmd.cc;
    if (ret == PECI_CC_SUCCESS)
    {
        memcpy(pData, cmd.data, u8ReadLen);
    }
    else
    {
        ret = PECI_CC_DRIVER_ERR;
    }

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function provides crashdump GetFrame data over PECI
 *------------------------------------------------------------------------*/
EPECIStatus peci_CrashDump_GetFrame(uint8_t target, uint16_t param0,
                                    uint16_t param1, uint16_t param2,
                                    uint8_t u8ReadLen, uint8_t* pData,
                                    uint8_t* cc)
{
    //  Default to domain ID 0
    return peci_CrashDump_GetFrame_dom(target, 0, param0, param1, param2,
                                       u8ReadLen, pData, cc);
}

/*-------------------------------------------------------------------------
 * This function provides crashdump GetFrame data over PECI in the specified
 * domain
 *------------------------------------------------------------------------*/
EPECIStatus peci_CrashDump_GetFrame_dom(uint8_t target, uint8_t domainId,
                                        uint16_t param0, uint16_t param1,
                                        uint16_t param2, uint8_t u8ReadLen,
                                        uint8_t* pData, uint8_t* cc)
{
    int peci_fd = -1;
    struct peci_crashdump_get_frame_msg cmd = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (pData == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    // Per the PECI spec, the read length must be a qword or dqword
    if (u8ReadLen != 8 && u8ReadLen != 16)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The PECI buffer must be large enough to hold the requested data
    if (sizeof(cmd.data) < u8ReadLen)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }

    cmd.addr = target;
    cmd.param0 = param0;
    cmd.param1 = param1;
    cmd.param2 = param2;
    cmd.rx_len = u8ReadLen;
    cmd.domain_id = domainId;

    ret = HW_peci_issue_cmd(PECI_IOC_CRASHDUMP_GET_FRAME, (char*)&cmd, peci_fd);
    *cc = cmd.cc;
    if (ret == PECI_CC_SUCCESS)
    {
        memcpy(pData, cmd.data, u8ReadLen);
    }
    else
    {
        ret = PECI_CC_DRIVER_ERR;
    }

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 *  This function provides raw PECI command access
 *------------------------------------------------------------------------*/
EPECIStatus peci_raw(uint8_t target, uint8_t u8ReadLen, const uint8_t* pRawCmd,
                     const uint32_t cmdSize, uint8_t* pRawResp,
                     uint32_t respSize)
{
    int peci_fd = -1;
    struct peci_xfer_msg cmd = {0};
    uint8_t u8TxBuf[PECI_BUFFER_SIZE] = {0};
    uint8_t u8RxBuf[PECI_BUFFER_SIZE] = {0};
    EPECIStatus ret = PECI_CC_SUCCESS;

    if (u8ReadLen && pRawResp == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The target address must be in the valid range
    if (target < MIN_CLIENT_ADDR || target > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Open(&peci_fd) != PECI_CC_SUCCESS)
    {
        return PECI_CC_DRIVER_ERR;
    }

    // Check for valid buffer sizes
    if (cmdSize > PECI_BUFFER_SIZE || respSize < u8ReadLen ||
        u8ReadLen >
            (PECI_BUFFER_SIZE - 1)) // response buffer is data + 1 status byte
    {
        peci_Close(peci_fd);
        return PECI_CC_INVALID_REQ;
    }

    cmd.addr = target;
    cmd.tx_len = (uint8_t)cmdSize;
    cmd.rx_len = u8ReadLen;

    memcpy(u8TxBuf, pRawCmd, cmdSize);

    cmd.tx_buf = u8TxBuf;
    cmd.rx_buf = u8RxBuf;
    ret = HW_peci_issue_cmd(PECI_IOC_XFER, (char*)&cmd, peci_fd);

    if (ret == PECI_CC_SUCCESS || ret == PECI_CC_TIMEOUT)
    {
        memcpy(pRawResp, u8RxBuf, u8ReadLen);
    }

    peci_Close(peci_fd);
    return ret;
}

/*-------------------------------------------------------------------------
 * This function returns the CPUID (Model and stepping) for the given PECI
 * client address
 *------------------------------------------------------------------------*/
EPECIStatus peci_GetCPUID(const uint8_t clientAddr, CPUModel* cpuModel,
                          uint8_t* stepping, uint8_t* cc)
{
    EPECIStatus ret = PECI_CC_SUCCESS;
    uint32_t cpuid = 0;

    if (cpuModel == NULL || stepping == NULL || cc == NULL)
    {
        return PECI_CC_INVALID_REQ;
    }

    // The client address must be in the valid range
    if (clientAddr < MIN_CLIENT_ADDR || clientAddr > MAX_CLIENT_ADDR)
    {
        return PECI_CC_INVALID_REQ;
    }

    if (peci_Ping(clientAddr) != PECI_CC_SUCCESS)
    {
        return PECI_CC_CPU_NOT_PRESENT;
    }

    ret =
        peci_RdPkgConfig(clientAddr, PECI_MBX_INDEX_CPU_ID, PECI_PKG_ID_CPU_ID,
                         sizeof(uint32_t), (uint8_t*)&cpuid, cc);

    // Separate out the model and stepping (bits 3:0) from the CPUID
    *cpuModel = cpuid & 0xFFFFFFF0;
    *stepping = (uint8_t)(cpuid & 0x0000000F);
    return ret;
}
