#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include "tc_tpm2.h"
#include "tc_errcode.h"

API_CTX TPM2_API_CTX_TEMPLATE[API_MAX] = {
    {NULL, API_NULL,            NULL,                      NULL},
    {NULL, API_START,           tpm2_start_init,           tpm2_start_free},
    {NULL, API_END,             tpm2_end_init,             tpm2_end_free},
    {NULL, API_CREATEPRIMARY,   tpm2_createprimary_init,   tpm2_createprimary_free},
    {NULL, API_CREATE,          tpm2_create_init,          tpm2_create_free},
    {NULL, API_LOAD,            tpm2_load_init,            tpm2_load_free},
    {NULL, API_EVICTCONTROL,    tpm2_evictcontrol_init,    tpm2_evictcontrol_free},
    {NULL, API_ENCRYPT,         tpm2_encrypt_init,         tpm2_encrypt_free},
    {NULL, API_DECRYPT,         tpm2_decrypt_init,         tpm2_decrypt_free},
    {NULL, API_HASH,            tpm2_hash_init,            tpm2_hash_free},
    {NULL, API_SIGN,            tpm2_sign_init,            tpm2_sign_free},
    {NULL, API_VERIFYSIGNATURE, tpm2_verifysignature_init, tpm2_verifysignature_free},
    {NULL, API_NVDEFINE,        tpm2_nvdefine_init,        tpm2_nvdefine_free},
    {NULL, API_NVRELEASE,       tpm2_nvrelease_init,       tpm2_nvrelease_free},
    {NULL, API_NVREAD,          tpm2_nvread_init,          tpm2_nvread_free},
    {NULL, API_NVWRITE,         tpm2_nvwrite_init,         tpm2_nvwrite_free}
};

ENGINE_OPS engine_ops_tpm2 = {
    tpm2_start,
    tpm2_end,
    tpm2_createprimary,
    tpm2_create,
    tpm2_load,
    tpm2_evictcontrol,
    tpm2_encrypt,
    tpm2_decrypt,
    tpm2_hash,
    tpm2_sign,
    tpm2_verifysignature,
    tpm2_nvdefine,
    tpm2_nvrelease,
    tpm2_nvread,
    tpm2_nvwrite
};

TC_RC tpm2_alloc_api_ctx(enum API_TYPE cmd_code)
{
    TC_RC rc = TC_SUCCESS;
    engine_ctx_tpm2.api_ctx = (API_CTX*)malloc(sizeof(API_CTX));
    memcpy(engine_ctx_tpm2.api_ctx,
           &TPM2_API_CTX_TEMPLATE[cmd_code],
           sizeof(API_CTX));
    return rc;
}

TC_RC tpm2_release_api_ctx()
{
    TC_RC rc = TC_SUCCESS;
    free(engine_ctx_tpm2.api_ctx);
    engine_ctx_tpm2.api_ctx = NULL;
    return rc;
}

ENGINE_CTX engine_ctx_tpm2 =
{
    NULL,
    tpm2_alloc_api_ctx,
    tpm2_release_api_ctx,
    &engine_ops_tpm2,
};