/*
 *  Copyright (c) 2017, The OpenThread Authors.
 *  All rights reserved.
 *
 *  Redistribution and use in source and binary forms, with or without
 *  modification, are permitted provided that the following conditions are met:
 *  1. Redistributions of source code must retain the above copyright
 *     notice, this list of conditions and the following disclaimer.
 *  2. Redistributions in binary form must reproduce the above copyright
 *     notice, this list of conditions and the following disclaimer in the
 *     documentation and/or other materials provided with the distribution.
 *  3. Neither the name of the copyright holder nor the
 *     names of its contributors may be used to endorse or promote products
 *     derived from this software without specific prior written permission.
 *
 *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
 *  AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 *  IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 *  ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
 *  LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
 *  CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
 *  SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
 *  INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
 *  CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 *  ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 *  POSSIBILITY OF SUCH DAMAGE.
 */

/**
 * @file
 *   This file implements the OpenThread platform abstraction for radio communication.
 *
 */

#include "openthread/types.h"

#include <utils/code_utils.h>
#include "openthread/platform/radio.h"
#include "platform-emsk.h"

#include "device/device_hal/inc/dev_gpio.h"
#include <string.h>

#include <stdio.h>
#define DBG(fmt, ...)   printf(fmt, ##__VA_ARGS__)

enum
{
    IEEE802154_MIN_LENGTH         = 5,
    IEEE802154_MAX_LENGTH         = 127,
    IEEE802154_ACK_LENGTH         = 5,

    IEEE802154_BROADCAST          = 0xffff,

    IEEE802154_FRAME_TYPE_ACK     = 2 << 0,
    IEEE802154_FRAME_TYPE_MACCMD  = 3 << 0,
    IEEE802154_FRAME_TYPE_MASK    = 7 << 0,

    IEEE802154_SECURITY_ENABLED   = 1 << 3,
    IEEE802154_FRAME_PENDING      = 1 << 4,
    IEEE802154_ACK_REQUEST        = 1 << 5,
    IEEE802154_PANID_COMPRESSION  = 1 << 6,

    IEEE802154_DST_ADDR_NONE      = 0 << 2,
    IEEE802154_DST_ADDR_SHORT     = 2 << 2,
    IEEE802154_DST_ADDR_EXT       = 3 << 2,
    IEEE802154_DST_ADDR_MASK      = 3 << 2,

    IEEE802154_SRC_ADDR_NONE      = 0 << 6,
    IEEE802154_SRC_ADDR_SHORT     = 2 << 6,
    IEEE802154_SRC_ADDR_EXT       = 3 << 6,
    IEEE802154_SRC_ADDR_MASK      = 3 << 6,

    IEEE802154_DSN_OFFSET         = 2,
    IEEE802154_DSTPAN_OFFSET      = 3,
    IEEE802154_DSTADDR_OFFSET     = 5,

    IEEE802154_SEC_LEVEL_MASK     = 7 << 0,

    IEEE802154_KEY_ID_MODE_0      = 0 << 3,
    IEEE802154_KEY_ID_MODE_1      = 1 << 3,
    IEEE802154_KEY_ID_MODE_2      = 2 << 3,
    IEEE802154_KEY_ID_MODE_3      = 3 << 3,
    IEEE802154_KEY_ID_MODE_MASK   = 3 << 3,

    IEEE802154_MACCMD_DATA_REQ    = 4
};

enum
{
    EMSK_RECEIVE_SENSITIVITY = -100,  // dBm
};

enum
{
    MRF24J40_RSSI_OFFSET = 90,
    MRF24J40_RSSI_SLOPE = 5
};

static void radioTransmitMessage(otInstance *aInstance);

static otRadioFrame sTransmitFrame;
static otRadioFrame sReceiveFrame;
static otRadioFrame sAckFrame;

static otError sTransmitError;
static otError sReceiveError;

static uint8_t sTransmitPsdu[IEEE802154_MAX_LENGTH];
static uint8_t sReceivePsdu[IEEE802154_MAX_LENGTH];
static uint8_t sAckPsdu[IEEE802154_MAX_LENGTH];

static otRadioState sState = OT_RADIO_STATE_DISABLED;
static bool sIsReceiverEnabled = false;

static volatile uint8_t Mrf24StatusTx = 0;
static volatile uint8_t Mrf24StatusRx = 0;
static volatile uint8_t Mrf24StatusSec = 0;

static DEV_SPI_PTR pmrf_spi_ptr;
static DEV_GPIO_PTR pmrf_gpio_ptr;
static void RadioIsr(void *ptr);

/* Variables for test */
static uint32_t numInterruptRev = 0;
static uint32_t numInterruptTrans = 0;
static uint32_t numRadioProcess = 0;

static inline bool isSecurityEnabled(const uint8_t *frame)
{
    return (frame[0] & IEEE802154_SECURITY_ENABLED) != 0;
}

static inline bool isAckRequested(const uint8_t *frame)
{
    return (frame[0] & IEEE802154_ACK_REQUEST) != 0;
}

static inline bool isPanIdCompressed(const uint8_t *frame)
{
    return (frame[0] & IEEE802154_PANID_COMPRESSION) != 0;
}

static inline uint8_t getHeadLength(const uint8_t *frame)
{
    uint8_t length = 0;
    /* Frame Control-2 + Sequence Number-1 */
    length += 2 + 1;

    /* Destination PAN + Address */
    switch (frame[1] & IEEE802154_DST_ADDR_MASK)
    {
    case IEEE802154_DST_ADDR_SHORT:
        length += sizeof(otPanId) + sizeof(otShortAddress);
        break;

    case IEEE802154_DST_ADDR_EXT:
        length += sizeof(otPanId) + sizeof(otExtAddress);
        break;

    default:
        length = 0;
        goto exit;
    }

    /* Source PAN + Address */
    switch (frame[1] & IEEE802154_SRC_ADDR_MASK)
    {
    case IEEE802154_SRC_ADDR_SHORT:
        if (!isPanIdCompressed(frame))
        {
            length += sizeof(otPanId);
        }

        length += sizeof(otShortAddress);
        break;

    case IEEE802154_SRC_ADDR_EXT:
        if (!isPanIdCompressed(frame))
        {
            length += sizeof(otPanId);
        }

        length += sizeof(otExtAddress);
        break;

    default:
        length = 0;
        goto exit;
    }

exit:
    return length;
}

void enableReceiver(void)
{
    if (!sIsReceiverEnabled)
    {
        mrf24j40_rxfifo_flush();
        /* add code to enable receiver (wakeup) */
        sIsReceiverEnabled = true;
    }
}

void disableReceiver(void)
{
    if (sIsReceiverEnabled)
    {
        mrf24j40_rxfifo_flush();
        /* add code to disable receiver (sleep) */
        sIsReceiverEnabled = false;
    }
}

void setChannel(uint8_t channel)
{
    mrf24j40_set_channel((int16_t)(channel - 11));
}

void otPlatRadioGetIeeeEui64(otInstance *aInstance, uint8_t *aIeeeEui64)
{
    (void)aInstance;
    /* should set it manually or preset it in memory */
    aIeeeEui64[0] = 0x00;
    aIeeeEui64[1] = 0x50;
    aIeeeEui64[2] = 0xC2;
    aIeeeEui64[3] = 0xFF;
    aIeeeEui64[4] = 0XFE;
    aIeeeEui64[5] = 0X1D;
    aIeeeEui64[6] = 0X30;
    aIeeeEui64[7] = 0x00;
}

void otPlatRadioSetPanId(otInstance *aInstance, uint16_t panid)
{
    (void)aInstance;
    uint8_t pan[2];

    pan[0] = (uint8_t)(panid & 0xFF);
    pan[1] = (uint8_t)(panid >> 8);
    mrf24j40_set_pan(pan);
}

void otPlatRadioSetExtendedAddress(otInstance *aInstance, uint8_t *address)
{
    (void)aInstance;
    mrf24j40_set_eui(address);
}

void otPlatRadioSetShortAddress(otInstance *aInstance, uint16_t address)
{
    (void)aInstance;
    uint8_t addr[2];

    addr[0] = (uint8_t)(address & 0xFF);
    addr[1] = (uint8_t)(address >> 8);
    mrf24j40_set_short_addr(addr);
}

void emskRadioInit(void)
{
    DEV_GPIO_BIT_ISR isr;
    DEV_GPIO_INT_CFG int_cfg;

    int32_t ercd;
    uint32_t temp;

    sTransmitFrame.mLength = 0;
    sTransmitFrame.mPsdu = sTransmitPsdu;
    sReceiveFrame.mLength = 0;
    sReceiveFrame.mPsdu = sReceivePsdu;
    sAckFrame.mLength = 0;
    sAckFrame.mPsdu = sAckPsdu;

    pmrf_spi_ptr = spi_get_dev(EMSK_PMRF_0_SPI_ID);
    ercd = pmrf_spi_ptr->spi_open(DEV_MASTER_MODE, EMSK_PMRF_0_SPIFREQ);

    if ((ercd != E_OK) && (ercd != E_OPNED))
    {
        DBG("PmodRF2 SPI open error\r\n");
    }

    pmrf_spi_ptr->spi_control(SPI_CMD_SET_CLK_MODE, CONV2VOID(EMSK_PMRF_0_SPICLKMODE));

    /*MRF24J40 wakepin:output, rstpin:output, INT_PIN:input, interrupt */
    pmrf_gpio_ptr = gpio_get_dev(EMSK_PMRF_0_GPIO_ID);
    ercd = pmrf_gpio_ptr->gpio_open(MRF24J40_WAKE_PIN | MRF24J40_RST_PIN);

    if ((ercd != E_OK) && (ercd != E_OPNED))
    {
        DBG("PmodRF2 CRTL port open error");
    }

    if (ercd == E_OPNED)
    {
        pmrf_gpio_ptr->gpio_control(GPIO_CMD_SET_BIT_DIR_OUTPUT, (void *)(MRF24J40_WAKE_PIN | MRF24J40_RST_PIN));
        pmrf_gpio_ptr->gpio_control(GPIO_CMD_SET_BIT_DIR_INPUT, (void *)MRF24J40_INT_PIN);
    }

    pmrf_gpio_ptr->gpio_control(GPIO_CMD_DIS_BIT_INT, (void *)MRF24J40_INT_PIN);

    temp = MRF24J40_INT_PIN;
    int_cfg.int_bit_mask = temp;
    int_cfg.int_bit_type = GPIO_INT_BITS_EDGE_TRIG(temp);
    int_cfg.int_bit_polarity = GPIO_INT_BITS_POL_FALL_EDGE(temp);
    int_cfg.int_bit_debounce = GPIO_INT_BITS_DIS_DEBOUNCE(temp);
    pmrf_gpio_ptr->gpio_control(GPIO_CMD_SET_BIT_INT_CFG, (void *)(&int_cfg));

    isr.int_bit_ofs = MRF24J40_INT_PIN_OFS;
    isr.int_bit_handler = RadioIsr;
    pmrf_gpio_ptr->gpio_control(GPIO_CMD_SET_BIT_ISR, (void *)(&isr));

    /* interrupt for mrf24j40 is enabled at the end of the init process */
    DBG("MRF24J40 Init Started\r\n");
    mrf24j40_initialize();
    DBG("MRF24J40 Init Finished\r\n");

    pmrf_gpio_ptr->gpio_control(GPIO_CMD_ENA_BIT_INT, (void *)MRF24J40_INT_PIN);

}

bool otPlatRadioIsEnabled(otInstance *aInstance)
{
    (void)aInstance;
    return (sState != OT_RADIO_STATE_DISABLED);
}

otError otPlatRadioEnable(otInstance *aInstance)
{
    if (!otPlatRadioIsEnabled(aInstance))
    {
        sState = OT_RADIO_STATE_SLEEP;
    }

    return OT_ERROR_NONE;
}

otError otPlatRadioDisable(otInstance *aInstance)
{
    if (otPlatRadioIsEnabled(aInstance))
    {
        sState = OT_RADIO_STATE_DISABLED;
    }

    return OT_ERROR_NONE;
}

otError otPlatRadioSleep(otInstance *aInstance)
{
    otError error = OT_ERROR_INVALID_STATE;
    (void)aInstance;

    if (sState == OT_RADIO_STATE_SLEEP || sState == OT_RADIO_STATE_RECEIVE)
    {
        error = OT_ERROR_NONE;
        sState = OT_RADIO_STATE_SLEEP;
        disableReceiver();
    }

    return error;
}

otError otPlatRadioReceive(otInstance *aInstance, uint8_t aChannel)
{
    otError error = OT_ERROR_INVALID_STATE;
    (void)aInstance;

    if (sState != OT_RADIO_STATE_DISABLED)
    {
        error = OT_ERROR_NONE;
        sState = OT_RADIO_STATE_RECEIVE;
        setChannel(aChannel);
        sReceiveFrame.mChannel = aChannel;
        enableReceiver();
    }

    return error;
}

otError otPlatRadioTransmit(otInstance *aInstance, otRadioFrame *aFrame)
{
    otError error = OT_ERROR_INVALID_STATE;
    (void)aInstance;
    (void)aFrame;

    if (sState == OT_RADIO_STATE_RECEIVE)
    {
        error = OT_ERROR_NONE;
        sState = OT_RADIO_STATE_TRANSMIT;
    }

    return error;

}

otRadioFrame *otPlatRadioGetTransmitBuffer(otInstance *aInstance)
{
    (void)aInstance;
    return &sTransmitFrame;
}

int8_t otPlatRadioGetRssi(otInstance *aInstance)
{
    (void)aInstance;
    return 0;
}

otRadioCaps otPlatRadioGetCaps(otInstance *aInstance)
{
    (void)aInstance;
    return OT_RADIO_CAPS_NONE;
}

bool otPlatRadioGetPromiscuous(otInstance *aInstance)
{
    (void)aInstance;
    return (bool)(mrf24j40_read_short_ctrl_reg(MRF24J40_RXMCR) & MRF24J40_PROMI);
}

// should be checked again with CC2538
void otPlatRadioSetPromiscuous(otInstance *aInstance, bool aEnable)
{
    (void)aInstance;
    mrf24j40_set_promiscuous(~aEnable);
}

void readFrame(void)
{

    /* readBuffer
     * 1 bit -- 5 to 127 bits -- 1 bit -- 1bit
     * Frame Length -- PSDU (Header + Data Payload + FCS) -- LQI -- RSSI
     */
    uint8_t readBuffer[MRF24J40_RXFIFO_SIZE];
    uint8_t readPlqi = 0;
    uint8_t readRssi = 0;

    uint16_t length;
    int16_t i;

    memset(readBuffer, 0, MRF24J40_RXFIFO_SIZE);

    otEXPECT_ACTION(sState == OT_RADIO_STATE_RECEIVE || sState == OT_RADIO_STATE_TRANSMIT, ;);
    otEXPECT_ACTION(Mrf24StatusRx, ;);

    if (Mrf24StatusRx == 1)
    {
        Mrf24StatusRx = 0;
    }

    if (Mrf24StatusSec == 1)
    {
        Mrf24StatusSec = 0;
    }

    /* Read length */
    length = (uint16_t)mrf24j40_rxpkt_intcb(readBuffer, &readPlqi, &readRssi);

    otEXPECT_ACTION(IEEE802154_MIN_LENGTH <= length && length <= IEEE802154_MAX_LENGTH, ;);

    /* Read PSDU */
    memcpy(sReceiveFrame.mPsdu, readBuffer, length - 2);

    sReceiveFrame.mPower = (int8_t)(readRssi / MRF24J40_RSSI_SLOPE) - MRF24J40_RSSI_OFFSET;
    sReceiveFrame.mLength = (uint8_t) length;
    sReceiveFrame.mLqi = readPlqi;

exit:
    return;

}

void radioTransmitMessage(otInstance *aInstance)
{
    (void)aInstance;
    uint8_t header_len = 0;

    sTransmitError = OT_ERROR_NONE;
    setChannel(sTransmitFrame.mChannel);

    uint8_t reg = mrf24j40_read_short_ctrl_reg(MRF24J40_TXNCON);

    header_len = getHeadLength(sTransmitFrame.mPsdu);

    if (isAckRequested(sTransmitFrame.mPsdu))
    {
        reg |= MRF24J40_TXNACKREQ;
    }
    else
    {
        reg &= ~(MRF24J40_TXNACKREQ);
    }

    if (isSecurityEnabled(sTransmitFrame.mPsdu))
    {
        reg |= MRF24J40_TXNSECEN;
    }
    else
    {
        reg &= ~(MRF24J40_TXNSECEN);
        mrf24j40_write_short_ctrl_reg(MRF24J40_TXNCON, mrf24j40_read_short_ctrl_reg(MRF24J40_TXNCON) & (~MRF24J40_TXNSECEN));
    }

    mrf24j40_txfifo_write(MRF24J40_TXNFIFO, sTransmitFrame.mPsdu, header_len, (sTransmitFrame.mLength - 2));

    mrf24j40_write_short_ctrl_reg(MRF24J40_TXNCON, reg | MRF24J40_TXNTRIG);

    int16_t tx_timeout = 500;
    Mrf24StatusTx = 0;

    while ((tx_timeout > 0) && (Mrf24StatusTx != 1))
    {
        mrf24j40_delay_ms(1);
        tx_timeout--;

        if (tx_timeout <= 0)
        {
            DBG("Radio Transmit Timeout!!!!!!!!!!!!\r\n");
        }
    }
}

void emskRadioProcess(otInstance *aInstance)
{
    numRadioProcess++;

    readFrame();
    uint8_t reg = mrf24j40_read_short_ctrl_reg(MRF24J40_TXSTAT);

    if (reg & MRF24J40_TXNSTAT)
    {
        DBG("TX MAC Timeout!!!!!!\r\n");

        if (reg & MRF24J40_CCAFAIL)
        {
            DBG("Channel busy!!!!!!\r\n");
        }
    }

    if ((sState == OT_RADIO_STATE_RECEIVE) && (sReceiveFrame.mLength > 0))
    {
        otPlatRadioReceiveDone(aInstance, &sReceiveFrame, sReceiveError);
    }

    if (sState == OT_RADIO_STATE_TRANSMIT)
    {
        radioTransmitMessage(aInstance);

        if (sTransmitError != OT_ERROR_NONE || (sTransmitFrame.mPsdu[0] & IEEE802154_ACK_REQUEST) == 0)
        {
            sState = OT_RADIO_STATE_RECEIVE;
            otPlatRadioTxDone(aInstance, &sTransmitFrame, NULL, sTransmitError);
        }
        else if (Mrf24StatusTx == 1)
        {
            Mrf24StatusTx = 0;
            sState = OT_RADIO_STATE_RECEIVE;
            otPlatRadioTxDone(aInstance, &sTransmitFrame, &sReceiveFrame, sTransmitError);
        }
    }

    sReceiveFrame.mLength = 0;

}

/**
 * \brief isr routine of mrf24j40
 * \param[in] ptr pointer transferred frome interrupt entry
 */
static void RadioIsr(void *ptr)
{
    uint8_t int_status = 0;

    int_status = pmrf_read_short_ctrl_reg(MRF24J40_INTSTAT);

    /* a frame is received */
    if (int_status & MRF24J40_RXIF)
    {
        numInterruptRev++;
        Mrf24StatusRx = 1;
    }

    /* a frame is transmitted */
    if (int_status & MRF24J40_TXNIF)
    {
        switch (mrf24j40_txpkt_intcb())
        {
        case MRF24J40_EBUSY:
            /* Channel busy */
            break;

        case MRF24J40_EIO:
            /* Channel idle */
            break;

        case 0:
            numInterruptTrans++;
            Mrf24StatusTx = 1;
            break;
        }
    }

    /* a frame with security key request is received */
    if (int_status & MRF24J40_SECIF)
    {
        Mrf24StatusSec = 1;
        mrf24j40_sec_intcb(false);
    }

}

/* CC2538 supports source address matching for low power consumption
   and this is not supported in MRF24J40 */
void otPlatRadioEnableSrcMatch(otInstance *aInstance, bool aEnable)
{
    (void)aInstance;
    (void)aEnable;
}

otError otPlatRadioAddSrcMatchShortEntry(otInstance *aInstance, const uint16_t aShortAddress)
{
    (void)aInstance;
    (void)aShortAddress;
    return OT_ERROR_NONE;
}

otError otPlatRadioAddSrcMatchExtEntry(otInstance *aInstance, const uint8_t *aExtAddress)
{
    (void)aInstance;
    (void)aExtAddress;
    return OT_ERROR_NONE;
}

otError otPlatRadioClearSrcMatchShortEntry(otInstance *aInstance, const uint16_t aShortAddress)
{
    (void)aInstance;
    (void)aShortAddress;
    return OT_ERROR_NONE;
}

otError otPlatRadioClearSrcMatchExtEntry(otInstance *aInstance, const uint8_t *aExtAddress)
{
    (void)aInstance;
    (void)aExtAddress;
    return OT_ERROR_NONE;
}

void otPlatRadioClearSrcMatchShortEntries(otInstance *aInstance)
{
    (void)aInstance;
}

void otPlatRadioClearSrcMatchExtEntries(otInstance *aInstance)
{
    (void)aInstance;
}

otError otPlatRadioEnergyScan(otInstance *aInstance, uint8_t aScanChannel, uint16_t aScanDuration)
{
    (void)aInstance;
    (void)aScanChannel;
    (void)aScanDuration;
    return OT_ERROR_NOT_IMPLEMENTED;
}

void otPlatRadioSetDefaultTxPower(otInstance *aInstance, int8_t aPower)
{
    // TODO: Create a proper implementation for this driver.
    (void)aInstance;
    (void)aPower;
}

int8_t otPlatRadioGetReceiveSensitivity(otInstance *aInstance)
{
    (void)aInstance;
    return EMSK_RECEIVE_SENSITIVITY;
}
