diff --git a/hsm_utils/Makefile b/hsm_utils/Makefile index 16e8193..4c5c72c 100644 --- a/hsm_utils/Makefile +++ b/hsm_utils/Makefile @@ -105,11 +105,15 @@ import_common_key: import_common_key.c $(EXTRA_OBJECTS) import_rsa_keypair: import_rsa_keypair.c $(EXTRA_OBJECTS) $(CC) $(CFLAGS) $(CPPFLAGS) -o import_rsa_keypair import_rsa_keypair.c $(COMMON_OBJECTS) $(EXTRA_OBJECTS) $(LDLIBS) +import_ecc_keypair: import_ecc_keypair.c $(EXTRA_OBJECTS) + $(CC) $(CFLAGS) $(CPPFLAGS) -o import_ecc_keypair import_ecc_keypair.c $(COMMON_OBJECTS) $(EXTRA_OBJECTS) $(LDLIBS) + # All single-threaded targets TARGETS_SIMPLE= \ import_common_key \ import_rsa_keypair \ + import_ecc_keypair \ simple: $(TARGETS_SIMPLE) diff --git a/hsm_utils/import_ecc_keypair.c b/hsm_utils/import_ecc_keypair.c new file mode 100644 index 0000000..aefea3a --- /dev/null +++ b/hsm_utils/import_ecc_keypair.c @@ -0,0 +1,735 @@ + +// import key (+ encrypt, decrypt) test for nShield + +#include +#include +#include +#include + +// openssl +#include +#include +#include +#include +#include +#include +#include + +#include "nfastapp.h" +#include "nfkm.h" +#include "rqcard-applic.h" +#include "rqcard-fips.h" + +#include "ncthread-upcalls.h" +//#include "picky-upcalls.h" + +#include "mybignum.h" + + +#define PRIV_KEY_FILE "/opt/nfast/work/rsa-priv-key2048.der" +#define PUB_KEY_FILE "/opt/nfast/work/rsa-pub-key2048.der" + +#define MODULE_ID 1 +#define DATA_LEN 256 // bytes + +typedef struct _NFast_Call_Context +{ + int notused; +} +NFast_Call_Context; +NFast_Call_Context context; + +// RSA private key data +typedef struct +{ + struct NFast_Bignum *p; + struct NFast_Bignum *q; + struct NFast_Bignum *dmp1; + struct NFast_Bignum *dmq1; + struct NFast_Bignum *iqmp; + struct NFast_Bignum *e; +} +RSAPrivateKeyData; + +// RSA public key data +typedef struct +{ + struct NFast_Bignum *e; + struct NFast_Bignum *n; +} +RSAPublicKeyData; + +static void *my_malloc( size_t nbytes, + struct NFast_Call_Context *cctx, struct NFast_Transaction_Context *tctx ); +static void *my_realloc( void *ptr, size_t nbytes, + struct NFast_Call_Context *cctx, struct NFast_Transaction_Context *tctx ); +static void my_free( void *ptr, + struct NFast_Call_Context *cctx, struct NFast_Transaction_Context *tctx ); + +int sbn_bin2bignum ( struct NFast_Bignum **ppBN_out, + struct NFast_Application *app, + const unsigned char *bin, const int size ); + +void PrintArray( char *pStr, const unsigned char *pData, int length ); + +const NFast_MallocUpcalls my_malloc_upcalls = +{ + my_malloc, my_realloc, my_free +}; + +static void *my_malloc( size_t nbytes, + struct NFast_Call_Context *cctx, struct NFast_Transaction_Context *tctx ) +{ + return malloc( nbytes ); +} + +static void *my_realloc( void *ptr, size_t nbytes, + struct NFast_Call_Context *cctx, struct NFast_Transaction_Context *tctx ) +{ + return realloc( ptr, nbytes ); +} + +static void my_free( void *ptr, + struct NFast_Call_Context *cctx, struct NFast_Transaction_Context *tctx ) +{ + free( ptr ); +} + +// bin データを NFastApp の BigNum データに変換する +int sbn_bin2bignum ( struct NFast_Bignum **ppBN_out, + struct NFast_Application *app, + const unsigned char *bin, const int size ) +{ + struct NFast_Bignum *pBN; + int len, i; + + len = size; + + if ( len > MAXBIGNUMBITS/4 ) return Status_OutOfRange; + + pBN = (struct NFast_Bignum *)NFastApp_Malloc( app, sizeof(struct NFast_Bignum), NULL, NULL ); + if ( !pBN ) return NOMEM; + + pBN->msb_first = 0; + pBN->msw_first = 0; + + for ( i = 0; i < len; i++ ) + pBN->bytes[i] = bin[len-1-i]; + + while ( (i & 3) != 0 ) + pBN->bytes[i++] = 0; + + pBN->nbytes = i; + + *ppBN_out = pBN; + +#if 0 + PrintArray( (char*)"bin2bn array", (const char*)pBN->bytes, pBN->nbytes ); +#endif + + return Status_OK; +} // sbn_bin2bignum + +void PrintArray( char *pStr, const unsigned char *pData, int length ) +{ + int i; + printf( "%s(%d bytes)", pStr, length ); + for ( i = 0; i < length; i++ ) + { + if ( (i % 16) == 0 ) printf( "\n" ); + printf( "%02X ", pData[ i ] ); + } + printf( "\n" ); +} + +int main( int argc, char *argv[] ) +{ + int i; + int result = 0; + int rand_size = 80; + + M_Command cmd; + M_Reply reply; + + memset( &cmd, 0, sizeof( cmd ) ); + memset( &reply, 0, sizeof( reply ) ); + + NFast_AppHandle handle; + NFastApp_Connection nc; + NFKM_WorldInfo *world = NULL; + RQCard card; + RQCard_FIPS fips; + M_KeyID ltid; // the cardset loaded into the module + M_KeyID keyid; + NFKM_Key *keyinfo; + + if ( argc == 2 ) + rand_size = atoi( argv[1] ); + + // load rsa data (private) + RSA *privkey = NULL; + FILE *fp; + fp = fopen( PRIV_KEY_FILE, "rb" ); + if ( !fp ) + { + printf( "error : open %s file\n", PRIV_KEY_FILE ); + return 0; + } + privkey = d2i_RSAPrivateKey_fp( fp, NULL ); + if ( !privkey ) + { + printf( "error : d2i_RSAPrivateKey_fp\n" ); + return 0; + } + +#if 0 + printf( "RSA(p) : %d bytes\n", BN_num_bytes( privkey->p ) ); + printf( "RSA(q) : %d bytes\n", BN_num_bytes( privkey->q ) ); + printf( "RSA(dmp1) : %d bytes\n", BN_num_bytes( privkey->dmp1 ) ); + printf( "RSA(dmq1) : %d bytes\n", BN_num_bytes( privkey->dmq1 ) ); + printf( "RSA(iqmp) : %d bytes\n", BN_num_bytes( privkey->iqmp ) ); + printf( "RSA(e) : %d bytes\n", BN_num_bytes( privkey->e ) ); +#endif + + // p + unsigned char *pPtr; + int pLen = BN_num_bytes( privkey->p ); + pPtr = (char *)malloc( pLen ); + if ( pLen != BN_bn2bin( privkey->p, pPtr ) ) + { + printf( "BN_bn2bin failed!(p)\n" ); + } + + // q + unsigned char *qPtr; + int qLen = BN_num_bytes( privkey->q ); + qPtr = (char *)malloc( qLen ); + if ( qLen != BN_bn2bin( privkey->q, qPtr ) ) + { + printf( "BN_bn2bin failed!(q)\n" ); + } + + // dmp1 + unsigned char *dmp1Ptr; + int dmp1Len = BN_num_bytes( privkey->dmp1 ); + dmp1Ptr = (char *)malloc( dmp1Len ); + if ( dmp1Len != BN_bn2bin( privkey->dmp1, dmp1Ptr ) ) + { + printf( "BN_bn2bin failed!(dmp1)\n" ); + } + + // dmq1 + unsigned char *dmq1Ptr; + int dmq1Len = BN_num_bytes( privkey->dmq1 ); + dmq1Ptr = (char *)malloc( dmq1Len ); + if ( dmq1Len != BN_bn2bin( privkey->dmq1, dmq1Ptr ) ) + { + printf( "BN_bn2bin failed!(dmq1)\n" ); + } + + // iqmp + unsigned char *iqmpPtr; + int iqmpLen = BN_num_bytes( privkey->iqmp ); + iqmpPtr = (char *)malloc( iqmpLen ); + if ( iqmpLen != BN_bn2bin( privkey->iqmp, iqmpPtr ) ) + { + printf( "BN_bn2bin failed!(dmq1)\n" ); + } + + // e + unsigned char *ePtr; + int eLen = BN_num_bytes( privkey->e ); + ePtr = (char *)malloc( eLen ); + if ( eLen != BN_bn2bin( privkey->e, ePtr ) ) + { + printf( "BN_bn2bin failed!(e)\n" ); + } + + printf( "\n" ); + +#if 0 + printf( "RSA(p) : 0x%08X\n", (unsigned int)pPtr ); + printf( "RSA(q) : 0x%08X\n", (unsigned int)qPtr ); + printf( "RSA(dmp1) : 0x%08X\n", (unsigned int)dmp1Ptr ); + printf( "RSA(dmq1) : 0x%08X\n", (unsigned int)dmq1Ptr ); + printf( "RSA(iqmp) : 0x%08X\n", (unsigned int)iqmpPtr ); + printf( "RSA(e) : 0x%08X\n", (unsigned int)ePtr ); +#endif + + // init nFast + result = NFastApp_InitEx( &handle, NULL, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFastApp_InitEx\n", result ); + return 0; + } + + // connecting to hardserver + result = NFastApp_Connect( handle, &nc, 0, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFastApp_Connect\n", result ); + return 0; + } + + // set bignum upcalls setting + result = NFastApp_SetBignumUpcalls( + handle, + my_bignumreceiveupcall, + my_bignumsendlenupcall, + my_bignumsendupcall, + my_bignumfreeupcall, + my_bignumformatupcall, + NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFastApp_SetBignumUpcalls\n", result ); + return 0; + } + + // NFKM getinfo + result = NFKM_getinfo( handle, &world, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_getinfo\n", result ); + return 0; + } + + // init card-loading lib + result = RQCard_init( &card, handle, nc, world, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : RQCard_init\n", result ); + return 0; + } + + // init FIPS state + result = RQCard_fips_init( &card, &fips ); + if ( result != Status_OK ) + { + printf( "error(%d) : RQCard_fips_init\n", result ); + return 0; + } + + // ui select + result = RQCard_ui_default( &card ); + if ( result != Status_OK ) + { + printf( "error(%d) : RQCard_ui_default\n", result ); + return 0; + } + + // get strict-FIPS authorization +#if 0 + NFKM_FIPS140AuthHandle fipsHandle; + M_SlotID slotId; + result = RQCard_fips_get( &fips, 1, &fipsHandle, &slotId ); + if ( result != Status_OK ) + { + printf( "error(%d) : RQCard_fips_get\n", result ); + return 0; + } + if ( fipsHandle == NULL ) + { + printf( "this sworld isn't strict-FIPS.\n" ); + } +#endif + +#if 1 + // list cardsets + int card_num; + NFKM_CardSetIdent *cardident = NULL; + result = NFKM_listcardsets( handle, &card_num, &cardident, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_listcardsets\n", result ); + return 0; + } + + // find cardsets + NFKM_CardSet *cardset = NULL; + result = NFKM_findcardset( handle, cardident, &cardset, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_findcardset\n", result ); + return 0; + } + + // load cardset + result = RQCard_logic_ocs_specific( &card, &(cardset->hkltu), "Load Cardset" ); + if ( result != Status_OK ) + { + printf( "error(%d) : RQCard_logic_ocs_specific\n", result ); + return 0; + } + + // use specific module : #1 + // important!! : if you set resultplace=NULL, abort. (possibility is 100%) + result = RQCard_whichmodule_specific( &card, world->modules[0]->module, <id ); + if ( result != Status_OK ) + { + printf( "error(%d) : RQCard_whichmodule_specific\n", result ); + } + + // wait event loop + result = card.uf->eventloop( &card ); + if ( result != Status_OK ) + { + printf( "error(%d) : card module event loop\n", result ); + } +#endif + + // get usable module + NFKM_ModuleInfo *moduleinfo = world->modules[0]; + result = NFKM_getusablemodule( world, MODULE_ID, &moduleinfo ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_getusablemodule\n", result ); + } + + // make ACL + NFKM_MakeACLParams map; + memset( &map, 0, sizeof( map ) ); + map.f = NFKM_NKF_RecoveryEnabled | NFKM_NKF_ProtectionCardSet; + // 暗号化と復号化、署名とベリファイなど、相反する操作を持たせることはできない(エラーになる) + // e.g. NFKM_DEFOPPERMS_SIGN | NFKM_DEFOPPERMS_VERIFY -> エラー + // e.g. NFKM_DEFOPPERMS_ENCRYPT | NFKM_DEFOPPERMS_DECRYPT -> エラー + map.op_base = NFKM_DEFOPPERMS_SIGN | NFKM_DEFOPPERMS_DECRYPT; + map.cs = cardset; + result = NFKM_newkey_makeaclx( handle, nc, world, &map, &(cmd.args.import.acl), NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_newkey_makeaclx\n", result ); + } + +#if 0 + // set bignum upcalls setting + result = NFastApp_SetBignumUpcalls( + handle, + my_bignumreceiveupcall, + my_bignumsendlenupcall, + my_bignumsendupcall, + my_bignumfreeupcall, + my_bignumformatupcall, + NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFastApp_SetBignumUpcalls\n", result ); + } +#endif + + // convert bin -> M_Bignum + struct NFast_Bignum *pBn = NULL; + struct NFast_Bignum *qBn = NULL; + struct NFast_Bignum *dmp1Bn = NULL; + struct NFast_Bignum *dmq1Bn = NULL; + struct NFast_Bignum *iqmpBn = NULL; + struct NFast_Bignum *eBn = NULL; + { + // p + result = sbn_bin2bignum( &pBn, handle, pPtr, pLen ); + if ( result != Status_OK ) + { + printf( "error(%d) : sbn_bin2bignum( p )\n", result ); + return 0; + } + + // q + result = sbn_bin2bignum( &qBn, handle, qPtr, qLen ); + if ( result != Status_OK ) + { + printf( "error(%d) : sbn_bin2bignum( q )\n", result ); + return 0; + } + + // dmp1 + result = sbn_bin2bignum( &dmp1Bn, handle, dmp1Ptr, dmp1Len ); + if ( result != Status_OK ) + { + printf( "error(%d) : sbn_bin2bignum( dmp1 )\n", result ); + return 0; + } + + // dmq1 + result = sbn_bin2bignum( &dmq1Bn, handle, dmq1Ptr, dmq1Len ); + if ( result != Status_OK ) + { + printf( "error(%d) : sbn_bin2bignum( dmq1 )\n", result ); + return 0; + } + + // iqmp + result = sbn_bin2bignum( &iqmpBn, handle, iqmpPtr, iqmpLen ); + if ( result != Status_OK ) + { + printf( "error(%d) : sbn_bin2bignum( iqmp )\n", result ); + return 0; + } + + // e + result = sbn_bin2bignum( &eBn, handle, ePtr, eLen ); + if ( result != Status_OK ) + { + printf( "error(%d) : sbn_bin2bignum( e )\n", result ); + return 0; + } + } + + printf( "import ...\n" ); + + // import key + NFKM_KeyIdent keyident = { (char*)"simple", (char*)"rsa-import-privkey" }; + cmd.cmd = Cmd_Import; + cmd.args.import.module = MODULE_ID; + cmd.args.import.data.type = KeyType_RSAPrivate; + cmd.args.import.data.data.rsaprivate.p = pBn; + cmd.args.import.data.data.rsaprivate.q = qBn; + cmd.args.import.data.data.rsaprivate.dmp1 = dmp1Bn; + cmd.args.import.data.data.rsaprivate.dmq1 = dmq1Bn; + cmd.args.import.data.data.rsaprivate.iqmp = iqmpBn; + cmd.args.import.data.data.rsaprivate.e = eBn; + result = NFastApp_Transact( nc, NULL, &cmd, &reply, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : Cmd_Import\n", result ); + } + result = reply.status; + if ( result != Status_OK ) + { + printf( "error(%d) : Cmd_Import(reply)\n", result ); + } + printf( "keyid : 0x%08X\n", (unsigned int)reply.reply.import.key ); + + printf( "done. next : make blob ...\n" ); + + // make blobs + NFKM_MakeBlobsParams mbp; + NFKM_Key reg_key; + memset( &mbp, 0, sizeof( mbp ) ); + memset( ®_key, 0, sizeof( reg_key ) ); + + reg_key.v = Key__maxversion; // TORIAEZU Version Max (8) + reg_key.name = keyident.ident; + reg_key.appname = keyident.appname; + reg_key.ident = keyident.ident; + time( &(reg_key.gentime) ); + + mbp.f = map.f; + mbp.kpriv = reply.reply.import.key; + mbp.lt = ltid; + mbp.cs = cardset; + result = NFKM_newkey_makeblobsx( handle, nc, world, &mbp, ®_key, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_newkey_makeblobsx\n", result ); + return 0; + } + + printf( "done. next : record blob ...\n" ); + + // record key to disk + result = NFKM_recordkey( handle, ®_key, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_recordkey\n", result ); + } + + printf( "record key success?\n" ); + + // destroy key + result = NFKM_cmd_destroy( handle, nc, 0, reply.reply.import.key, + "import.key", NULL ); + + // list key +#if 0 + int key_num; + NFKM_KeyIdent *keylist = NULL; + result = NFKM_listkeys( handle, &key_num, &keylist, "simple", NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_listkeys\n", result ); + } + NFKM_KeyIdent **tkp = &keylist; + for ( i = 0; i < key_num; i++ ) + { + printf( "appname : %s, ident : %s\n", tkp[i]->appname, tkp[i]->ident ); + } +#endif + + // find key + NFKM_KeyIdent ki_v = { (char*)"simple", (char*)"rsa-import-privkey" }; + + printf( "appname : %s, ident : %s\n", ki_v.appname, ki_v.ident ); + + result = NFKM_findkey( handle, ki_v, &keyinfo, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_findkey\n", result ); + } + + // load blob + M_ByteBlock *blobptr; + if ( keyinfo->pubblob.len) + blobptr = &keyinfo->pubblob; + else + { + blobptr = &keyinfo->privblob; + } + + result = NFKM_cmd_loadblob( handle, nc, + moduleinfo->module, blobptr, ltid, &keyid, "loading key blob", NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFKM_cmd_loadblob\n", result ); + } + printf( "key ID : %u\n", (unsigned int)keyid ); + + // get key info + cmd.cmd = Cmd_GetKeyInfo; + cmd.args.getkeyinfo.key = keyid; + result = NFastApp_Transact( nc, NULL, &cmd, &reply, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : FastApp_Transact(Cmd_GetKeyInfo)\n", result ); + } + // if type == 30 then Rijndael(AES) + printf( "keytype : %d\n", reply.reply.getkeyinfo.type ); + + // encrypt & dectypt test + { + M_ByteBlock enc_input, dec_input; + M_ByteBlock enc_output, dec_output; + M_IV base_iv, enc_iv, dec_iv; + + // data setting + enc_input.len = DATA_LEN; + enc_input.ptr = (unsigned char*)malloc( DATA_LEN ); + for ( i = 0; i < enc_input.len; i++ ) + enc_input.ptr[i] = i; + + base_iv.mech = Mech_RijndaelmCBCpNONE; + for ( i = 0; i < 16; i++ ) + base_iv.iv.generic128.iv.bytes[i] = i; + enc_iv = base_iv; + dec_iv = base_iv; + + // encrypt : my ver + cmd.cmd = Cmd_Encrypt; + cmd.args.encrypt.key = keyid; + cmd.args.encrypt.mech = Mech_RijndaelmCBCpNONE; + cmd.args.encrypt.plain.type = PlainTextType_Bytes; + cmd.args.encrypt.plain.data.bytes.data = enc_input; + cmd.args.encrypt.flags = Cmd_Encrypt_Args_flags_given_iv_present; + cmd.args.encrypt.given_iv = &enc_iv; + result = NFastApp_Transact( nc, NULL, &cmd, &reply, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : FastApp_Transact(Cmd_Encrypt)\n", result ); + } + result = reply.status; + if ( result != Status_OK ) + { + printf( "error(%d) : reply.status(Cmd_Encrypt)\n", result ); + } + enc_output.len = reply.reply.encrypt.cipher.data.generic128.cipher.len; + if ( enc_output.len != DATA_LEN ) + { + printf( "error : output data size isn't %d bytes(Cmd_Encrypt)\n", (int)enc_output.len ); + } + enc_output.ptr = (unsigned char*)malloc( enc_output.len ); + memcpy( enc_output.ptr, + reply.reply.encrypt.cipher.data.generic128.cipher.ptr, + enc_output.len ); + + printf( "encrypt ok\n" ); + + dec_input.len = enc_output.len; + dec_input.ptr = (unsigned char*)malloc( dec_input.len ); + memcpy( dec_input.ptr, enc_output.ptr, DATA_LEN ); + + NFastApp_Free_Reply( handle, NULL, NULL, &reply ); + + // decrypt : my ver + cmd.cmd = Cmd_Decrypt; + cmd.args.decrypt.flags = 0; + cmd.args.decrypt.key = keyid; + cmd.args.decrypt.mech = Mech_RSApPKCS1; + cmd.args.decrypt.cipher.mech = Mech_RSApPKCS1; + cmd.args.decrypt.cipher.data.generic128.cipher = dec_input; + cmd.args.decrypt.cipher.iv = dec_iv.iv; + cmd.args.decrypt.reply_type = PlainTextType_Bytes; + result = NFastApp_Transact( nc, NULL, &cmd, &reply, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : FastApp_Transact(Cmd_Decrypt)\n", result ); + } + result = reply.status; + if ( result != Status_OK ) + { + printf( "error(%d) : reply.status(Cmd_Decrypt)\n", result ); + } + dec_output.len = reply.reply.decrypt.plain.data.bytes.data.len; + if ( dec_output.len != DATA_LEN ) + { + printf( "error : output size isn't %d bytes(Cmd_Decrypt)\n", (int)enc_output.len ); + } + dec_output.ptr = (unsigned char*)malloc( dec_output.len ); + memcpy( dec_output.ptr, + reply.reply.decrypt.plain.data.bytes.data.ptr, + dec_output.len ); + + printf( "decrypt ok\n" ); + + NFastApp_Free_Reply( handle, NULL, NULL, &reply ); + + // key destroy + memset( &cmd, 0, sizeof( cmd ) ); // fail if NFastApp_Free_Command + cmd.cmd = Cmd_Destroy; + cmd.args.destroy.key = keyid; + result = NFastApp_Transact( nc, NULL, &cmd, &reply, NULL ); + if ( result != Status_OK ) + { + printf( "error(%d) : NFastApp_Transact(Cmd_Destroy)\n", result ); + } + NFastApp_Free_Reply( handle, NULL, NULL, &reply ); + + // data show + printf( "enc_input : (%d bytes)", (int)enc_input.len ); + for ( i = 0; i < enc_input.len; i++ ) + { + if ( i % 16 == 0 ) + printf( "\n" ); + printf( "%02X ", enc_input.ptr[i] ); + } + printf( "\n" ); + + printf( "\nenc_output : (%d bytes)", (int)enc_output.len ); + for ( i = 0; i < enc_output.len; i++ ) + { + if ( i % 16 == 0 ) + printf( "\n" ); + printf( "%02X ", enc_output.ptr[i] ); + } + printf( "\n" ); + + printf( "\ndec_output : (%d bytes)", (int)dec_output.len ); + for ( i = 0; i < dec_output.len; i++ ) + { + if ( i % 16 == 0 ) + printf( "\n" ); + printf( "%02X ", dec_output.ptr[i] ); + } + printf( "\n" ); + } // encrypt & decrypt + + // end processing + RQCard_fips_free( &card, &fips ); + RQCard_destroy( &card ); + NFKM_freekey( handle, keyinfo, NULL ); + NFKM_freeinfo( handle, &world, NULL ); + NFastApp_Disconnect( nc, NULL ); + NFastApp_Finish( handle, NULL ); + + return 0; + +} // main