title: How to verify intermediate CA
body: <p>I have SSL connection to server. I had root CA and it was also the server certificate. I don't have a client certificate, when connection starts client verifies the server certificate and if it's valid connects. Now I've created Intermediate CA from my root CA, and replace it as server certificate, now I want the client to verify if the server certificate is trusted by root CA, I do it in C++ with openSSL API. how can I do it? here is what i've tried but it needs something more.</p>
  
  <pre><code>  const Char *caCert = "/home/omar/CA/host/host_rsa_key.crt";
  
        X509_LOOKUP *lookup = X509_STORE_add_lookup(ctx_ -&gt;  cert_store,X509_LOOKUP_file());
  
  
        result=X509_LOOKUP_load_file(lookup,caCert,X509_FILETYPE_PEM);
        if(result != 1)
        {
          log()&lt;&lt;ERROR! Cannot load file to lookup structure\n";
          return;
        }
  
  
        SSL_CTX_sess_set_new_cb(ctx_, handshakeCallback);
  
        SSL_CTX_set_verify(ctx_, SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
                           verifyCallback);
        SSL_CTX_set_verify_depth(ctx_, 8);
  </code></pre>
  
  <p>this is where I load all certificate into ssl_ctx.</p>
  
  <p>I have verifyCallback function which calls verifyCertificate() method here it is</p>
  
  <pre><code>  Int verifyCertificate(Int preverify, X509_STORE_CTX *store)
    {
    X509 *cert = NULL;
   // X509_NAME *name = NULL;
  
    SSL *ssl = NULL;
  
   Int certDepth = -1;
   Int certErr   = 0;
  
   Char *certHost = NULL;
   Char *certHash = NULL;
   Char *certData = NULL;
  
  
   cert = X509_STORE_CTX_get_current_cert(store);
  
   if (cert == NULL)
  
   log() &lt;&lt; " ERROR! Failed to get certificate.\n";
  
  
  goto VerifyCertificateError;
  }
  
  
  
   certDepth = X509_STORE_CTX_get_error_depth(store);
   certErr = X509_STORE_CTX_get_error(store);
  
  
  
  ssl = (SSL *) X509_STORE_CTX_get_ex_data(store, SSL_get_ex_data_X509_STORE_CTX_idx());
  
  if (ssl == NULL)
  {
   log() &lt;&lt;  ERROR! Failed to get SSL context from store context.\n";
  
   goto VerifyCertificateError;
  }
  
  if (preverify == 0)
  {
  //
  // Self signed certificate allowed, SSH host auth style.
  //
  
  if (certErr == X509_V_ERR_DEPTH_ZERO_SELF_SIGNED_CERT)
  {
  
    log() &lt;&lt; " Certificate preverify failed on self";
  
    return 1;
  }
  else if (certErr == X509_V_ERR_CERT_NOT_YET_VALID)
  {
  
    log() &lt;&lt; Allowing not yet valid certificate.\n";
  
    return 1;
   }
   else if (certErr == X509_V_ERR_CERT_HAS_EXPIRED)
   {
  
    log() &lt;&lt; " Allowing expired certificate.\n";
  
  
    return 1;
  }
  else if(certErr == X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT)
  {
  
    log()&lt;&lt;" Unable to get issuer cert.\n"
  
  
    return 1;
  }
  
  
  if (certDepth == 0)
  {
   if (parseCertificate(store, certHost, certHash, certData) == 0)
   {
     log() &lt;&lt; "Encryptable: ERROR! Failed to parse certificate.\n";
    goto VerifyCertificateError;
  }
  
  
    goto VerifyCertificateError;
  }
  
  
  if (authCallback_(certHost, certHash, certData, certCallback_,
                        callbackParameter_) == 0)
   {
  
    log() &lt;&lt; " ERROR! Failed to authorize "
          &lt;&lt; "the server certificate.\n";
  
    goto VerifyCertificateError;
  
  
  if (certData != NULL)
  {
    delete [] certData;
  }
  
  return 0;
  }
  </code></pre>