itayb
itayb

Reputation: 149

Converting PEM to DER in C++

I have a certificate in PEM format that I want to convert it to DER format using OpenSLL functions in C++.

How can I do it?

Thanks.

Upvotes: 3

Views: 9097

Answers (3)

ABD
ABD

Reputation: 300

You can do it without using OpenSSL functions. Try this-

int CertConv_pem2der(const uint8_t *pem, uint32_t plen, uint8_t **der,
                 uint32_t *dlen)
{
  int value = 0;
  int i;
  int j;
  int padZero = 0;
  uint8_t *derPtr;
  uint32_t derLen;

  if ((pem == NULL) || (der == NULL))
  {
    return (-1);
  }

  for (i = plen; pem[i - 1] == '='; i--)
  {
    padZero++;
  }

  /* Base64 decode: 4 characters to 3 bytes */
  derLen = (plen / 4) * 3;
  derPtr = (uint8_t *) malloc(derLen);
  if (!derPtr)
  {
    return (-1);
  }

  for (i = 0, j = 0; (i + 3) < plen && (j + 2) < derLen; i += 4, j += 3)
  {
    value = (base64Decode(pem[i]) << 18) + (base64Decode(pem[i + 1]) << 12)
            + (base64Decode(pem[i + 2]) << 6) + base64Decode(pem[i + 3]);

    derPtr[j] = (value >> 16) & 0xFF;
    derPtr[j + 1] = (value >> 8) & 0xFF;
    derPtr[j + 2] = value & 0xFF;
  }

  /* Actual length of buffer filled */
  *dlen = derLen - padZero;
  *der = derPtr;

  return (0);
}


static uint8_t base64Decode(uint8_t ch)
{
  uint8_t ret = 0;
  if (ch >= 'A' && ch <= 'Z')
  {
    ret = ch - 'A';
  }
  else if (ch >= 'a' && ch <= 'z')
  {
    ret = ch - 'a' + 26;
  }
  else if (ch >= '0' && ch <= '9')
  {
    ret = ch - '0' + 52;
  }
  else if (ch == '+')
  {
    ret = 62;
  }
  else if (ch == '/')
  {
    ret = 63;
  }

  return (ret);
}

Upvotes: 2

user1438832
user1438832

Reputation: 493

Try this -

void convert(const unsigned char * pem_string_cert,char* certificateFile)
{
    X509* x509 = NULL;
    FILE* fd = NULL;

    BIO *bio;

    bio = BIO_new(BIO_s_mem());
    BIO_puts(bio, pem_string_cert);
    x509 = PEM_read_bio_X509(bio, NULL, NULL, NULL);

    fd = fopen(certificateFile,"w+");
    if(fd) 
    {
            i2d_X509_fp(fd, x509);
    }
    else 
    {
         printf("can't open fd");
    }
    fclose(fd);
}

Upvotes: 1

user1438832
user1438832

Reputation: 493

You can do it like -

#include <stdio.h>
#include <openssl/x509.h>
#include <openssl/pem.h>
#include <openssl/err.h>

void convert(char* cert_filestr,char* certificateFile)
{
    X509* x509 = NULL;
    FILE* fd = NULL,*fl = NULL;

    fl = fopen(cert_filestr,"rb");
    if(fl) 
    {
        fd = fopen(certificateFile,"w+");
        if(fd) 
        {
            x509 = PEM_read_X509(fl,&x509,NULL,NULL);
            if(x509) 
            {
                 i2d_X509_fp(fd, x509);
            }
            else 
            {
                printf("failed to parse to X509 from fl");
            }
            fclose(fd);
        }
        else
        {
             printf("can't open fd");
        }
        fclose(fl);
    }
    else 
    {
         printf("can't open f");
    }
}


int main()
{
    convert("abc.pem","axc.der");
    return 0;
}

Upvotes: 2

Related Questions