Question:
We're currently looking for a PKI encryption solution that can be accessed from the Delphi XE2 development environment. We need to be able to produce a public / private key pair and encrypt files using the the PKI cryptography method.
I've downloaded your Delphi DLL trial software and I'm looking at your code examples ("DSA Generate Key", "Encrypt File to PKCS7 .p7m"), The keys are generated successfully however I'm getting the error detailed below when attempting to use the public .PEM or .DER to encrypt a file.
Please can you provide any help?
ChilkatLog: CkEncryptFile: DllDate: Dec 13 2012 UnlockPrefix: 30-day trial Username: *** Architecture: Little Endian; 32-bit Language: C++ Builder XE2 VerboseLogging: 0 hcCurDate: Mon, 13 May 2013 10:13:46 +0100 hcExpire: 3/2013 inputFile: [c:\temp\test.txt] outputFile: [c:\temp\test.txt.p7m] encryptionMethod: 1 algorithm: pki buildRecipientInfo: issuerSerialNum: Failed to get certificate's serial number Failed to create IssuerAndSerial ASN.1 --buildRecipientInfo Failed to build RecipientInfo ASN.1 Failed to build PKCS7 enveloped. Failed. --CkEncryptFile --ChilkatLog
Here's the code that I'm using from your example…
CkCrypt2_putCryptAlgorithm(crypt,'PKI');// Indicate the inner symmetric encryption algorithm to be used. // possible values are "aes", "des", "3des", and "rc2". // For this example, we'll use 256-bit AES encryption. CkCrypt2_putPkcs7CryptAlg(crypt,'aes'); CkCrypt2_putKeyLength(crypt,256);
// To encrypt, only a certificate w/ public key is needed. // (The certificate w/ private key is required for decryption.)
// The LoadFromFile method can load virtually any certificate format: // 1. DER encoded binary X.509 (.CER) // 2. Base-64 encoded X.509 (.CER) // 3. Cryptographic Message Syntax Standard - PKCS #7 Certificates (.P7B) // 4. PEM format encryptCert := CkCert_Create(); success := CkCert_LoadFromFile(encryptCert, 'dsa_pub.der'); if (success <> True) then begin Memo1.Lines.Add(CkCert__lastErrorText(encryptCert)); Exit; end;
// Tell the crypt object to use the certificate for encrypting: CkCrypt2_AddEncryptCert(crypt,encryptCert);
// Encrypt a file, producing a .p7m as output. // The input file is unchanged, the output .p7m contains the encrypted // contents of the input file. inFile := 'c:temptest.txt'; outFile := 'c:temptest.txt.p7m'; success := CkCrypt2_CkEncryptFile(crypt,inFile,outFile);
There is a conceptual misunderstanding between what is a digital certificate and what is a DSA/RSA key. A digital certificate is something that among other things, contains a DSA/RSA public key. A digital certificate contains information about the certificate owner (such as name, address, company name, etc.), it contains information about the issuing certificate, date of issue, etc., and it also contains the public-part of an RSA/DSA key. (The private components of the RSA/DSA are not stored within a certificate itself. They are typically stored in some sort of a protected keystore, or they can be contained in a secure PFX / .p12 file.)
In your code sample above, you created only the DSA key -- not an actual certificate. The solution is to instead create an RSA key (not DSA) and then use "Chilkat RSA" to encrypt using the bare RSA key. See this example: http://www.example-code.com/delphiDll/rsa_encryptStrings.asp
The "PKI" encryption/signature related methods in "Chilkat Crypt" (i.e. CkCrypt2) use digital certificates, whereas the "Chilkat RSA" methods work with bare RSA keys. Chilkat does not currently have (at the time of this writing, which is 13-May-2013) the ability to create a digital certificates. In any case, if it did, it would only be able to create self-signed certs. It takes a certificate authority to create certificates that are trusted by others outside your organization.