Example Code Using CryptDecryptMessage

The following example code implements the procedure just presented. Comments show which code fragments pertain to each step in the procedure. The details of the functions and structures can be found in Simplified Message Functions and Data Structures.

//-------------------------------------------------------------
//-------------------------------------------------------------
// EXAMPLE CODE FOR DECRYPTING AN ENCRYPTED MESSAGE USING
// CryptDecryptMessage().
//-------------------------------------------------------------
//-------------------------------------------------------------

//-------------------------------------------------------------
// Get a pointer to the encrypted message. Use the pointers,
// pbEncryptedBlob and cbEncryptedBlob, retrieved in the 
// previous code segment (Step 1).
//-------------------------------------------------------------

// View the encrypted blob.

char*    EncryptedString = new char[(cbEncryptedBlob *2) +1];

// Call a routine to convert the byte blob to ASCII HEX. See the
// function code at the end of this code fragment.
BytesToStr(cbEncryptedBlob, pbEncryptedBlob, EncryptedString);

// Show the string.
AfxMessageBox(EncryptedString);


//-------------------------------------------------------------
// Open the system certificate store (Step 2).
//-------------------------------------------------------------
//HCERTSTORE        hStoreHandle = NULL;

// Call CertOpenSystemStore to open the store.
hStoreHandle = CertOpenSystemStore(hCryptProv, "MY");
if (!hStoreHandle)
{
    AfxMessageBox( "Error Getting Store Handle");
    return;
}

// If the call was successful, the certificate store handle now
// resides at the location pointed to by hStoreHandle.

// Create a "CertStoreArray" (Step 3)
HCERTSTORE        CertStoreArray[] = {hStoreHandle};

//-------------------------------------------------------------
// Initialize the CRYPT_DECRYPT_MESSAGE_PARA structure. (Step 4).
//-------------------------------------------------------------
CRYPT_DECRYPT_MESSAGE_PARA        DecryptParams;
DWORD    DecryptParamsSize = sizeof(DecryptParams);
memset(&DecryptParams, 0, DecryptParamsSize);

DecryptParams.cbSize = DecryptParamsSize;
DecryptParams.dwMsgAndCertEncodingType = MY_ENCODING_TYPE;
DecryptParams.cCertStore = 1;
DecryptParams.rghCertStore = CertStoreArray;

//-------------------------------------------------------------
// Decrypt the message data (Step 5).
//-------------------------------------------------------------
DWORD        cbDecryptedMessage;

// Call CryptDecryptMessage to get the returned data size.
fReturn = CryptDecryptMessage(
          &DecryptParams,
          pbEncryptedBlob,
          cbEncryptedBlob,
          NULL,
          &cbDecryptedMessage,
          NULL);
if(FALSE == fReturn)
    AfxMessageBox( "Error Getting Decrypted Message Size");

// Allocate memory for the returned decrypted data.
BYTE*    pbDecryptedMessage;

pbDecryptedMessage = (BYTE*)malloc(cbDecryptedMessage);
if(!pbDecryptedMessage)
    AfxMessageBox("Memory Allocation Error While Decrypting");

// Call CryptDecryptMessage to decrypt the data.
fReturn = CryptDecryptMessage(
          &DecryptParams,
          pbEncryptedBlob,
          cbEncryptedBlob,
          pbDecryptedMessage,
          &cbDecryptedMessage,
          NULL);
LPSTR    DecryptedString = (LPSTR) pbDecryptedMessage;

if(FALSE == fReturn)
    AfxMessageBox("Error Decrypting The Data");
else
{
    AfxMessageBox("Data Decrypted Successfully");
    AfxMessageBox(DecryptedString);    // Display the string.
}

// If the function call succeeded, the decrypted message now
// resides at the location pointed to by pbDecryptedMessage.

//-------------------------------------------------------------
// Clean up memory.
//-------------------------------------------------------------

fReturn = CertCloseStore(
          hStoreHandle, 
          CERT_CLOSE_STORE_CHECK_FLAG);
if(FALSE == fReturn)
    AfxMessageBox("Store Closed After Decryption - \n"
                  "Not All Certs or CRLs Were Freed");

free(pbEncryptedBlob);
free(pbDecryptedMessage);
delete [] EncryptedString;


//************************************************************
// BytesToStr() - Converts the bytes into CHAR hex. Needs
// (cb * 2 + 1) * sizeof(CHAR) bytes of space in sz.
//************************************************************
static void BytesToStr(DWORD cb, void* pv, LPSTR sz)
{
    
    BYTE* pb = (BYTE*) pv;
    for (DWORD i = 0; i<cb; i++)
    {
        int b;

        b = (*pb & 0xF0) >> 4;
        *sz++ = (b <= 9) ? b + '0' : (b - 10) + 'A';
        b = *pb & 0x0F;
        *sz++ = (b <= 9) ? b + '0' : (b - 10) + 'A';
        
        pb++;
    }
    *sz++ = 0;
}