#include "sem.h"

#include "tz_debug.h"
#include "sec_apdu.h"

void getCPLC(p_rsp_t rsp) {
    uint8_t cn = 0;
    uint8_t isd_aid[] = {0xA0, 0x00, 0x00, 0x01, 0x51, 0x00, 0x00, 0x00};
    uint8_t data[MAX_RAPDU_DATA_SIZE] = {0,};
    secEse_7816_cpdu_t cpdu;
    secEse_7816_rpdu_t rpdu;

    LOGD("getCPLC start");

    if (ESESTATUS_SUCCESS != secEseOpen(&cn)) {
        LOGE("getCPLC channel open fail");
        rsp->ret = RET_ERR_GET_CPLC_FAIL;
        goto error;
    }

    memset(&rpdu, 0, sizeof(secEse_7816_rpdu_t));
    rpdu.pdata = data;
    if (cn < 1 || cn > 3 || ESESTATUS_SUCCESS != secEseSelect(cn, isd_aid, 0, 8, &rpdu) ) {
        LOGE("getCPLC failed to SELECT ISD");
        rsp->ret = RET_ERR_GET_CPLC_FAIL;
        goto error;
    }

    memset(&cpdu, 0, sizeof(secEse_7816_cpdu_t));
    memset(&rpdu, 0, sizeof(secEse_7816_rpdu_t));
    memset(data, 0, MAX_RAPDU_DATA_SIZE);
    rpdu.pdata = data;

    cpdu.cla = 0x80;
    cpdu.ins = 0xCA;
    cpdu.p1 = 0x9F;
    cpdu.p2 = 0x7F;
    cpdu.le_type = 1;

    if (ESESTATUS_SUCCESS != secEseTransmit(cn, &cpdu, &rpdu)) {
        LOGE("getCPLC failed to send APDU GET CPLC");
        rsp->ret = RET_ERR_GET_CPLC_FAIL;
        goto error;
    }

    if(rpdu.sw1 == 0x90 && rpdu.sw2 == 0x00 && rpdu.len > 0) {
        if (rpdu.len > 0) {
            /* Note:  rpdu.len is uint16 anc can't be > MAX_DATA_SIZE */
            memcpy (rsp->data, rpdu.pdata, rpdu.len);
            rsp->dataLen = rpdu.len;
            rsp->ret = RET_SUCCESS;
            hex_print_tag_debug("CPLC", rsp->data, rsp->dataLen);
        }
    } else {
        LOGE("getCPLC failed. Invalid response : sw1 0x%2x,sw2 0x%2x,datalen %d",rpdu.sw1,rpdu.sw2,rpdu.len);
        rsp->ret = RET_ERR_GET_CPLC_FAIL;
        goto error;
    }

error:
    if(cn != 0) {
        secEseClose(cn);
    }
}

void getHQMMemory(p_rsp_t rsp) {
    uint8_t cn = 0;
    uint8_t isd_aid[] = {0xA0, 0x00, 0x00, 0x01, 0x51, 0x00, 0x00, 0x00};
    uint8_t data[MAX_RAPDU_DATA_SIZE] = {0,};
    secEse_7816_cpdu_t cpdu;
    secEse_7816_rpdu_t rpdu;

    LOGD("getHQMMemory start");

    if (ESESTATUS_SUCCESS != secEseOpen(&cn)) {
        LOGE("getHQMMemory channel open fail");
        rsp->ret = RET_ERR_GET_HQM_MEMORY;
        goto error;
    }

    memset(&rpdu, 0, sizeof(secEse_7816_rpdu_t));
    rpdu.pdata = data;
    if (cn < 1 || cn > 3 || ESESTATUS_SUCCESS != secEseSelect(cn, isd_aid, 0, 8, &rpdu) ) {
        LOGE("getHQMMemory failed to SELECT ISD");
        rsp->ret = RET_ERR_GET_HQM_MEMORY;
        goto error;
    }
    LOGE("getHQMMemory cn:%d",cn);

    memset(&cpdu, 0, sizeof(secEse_7816_cpdu_t));
    memset(&rpdu, 0, sizeof(secEse_7816_rpdu_t));
    memset(data, 0, MAX_RAPDU_DATA_SIZE);
    rpdu.pdata = data;

    cpdu.cla = 0x80;
    cpdu.ins = 0xCA;
    cpdu.p1 = 0xFF;
    cpdu.p2 = 0x21;
    cpdu.le_type = 1;

    if (ESESTATUS_SUCCESS != secEseTransmit(cn, &cpdu, &rpdu)) {
        LOGE("getHQMMemory failed to send APDU");
        rsp->ret = RET_ERR_GET_HQM_MEMORY;
        goto error;
    }

    if(rpdu.sw1 == 0x90 && rpdu.sw2 == 0x00 && rpdu.len > 0) {
        if (rpdu.len > 0) {
            /* Note:  rpdu.len is uint16 anc can't be > MAX_DATA_SIZE */
            memcpy (rsp->data, rpdu.pdata, rpdu.len);
            rsp->dataLen = rpdu.len;
            rsp->ret = RET_SUCCESS;
            hex_print_tag_debug("HQM MEMORY:", rsp->data, rsp->dataLen);
        }
    } else {
        LOGE("getHQMMemory failed. Invalid response : sw1 0x%2x,sw2 0x%2x,datalen %d",rpdu.sw1,rpdu.sw2,rpdu.len);
        rsp->ret = RET_ERR_GET_HQM_MEMORY;
        goto error;
    }

error:
    if(cn != 0)
        secEseClose(cn);

}

#if defined(EXTENDED_APDU)
void extendedApduEcho(p_rsp_t rsp) {
    uint8_t extended_apdu_echo_aid[] = {0xE0, 0x00, 0x00, 0x00, 0x01, 0x00, 0x01};
    uint8_t cn = 0;
    uint8_t r_data[MAX_RAPDU_DATA_SIZE] = {0,};
    uint8_t p_data[65535] = {0,};
    uint32_t lc_size[] = {10000, 20000, 32767, 40000, 50000, 65535};
    secEse_7816_cpdu_t cpdu;
    secEse_7816_rpdu_t rpdu;

    LOGD("extendedApduEcho start");

    for (int cnt = 0; cnt<6; cnt++) {
        if (ESESTATUS_SUCCESS != secEseOpen(&cn)) {
            LOGE("extended_apdu channel open fail");
            rsp->ret = RET_ERR_EXTENDED_APDU_FAILED;
            goto error;
        }

        memset(&rpdu, 0, sizeof(secEse_7816_rpdu_t));
        rpdu.pdata = r_data;
        if (cn < 1 || cn > 3 || ESESTATUS_SUCCESS != secEseSelect(cn, extended_apdu_echo_aid, 0, 7, &rpdu) ) {
            LOGE("extended_apdu failed to SELECT ISD");
            rsp->ret = RET_ERR_EXTENDED_APDU_FAILED;
            goto error;
        }

        memset(&cpdu, 0, sizeof(secEse_7816_cpdu_t));
        memset(&rpdu, 0, sizeof(secEse_7816_rpdu_t));
        memset(r_data, 0, MAX_RAPDU_DATA_SIZE);
        memset(p_data, 0x10, lc_size[cnt]);
        rpdu.pdata = r_data;

        cpdu.cla = 0x00;
        cpdu.ins = 0x20;
        cpdu.p1 = 0x00;
        cpdu.p2 = 0x00;
        cpdu.lc = lc_size[cnt];
        cpdu.le = 0x03E8;
        cpdu.cpdu_type = 1;
        cpdu.le_type = 2;
        cpdu.pdata = p_data; 

        LOGD("Send APDU Size : %d",lc_size[cnt]);
        if (ESESTATUS_SUCCESS != secEseTransmit(cn, &cpdu, &rpdu)) {
            LOGE("extended_apdu failed to send APDU ECHO TEST");
            rsp->ret = RET_ERR_EXTENDED_APDU_FAILED;
            goto error;
        }

        if(rpdu.sw1 == 0x90 && rpdu.sw2 == 0x00 && rpdu.len > 0) {
            if (rpdu.len > 0) {
                /* Note:  rpdu.len is uint16 anc can't be > MAX_DATA_SIZE */
                memcpy (rsp->data, rpdu.pdata, rpdu.len);
                LOGD("EXTENDED_ECHO Applet Ver %d",rsp->data[0]);
                rsp->dataLen = rpdu.len;
                rsp->ret = RET_SUCCESS;
                hex_print_tag_debug("EXTENDED_APDU", rsp->data, rsp->dataLen);
            }
        } else {
            if (cnt > 2 && ((rpdu.sw1 == 0x6f && rpdu.sw2 == 0x00) || (rpdu.sw1 == 0x67 && rpdu.sw2 == 0x00) || (rpdu.sw1 == 0x90 && rpdu.sw2 == 0x00))) {
                rsp->ret = RET_SUCCESS;
                continue;
            }
            LOGE("extended_apdu failed. Invalid response : sw1 0x%2x,sw2 0x%2x,datalen %d, cnt %d",rpdu.sw1,rpdu.sw2,rpdu.len,cnt);
            rsp->ret = RET_ERR_EXTENDED_APDU_FAILED;
            goto error;
        }
        if(cn != 0) {
            secEseClose(cn);
            cn = 0;
        }
    }
    error:
    if(cn != 0) {
        secEseClose(cn);
    }
}
#endif

#ifdef DEBUG_LOW
#define CASE1           1
#define SHORT_CASE2     2
#define SHORT_CASE3     3
#define SHORT_CASE4     4
#define EXTENDED_CASE2  5
#define EXTENDED_CASE3  6
#define EXTENDED_CASE4  7
#define EXTENDED_APDU   1

#if defined LOW_SPI_TEST
void sendData(p_cmd_t cmd, p_rsp_t rsp) {
    uint8_t cdata[MAX_CAPDU_SIZE] = {0,};
    uint8_t rdata[MAX_RAPDU_SIZE] = {0,};
    uint32_t len = 0;
    secEse_7816_rpdu_t rpdu = {0,};
    secEse_7816_cpdu_t apdu = {0,};
    uint32_t offset = 0, inputSize;
    uint8_t cmdType = 0;

    LOGD(" **************** sendData start");
    inputSize = cmd->dataLen;
    if (inputSize < 4) {
        LOGE("Invalid parameters, cmd->dataLen");
        goto error;
    }

    apdu.pdata = cdata;
    rpdu.pdata = rdata;

    hex_print_tag_debug("sem cmd", cmd->data, inputSize);

    len = inputSize;
    apdu.cpdu_type = 0;
    apdu.cla = cmd->data[0];
    apdu.ins = cmd->data[1];
    apdu.p1 = cmd->data[2];
    apdu.p2 = cmd->data[3];
#ifndef EXTENDED_APDU
    if (len == 4) {
        // type = 1;
        apdu.lc = 0;
        apdu.le_type = 0;
        apdu.le = 0;
        apdu.pdata = NULL;
        cmdType = CASE1;
    } else if (len == 5) {
        // type = 2;
        apdu.lc = 0;
        apdu.le_type = 1;
        apdu.le = cmd->data[4];
        apdu.pdata = NULL;
        cmdType = SHORT_CASE2;
    } else if (len == cmd->data[4] + 5) {
        // type = 3;
        apdu.lc = cmd->data[4];
        apdu.le_type = 0;
        apdu.le = 0;
        memcpy(apdu.pdata, cmd->data + 5, apdu.lc);
        cmdType = SHORT_CASE3;
    } else if (len == cmd->data[4] + 6) {
        // type = 4;
        apdu.lc = cmd->data[4];
        apdu.le_type = 1;
        memcpy(apdu.pdata, cmd->data + 5, apdu.lc);
        apdu.le = cmd->data[cmd->data[4] + 5];
        cmdType = SHORT_CASE4;
    } else {
        LOGE("Invalid APDU");
        rsp->ret = RET_ERR_INVALID_APDU ;
        goto error;
    }
#else
    LOGD("extended apdu feature enabled");
    if (len == 4) { // type 1 command
        LOGD("type 1");
        // type = 1;
        apdu.lc = 0;
        apdu.le_type = 0;
        apdu.le = 0;
        apdu.pdata = NULL;
        cmdType = CASE1;
    } else if (len == 5) { // type 2 short command
        // type = 2;
        LOGD("type 2");
        apdu.lc = 0;
        apdu.le_type = 1;
        apdu.le = cmd->data[4];
        apdu.pdata = NULL;
        cmdType = SHORT_CASE2;
    } else if ( (cmd->data[4] == 0) && (len == 7) ) { // type 2 extended command
        LOGD("type 2 ext");
        apdu.lc = 0;
        apdu.le_type = 3;
        apdu.le = ((cmd->data[5] << 8) | (cmd->data[6])) & 0xFFFF;
        apdu.pdata = NULL;
        cmdType = EXTENDED_CASE2;
    } else if ( cmd->data[4] != 0 ) { // type 3, 4 short command
        apdu.lc = (uint16_t) (cmd->data[4] & 0xFF);
        LOGD("Short Lc: %d", apdu.lc);
        if ( len == apdu.lc + 5 ) { // type 3 short command
            LOGD("type 3");
            apdu.le_type = 0;
            apdu.le = 0;
            memcpy(apdu.pdata, cmd->data + 5, apdu.lc);
            cmdType = SHORT_CASE3;
        } else if ( len == apdu.lc + 6) { // type 4 short command
            LOGD("type 4");
            apdu.le_type = 1;
            memcpy(apdu.pdata, cmd->data + 5, apdu.lc);
            apdu.le = cmd->data[apdu.lc + 5];
            cmdType = SHORT_CASE4;
        } else {
            LOGE("Invalid APDU");
            rsp->ret = RET_ERR_INVALID_APDU - 2;
            goto error;
        }

    } else if (len >= 8) { // type 3, 4 extended command
        apdu.lc = (uint16_t) (((cmd->data[5] << 8) | (cmd->data[6])) & (uint16_t)0xFFFF);
        apdu.cpdu_type = 1;
        LOGD("Extended Lc: %d", apdu.lc);
        if ( len == apdu.lc + 7 ) { // type 3 extended command
            LOGD("type 3 ext");
            apdu.le_type = 0;
            apdu.le = 0;
            if (apdu.lc > MAX_CAPDU_DATA_SIZE) {
                LOGE("Invalid buffer size");
                rsp->ret = RET_ERR_BUFFER_OVERFLOW;
                goto error;
            }
            memcpy(apdu.pdata, cmd->data + 7, apdu.lc);
            cmdType = EXTENDED_CASE3;
        } else if ( len == apdu.lc + 7 + 2) { // type 4 extended command
            LOGD("type 4 ext");
            apdu.le_type = 2;
            if (apdu.lc > MAX_CAPDU_DATA_SIZE) {
                LOGE("Invalid buffer size");
                rsp->ret = RET_ERR_BUFFER_OVERFLOW;
                goto error;
            }
            memcpy(apdu.pdata, cmd->data + 7, apdu.lc);
            apdu.le = (cmd->data[apdu.lc + 7] << 8) | cmd->data[apdu.lc + 8];
            cmdType = EXTENDED_CASE4;
        } else {
            LOGE("Invalid APDU");
            rsp->ret = RET_ERR_INVALID_APDU - 3;
            goto error;
        }
    } else {
        LOGE("Invalid APDU");
        rsp->ret = RET_ERR_INVALID_APDU - 4;
        goto error;
    }
#endif
    LOGD("%d command type", cmdType);
    if (0 != secEseTransmit((uint8_t)(apdu.cla & 0x03), &apdu, &rpdu)) {
        LOGE("failed to send data");
        rsp->ret = RET_ERR_TZ;
        goto error;
    }

    if (rpdu.len > 0) {
        offset += rpdu.len;
        memcpy (rsp->data, rpdu.pdata, offset);
    }

    memcpy (rsp->data + offset, &(rpdu.sw1), 1);
    offset++;
    memcpy (rsp->data + offset, &(rpdu.sw2), 1);
    offset++;

    rsp->dataLen = offset;
    rsp->ret = RET_SUCCESS;

    hex_print_tag_debug("rsp", rsp->data, rsp->dataLen);
    LOGD("sendData rsp len: %d", rsp->dataLen);

error :
    LOGD("sendData end. %02X", rsp->ret);
}

#endif

void getCASDCert(p_rsp_t rsp) {
    ESESTATUS isoStatus = 0;
    uint8_t channelId = 0;
    secEse_7816_cpdu_t isoCommand;
    secEse_7816_rpdu_t isoResponse;
    uint8_t responseData[MAX_RAPDU_DATA_SIZE] = {0,};

    uint8_t CASD_AID[12] = {0xA0,0x00,0x00,0x01,0x51,0x53,0x50,0x43,0x41,0x53,0x44,0x00};

    uint32_t max_retry_cnt = 5;
    uint32_t current_retry_cnt = 0;

    uint8_t cert_1[2048], cert_2[2048];
    uint16_t cert_1_len = 0, cert_2_len = 0;

    memset(&isoCommand, 0, sizeof(secEse_7816_cpdu_t));
    memset(&isoResponse, 0, sizeof(secEse_7816_rpdu_t));

    isoResponse.pdata = responseData;

    // manage channel
    isoStatus = secEseOpen(&channelId);
    if (isoStatus != ESESTATUS_OK) {
        LOGE("Failed to open channel in selectCASDTest");
        return;
    }
    LOGD("selectCASDTest channel ID : %d",channelId);

    // select CASD
    isoStatus = secEseSelect(channelId, CASD_AID, 0, 12, &isoResponse);
    if (isoStatus != ESESTATUS_OK || isoResponse.sw1 != 0x90 || isoResponse.sw2 !=0x00) {
        LOGE("Failed to [SELECT CASD]");
        return;
    }
    hex_print_tag_debug("CASD SELECT RESPOPNSE", isoResponse.pdata, isoResponse.len);

    isoCommand.cla = 0x80;
    isoCommand.ins = 0xca;
    isoCommand.p1 = 0x7f;
    isoCommand.p2 = 0x21;
    isoCommand.le = 0x00;

retry:
    if (max_retry_cnt < current_retry_cnt) {
        current_retry_cnt = 0;
        goto second;
    }
    isoStatus = secEseTransmit(channelId, &isoCommand, &isoResponse);
    LOGD("CASD Command isoStatus :: 0x%x, sw1- 0x%x, sw2- 0x%x", isoStatus, isoResponse.sw1, isoResponse.sw2);
    LOGD("CASD Command isoStatus :: %d", isoResponse.len);
    hex_print_tag_debug("CASD CMD RESPOPNSE", isoResponse.pdata, isoResponse.len);
    memcpy(cert_1 + cert_1_len,  isoResponse.pdata, isoResponse.len);
    cert_1_len += isoResponse.len;
    if (isoResponse.sw1 == 0x61) {
        isoCommand.cla = 0x00;
        isoCommand.ins = 0xC0;
        isoCommand.p1 = 0x00;
        isoCommand.p2 = 0x00;
        isoCommand.le = 0x00;
        current_retry_cnt++;
        goto retry;
    } else if (isoResponse.sw1 == 0x63 && isoResponse.sw2 == 0x10) {
        current_retry_cnt++;
        goto retry;
    } else if (isoResponse.sw1 != 0x90 || isoResponse.sw2 != 0x00) {
        LOGE("Get 80CA7F21 error");
        goto exit;
    }

second:
    isoCommand.cla = 0x80;
    isoCommand.ins = 0xca;
    isoCommand.p1 = 0x7f;
    isoCommand.p2 = 0xd2;
#ifdef OT
    isoCommand.le = 0xe9;
#else
    isoCommand.le = 0x00;
#endif

    isoStatus = secEseTransmit(channelId, &isoCommand, &isoResponse);
    LOGD("CASD Command isoStatus :: 0x%x, sw1- 0x%x, sw2- 0x%x",isoStatus, isoResponse.sw1, isoResponse.sw2);
    LOGD("CASD Command isoStatus :: %d", isoResponse.len);
    hex_print_tag_debug("CASD CMD RESPOPNSE", isoResponse.pdata, isoResponse.len);
    memcpy(cert_2 + cert_2_len,  isoResponse.pdata, isoResponse.len);
    cert_2_len += isoResponse.len;

    if (isoResponse.sw1 != 0x90 || isoResponse.sw2 != 0x00) {
        LOGE("Get 80CA7FD2 error");
        goto exit;
    }

    hex_print_tag_debug("cert_1", cert_1, cert_1_len);
    hex_print_tag_debug("cert_2", cert_2, cert_2_len);

    memcpy(rsp->data, &cert_1_len, 2);
    memcpy(rsp->data + 2, cert_1, cert_1_len);
    memcpy(rsp->data + 2 + cert_1_len, &cert_2_len, 2);
    memcpy(rsp->data + 2 + cert_1_len + 2, cert_2, cert_2_len);
    rsp->dataLen = 4 + cert_1_len + cert_2_len;

exit:
    secEseClose(channelId);
    rsp->ret = RET_SUCCESS;
}

void getInfoTest() {
#if 0
    ESESTATUS isoStatus = 0;
    uint8_t channelId = 0;
    secEse_7816_cpdu_t isoCommand;
    secEse_7816_rpdu_t isoResponse;
    uint8_t responseData[MAX_RAPDU_DATA_SIZE] = {0,};

    uint8_t DMSD_AID[14] = {0xA0, 0x00, 0x00, 0x01, 0x51, 0x53, 0x50, 0x41, 0x4C, 0x43, 0x43, 0x4D, 0x44, 0x4D};
//    uint8_t ISD_AID[8] = {0xA0, 0x00, 0x00, 0x01, 0x51, 0x00, 0x00, 0x00};

    memset(&isoCommand, 0, sizeof(secEse_7816_cpdu_t));
    memset(&isoResponse, 0, sizeof(secEse_7816_rpdu_t));

    isoResponse.pdata = responseData;

    // manage channel
    isoStatus = secEseOpen(&channelId);
    if (isoStatus != ESESTATUS_OK) {
        LOGE("Failed to open channel in DMSD");
        return;
    }
    LOGD("channel ID : %d",channelId);

#if 1
    // select DMSD
    isoStatus = secEseSelect(channelId, DMSD_AID, 0, 14, &isoResponse);
    if (isoStatus != ESESTATUS_OK || isoResponse.sw1 != 0x90 || isoResponse.sw2 !=0x00) {
        LOGE("Failed to [SELECT DMSD]");
        return;
    }
    hex_print_tag_debug("DMSD SELECT RESPOPNSE", isoResponse.pdata, isoResponse.len);
#else
    // select ISD
    isoStatus = secEseSelect(channelId, ISD_AID, 0, 8, &isoResponse);
    if (isoStatus != ESESTATUS_OK || isoResponse.sw1 != 0x90 || isoResponse.sw2 !=0x00) {
        LOGE("Failed to [SELECT ISD]");
        goto error;
    }
    hex_print_tag_debug("ISD SELECT RESPOPNSE", isoResponse.pdata, isoResponse.len);
#endif
    isoCommand.cla = 0x80;
    isoCommand.ins = 0xCA;
    isoCommand.p1 = 0x00;
    isoCommand.p2 = 0x42;
    isoCommand.le = 0xFF;

    isoStatus = secEseTransmit(channelId, &isoCommand, &isoResponse);
    LOGD("Command isoStatus :: 0x%x, sw1- 0x%x, sw2- 0x%x", isoStatus, isoResponse.sw1, isoResponse.sw2);
    LOGD("Command isoStatus :: %d", isoResponse.len);
    hex_print_tag_debug("CMD RESPOPNSE", isoResponse.pdata, isoResponse.len);

#if 0
    secEseClose(channelId);
    isoStatus = secEseOpen(&channelId);
    if (isoStatus != ESESTATUS_OK) {
        LOGE("Failed to open channel in ISD");
        return;
    }
    LOGD("channel ID : %d",channelId);

    // select ISD
    isoStatus = secEseSelect(channelId, ISD_AID, 0, 8, &isoResponse);
    if (isoStatus != ESESTATUS_OK || isoResponse.sw1 != 0x90 || isoResponse.sw2 !=0x00) {
        LOGE("Failed to [SELECT ISD]");
        goto error;
    }
    hex_print_tag_debug("ISD SELECT RESPOPNSE", isoResponse.pdata, isoResponse.len);
#endif

    isoCommand.cla = 0x80;
    isoCommand.ins = 0xCA;
    isoCommand.p1 = 0x00;
    isoCommand.p2 = 0x45;
    isoCommand.le = 0xFF;

    isoStatus = secEseTransmit(channelId, &isoCommand, &isoResponse);
    LOGD("Command isoStatus :: 0x%x, sw1- 0x%x, sw2- 0x%x",isoStatus, isoResponse.sw1, isoResponse.sw2);
    LOGD("Command isoStatus :: %d", isoResponse.len);
    hex_print_tag_debug("CMD RESPOPNSE", isoResponse.pdata, isoResponse.len);

error:
    secEseClose(channelId);

// Select CASD Test
#if 0
    selectCASDTest();
#endif

#else
    //getCASDCert();
#endif
}

#endif // DEBUG_LOW

