Dear all,

I'm struggling with programatically verifying a certificate which is solely 
stored in memory, i. e. not on the file system. The certificate and the CA seem 
to be fine though, because when I extract them from memory and store them as a 
file, and use the `openssl verify`, verification is successful. Hence I suspect 
my code is faulty.

Unfortunately, I'm under the impression that validating certificates which 
exist solely in memory is a niche application. I was yet not able to find a 
comprehensive tutorial or even a code sample on the internet. Hence, I hope you 
can help me.

Below I'm posting my sample code. (I have stripped the certificate and CA raw 
data, tough.) It can be compiled an run under a GNU/Linux system.
When this code is run, OpenSSL emits a "certificate signature failure" with an 
error depth of 0.

Thanks a lot!
Manuel

============

#include <openssl/x509.h>
#include <stdexcept>
#include <iostream>

unsigned char g_authority[] = { 0x30, 0x82, 0x03, 0x00 /* and so on */ };
unsigned char g_cert[] = { 0x30, 0x82, 0x02, 0x9b /* and so on */ };

int main(int, char**)
{
        // This holds the return codes and gets reused for most function calls
        int rc = 0;

        // Make a new store
        X509_STORE *x509_store = X509_STORE_new();
        if (x509_store == NULL) {
                throw std::runtime_error("X509_STORE_new() failed");
        }

        // Load and convert the authoritys certificate to a compatible form
        X509 *auth_cert = NULL;
        {
                const unsigned char* auth_cert_ptr = g_authority;
                auth_cert = d2i_X509(NULL, &auth_cert_ptr, sizeof(g_authority));
                if (auth_cert == nullptr) {
                        throw std::runtime_error("d2i_X509() failed for 
authoritys certificate");
                }
        }

        // Add the authoritys certificate to the store
        rc = X509_STORE_add_cert(x509_store, auth_cert);
        if (rc != 1) {
                throw std::runtime_error("X509_STORE_add_cert() failed");
        }

        // Make a new store context
        X509_STORE_CTX *x509_store_ctx = X509_STORE_CTX_new();
        if (x509_store_ctx == NULL) {
                throw std::runtime_error("X509_STORE_CTX_new() failed");
        }

        // Load and convert the certificate to be verified to a compatible form
        X509 *myself = NULL;
        {
                const unsigned char *my_cert_ptr = g_cert;
                myself = d2i_X509(NULL, &my_cert_ptr, sizeof(g_cert));
                if (myself == NULL) {
                        throw std::runtime_error("d2i_X509() failed for own 
certificate");
                }
        }

        rc = X509_STORE_CTX_init(x509_store_ctx, x509_store, myself, NULL);
        if (rc != 1) {
                throw std::runtime_error("X509_STORE_CTX_init() failed");
        }

        rc = X509_verify_cert(x509_store_ctx);

        X509_STORE_free(x509_store);
        X509_STORE_CTX_free(x509_store_ctx);

        if (rc > 0) {
                std::cout << 
X509_verify_cert_error_string(X509_STORE_CTX_get_error(x509_store_ctx)) << 
std::endl;
                return 0;
        } else {
                std::cerr << 
X509_verify_cert_error_string(X509_STORE_CTX_get_error(x509_store_ctx)) << 
std::endl;
                std::cerr << "Error depth: " << 
X509_STORE_CTX_get_error_depth(x509_store_ctx) << std::endl;
                return 1;
        }
}
-- 
openssl-users mailing list
To unsubscribe: https://mta.openssl.org/mailman/listinfo/openssl-users

Reply via email to