PKCS7 messages
From OpenCA::Wiki
[edit]
Loading a PKCS#7 Message
This example shows how to load a PKCS#7 file and get the embedded data from the file:
#include <libpki/pki.h>
int main () {
PKI_X509_PKCS7 *p7 = NULL;
BIO *p7bio = NULL;
PKI_X509_CERT_STACK *sk_cert = NULL;
PKI_MEM * mem = NULL;
PKI_init_all();
// Loads the PKCS7 file ("data.der")
if((p7 = PKI_X509_PKCS7_get ( "data.der", NULL, NULL )) == NULL ) {
exit(1);
}
// Gets the data from a PKCS7 object
if((mem = PKI_X509_PKCS7_get_data( p7, NULL, NULL )) == NULL ) {
printf("ERROR: Can not get data!\n");
exit(1);
}
// Naively prints out the data from the PKI_MEM data structure
printf("DATA:\n%s\n", mem->data);
// Saves the file in PEM format
PKI_X509_PKCS7_put ( p7, PKI_DATA_FORMAT_PEM,
"output/p7.pem", NULL, NULL, NULL );
return 0;
}
[edit]
Create a new PKCS7
This example shows how to create a new PKCS7 and encrypt its contents for a recipient (cacert.pem)
#include <libpki/pki.h>
int main () {
PKI_MSG_REQ *r = NULL;
PKI_X509_CERT *cacert = NULL;
PKI_TOKEN *tk = NULL;
PKI_MEM_STACK *mem_sk = NULL;
PKI_X509_PKCS7 *p7 = NULL;
BIO *p7bio = NULL;
PKI_MEM *mm = NULL;
// This is the data to be transmitted
char *data = "aaaaaaaaaaaaaaaaavvvvvvvvvvvvvvbbbbbbbbbbbbb";
PKI_init_all();
// Load the cacert.pem certificate
if((cacert = PKI_X509_CERT_get( "cacert.pem", NULL, NULL )) == NULL ){
printf("ERROR, can not load cacert.pem!\n\n");
exit(1);
}
// We need a new PKI_TOKEN to sign with - let's create a new one,
// a new keypair, and a self-signed certificate
if((tk = PKI_TOKEN_new_null()) == NULL ) {
printf("ERROR, can not create a new token!\n");
exit ( 1 );
}
if((PKI_TOKEN_new_keypair(tk, 1024, NULL)) == PKI_ERR){
printf("ERROR, can not generate new keypair!\n");
exit(1);
}
PKI_TOKEN_set_cacert( tk, cacert );
/* We need a signer to sign the P7! */
PKI_TOKEN_new_req ( tk, "CN=Max2, O=OpenCA", NULL );
PKI_TOKEN_self_sign( tk, NULL, NULL, 3600*24*30, NULL );
// Let's create a new PKCS7 (signed and encrypted)
if((p7 = PKI_X509_PKCS7_new( PKI_X509_PKCS7_TYPE_SIGNEDANDENCRYPTED )) == NULL ) {
printf("ERROR, can not gen new PKCS7\n");
exit(1);
}
// Now we add the recipient (in this case, the newly created certificate)
PKI_X509_PKCS7_add_recipient ( p7, tk->cert );
// Here we add the signer information from the PKI_TOKEN
PKI_X509_PKCS7_add_signer_tk ( p7, tk, NULL );
// All we need to do now is to "encode" the data we want to encode in the
// final PKCS7 file
if(PKI_X509_PKCS7_encode(p7, data, strlen(data)+1 ) == PKI_ERR) {
printf("ERROR!!!!\n\n");
exit(1);
}
// Now we save the new PKCS#7 file
PKI_X509_PKCS7_put( p7, PKI_DATA_FORMAT_PEM, "output/p7_enc.pem", NULL, NULL, NULL );
// As a test, we decrypt the new PKCS7 data by using our certificate
if((mm = PKI_X509_PKCS7_get_data( p7, tk->keypair, tk->cert)) == NULL ){
printf("ERROR::Can not decrypt!\n");
} else {
printf("DATA %d \n => %s <== END\n\n", mm->size, mm->data );
}
return 0;
}
[edit]
Adding Signed Attributes
This example shows how to add a signed attribute to a PKCS#7 object. For simplicity, we assume a p7 has already been created. We omit the PKI_TOKEN creation/load part.
#include <libpki/pki.h>
int main () {
PKI_X509_CERT *cacert = NULL;
PKI_TOKEN *tk = NULL;
PKI_MEM_STACK *mem_sk = NULL;
PKI_X509_PKCS7 *p7 = NULL;
PKI_X509_CERT_STACK *sk_cert = NULL;
PKI_X509_ATTRIBUTE *attr = NULL;
PKI_X509_CRL * crl = NULL;
char *data = "THIS IS THE DATA!";
....
// Here we create the new Attribute
attr = PKI_X509_ATTRIBUTE_new (
PKI_X509_SCEP_ATTRIBUTE_get_nid (
SCEP_ATTRIBUTE_MESSAGE_TYPE),
V_ASN1_PRINTABLESTRING, "Pippo", 6);
// Check for errors
if( attr == NULL ) {
printf("ERROR::Can not create Attribute!\n\n");
exit ( 1 );
} else {
int i = 0;
// Adds the signed attribute
i = PKI_X509_PKCS7_add_signed_attribute( p7, attr );
printf("ADDED SIGNED ATTRIBUTE => RESULT is %d\n", i );
}
// Why not adding a CRL to the PKCS7 ?
crl = PKI_X509_CRL_get ( "crl.pem", NULL, NULL );
PKI_X509_PKCS7_add_crl ( p7, crl );
// When ready, we finalize the data structure by encoding it
if( PKI_X509_PKCS7_encode( p7, data, strlen(data)+1 ) == PKI_ERR){
printf("ERROR::Can not Sign!!!!\n\n");
}
// Let's save the PKCS7 in B64
PKI_X509_PKCS7_put ( p7, PKI_DATA_FORMAT_B64,
"output/test_6_p7.b64", NULL, NULL, NULL );
return 0;
}

