Пример #1
0
void gcm_init(gcm* g,int nk,char *key,int niv,char *iv)
{ /* iv size niv is usually 12 bytes (96 bits). AES key size nk can be 16,24 or 32 bytes */
	int i;
	MR_BYTE H[16];
	for (i=0;i<16;i++) {H[i]=0; g->stateX[i]=0;}

	aes_init(&(g->a),MR_ECB,nk,key,iv);
	aes_ecb_encrypt(&(g->a),H);     /* E(K,0) */
	precompute(g,H);
	
	g->lenA[0]=g->lenC[0]=g->lenA[1]=g->lenC[1]=0;
	if (niv==12)
	{
		for (i=0;i<12;i++) g->a.f[i]=iv[i];
		unpack((MR_WORD)1,(MR_BYTE *)&(g->a.f[12]));  /* initialise IV */
		for (i=0;i<16;i++) g->Y_0[i]=g->a.f[i];
	}
	else
	{
		g->status=GCM_ACCEPTING_CIPHER;
		gcm_add_cipher(g,0,iv,niv,NULL); /* GHASH(H,0,IV) */
		gcm_wrap(g);
		for (i=0;i<16;i++) {g->a.f[i]=g->stateX[i];g->Y_0[i]=g->a.f[i];g->stateX[i]=0;}
		g->lenA[0]=g->lenC[0]=g->lenA[1]=g->lenC[1]=0;
	}
	g->status=GCM_ACCEPTING_HEADER;
}
void AES_GCM_DECRYPT(octet *K,octet *IV,octet *H,octet *C,octet *P,octet *T)
{
	gcm g;
	gcm_init(&g,K->len,K->val,IV->len,IV->val);
	gcm_add_header(&g,H->val,H->len);
	gcm_add_cipher(&g,GCM_DECRYPTING,P->val,C->len,C->val);
	P->len=C->len;
	gcm_finish(&g,T->val); 
	T->len=16;
}
/*! \brief Decrypt data using AES GCM
 *
 *  AES is run as a block cypher in the GCM  mode of operation. The key size is 128 bits.
 *  This function will decrypt any data length.
 *
 *  @param  key           128 bit secret key
 *  @param  IV            96 bit initialization vector
 *  @param  header        Additional authenticated data (AAD). This data is authenticated, but not decrypted.
 *  @param  ciphertext    Encrypted data.
 *  @return plaintext     Decrypted data. It is the same length as the ciphertext.
 *  @return tag           128 bit authentication tag.
 *  @return rtn           Returns 0 if successful or else an error code
 */
AESGCM_EXPORT int aesGcmDecrypt(char* key, char* IV, char* header, int headerLength,
                                char* ciphertext, int ciphertextLength, char* plaintext,
                                char* tag)
{
    gcm g;
    int keyLength=AS;
    int tagLength=AS;
    gcm_init(&g,keyLength,key,IVLength,IV);

    if(!gcm_add_header(&g,header,headerLength))
    {
        return AES_INIT_ERROR;
    }

    if(!gcm_add_cipher(&g,GCM_DECRYPTING,plaintext,ciphertextLength,ciphertext))
    {
        return AES_DECRYPT_ERROR;
    }

    gcm_finish(&g,tag);
    tagLength=16;
    return 0;
}
Пример #4
0
PlaintextMessage EncryptedMessage::decrypt(const G2& P, const G2& Ppub, G1 D, PFC *pfc) {
    G2 uCalc;
    G2 U = (*autData).getU();
    Big ud_hash = (*pfc).hash_to_aes_key((*pfc).pairing(U,D));
    Big ses_key;
    Big r;
    int nbOfRecipients = (*autData).getNbOfRecipients();

    Big W;
    Big V = (*autData).getV();
    Big rho, rho_hash;
    vector <Big> ws = (*autData).getEncryptedRecipientKeys();
    char P_text[Clen];
    bool integrity = false;

    time_t begin_time = clock();

    int i = 0;
    while(U != uCalc && i < nbOfRecipients){
        // rho = V XOR Hash(e(D,U))
        W=ws.at(i);
        rho = lxor(W, ud_hash);

        // M = W XOR Hash(rho)
        (*pfc).start_hash();
        (*pfc).add_to_hash(rho);
        rho_hash = (*pfc).finish_hash_to_group();
        ses_key = lxor(V, rho_hash);

        // r = Hash(rho,M)
        (*pfc).start_hash();
        (*pfc).add_to_hash(rho);
        (*pfc).add_to_hash(ses_key);
        r = (*pfc).finish_hash_to_group();
        uCalc = (*pfc).mult(P,r);
        i++;
    }
    cout << "ses_key is " << endl << ses_key << endl;

    /*************************************************
    *       AES GCM part of the decryption step      *
    **************************************************/
    to_binary(ses_key, HASH_LEN, sessionKey, TRUE);
    char k1[HASH_LEN/2];
    char iv[HASH_LEN/2];
    char Tdec[TAG_LEN];
    memset(P_text, 0, Clen+1);

    getIV(iv);
    getK1(k1);

    int Alen = (*autData).getLength();
    char A[Alen];
    (*autData).encodeTo(A);
    gcm g;
    gcm_init(&g, HASH_LEN/2, k1, HASH_LEN/2, iv);
    gcm_add_header(&g, A, Alen);
    gcm_add_cipher(&g, GCM_DECRYPTING, P_text, Clen, C);
    gcm_finish(&g, Tdec);

    integrity = true;
    for (int j = 0; j < TAG_LEN; j++) {
        if(Tdec[j] != T[j]) {
            integrity = false;
        }
    }

    if(integrity == false) {
        cout << "Received tag T does not correspond to decrypted T. There are some integrity issues here." << endl;
    } else {
        cout << "Successful integrity check!" << endl;
    }

    message = (string)P_text;

    return PlaintextMessage(message);
}