idgen.c 6.43 KB
#include <openssl/rsa.h>
#include <openssl/bn.h>
#include <stdlib.h>
#include <sha1.h>
#include <PR/bbmetadata.h>
#include <PR/bbcert.h>
#include <openssl/rand.h>
#include <stdlib.h>
#include <bb_nn.h>
#include <util.h>

#define MAX_KEY_SIZE 4096

#define DEBUG


#define SIZE_RSA_CERTBLOB_WORDS 228
#define SIZE_BB_CERTBLOB_WORDS 179
#define BB_ECC_CERT_SIGNED_BYTES (sizeof(BbEccCert) - sizeof(BbGenericSig))
   
     
int main(int argc, char **argv){
    RSA *prsa;
    
    int count;
    int size, newsize, i, e_size, n_size;
    int num_bits, num_bytes;  
    unsigned char hash_data[20];
    
    unsigned char e_string[512];
    unsigned char n_string[512];
    
    unsigned long certsign[128];
    unsigned long certexponent;
    unsigned char subjectname[64];
    unsigned char issuername[64];
    unsigned char signature[512];
    unsigned long certdata[SIZE_RSA_CERTBLOB_WORDS];
    unsigned long *bbcertdata;

    char *temp_string;
    unsigned char *padded_data;
    unsigned char *verify;
    unsigned long number;
    
    SHA1Context sha;
    FILE *certptr;
    FILE *ecccertptr;
    FILE *rsawriteptr;
    FILE *rsareadptr;

    BbEccCert bbcert;
   
    certptr = fopen("ida.sys", "w");
      
    if((certptr == 0)){
        fprintf(stderr,"cannot open file to write \n");
	exit(1);
    }

  
    padded_data = (unsigned char *) malloc(512);
    verify = (unsigned char *) malloc(512);
    
    /* input file name is root key data, use it */

    if(argc ==3){
        prsa = RSA_new();
        rsareadptr = fopen(argv[1], "r");
        readRsaData(rsareadptr, prsa);

	   
	ecccertptr = fopen(argv[2], "r");
	if(ecccertptr ==0){
	  fprintf(stderr,"cannot open ecc cert to read\n");
	  exit(1);
	}
	fread((u8 *) &bbcert, sizeof(BbEccCert), 1, ecccertptr);
	bbcertdata = malloc(sizeof(BbEccCert));
	memcpy((u8 *)bbcertdata, (u8 *)&bbcert, sizeof(BbEccCert));
    }
    else{
      printf("usage: %s root.key bb-cert-file-name\n", argv[0]);
      exit(1);
    }
    if( validate(prsa, 4096) != 0){
      fprintf(stderr,"Key validation failed\n");
    }
    fclose(rsareadptr);
    free(prsa);

/* generate the two certs for cp chain and save and validate */
    /* CP cert keys */
    prsa = RSA_new();
    
    num_bits = 2048;
    num_bytes = num_bits/8;
    prsa = RSA_generate_key(num_bits, 3, NULL, NULL);
    
    /* write out data */

    rsawriteptr = fopen("msbindata", "w");
        
    saveRsaData(rsawriteptr, prsa);
    fclose(rsawriteptr);
    
    /* validate */
    if(validate(prsa, 2048) != 0){
      fprintf(stderr,"Key validation failed\n");
    }

    /* sign BB cert */
        
    /* compute hash */
    SHA1Reset(&sha);
    SHA1Input(&sha, (u8 *)&(bbcertdata[0]),BB_ECC_CERT_SIGNED_BYTES);
    SHA1Result(&sha, hash_data);
    
    RSA_padding_add_PKCS1_type_2(padded_data, num_bytes, hash_data, 20);
#ifdef DEBUG
    for (i = 0; i < 20; i++){
        printf("hash[%d] of bb cert= %02x\n",i,hash_data[i]);
    }

    
    for (i = 0; i < num_bytes; i++){
        printf(" padded data = %02x\n", padded_data[i]);
    }
#endif
    
    size = RSA_private_encrypt(num_bytes, 
                      padded_data, signature, prsa, RSA_NO_PADDING);

    
    
/* zero the result: just verifying for fun using RSA */
    for(i = 0; i < num_bytes; i++){
        verify[i]  = 0;
    }
    newsize = RSA_public_decrypt(RSA_size(prsa), signature, verify, prsa, RSA_NO_PADDING);

#ifdef DEBUG
    printf("size of decrypted = %d\n", newsize);
    for(i =0; i< newsize; i++){
        printf("BB cert signature = %02x verify [%d] = %02x padded_data = %02x\n", signature[i] , i, verify[i], padded_data[i]);
    }
#endif

    /* initialise bigint */

    e_size = BN_bn2bin(prsa->e, e_string);
    n_size = BN_bn2bin(prsa->n, n_string);

#define get_word(x)	*(u32*)(x)
    certexponent = get_word(e_string);
    count = 0;
    for(i=0; i< n_size; i= i+4){
        certsign[count] = htonl(get_word(signature + i));
        count++;
    }
   
    /* copy the sign to its rightful place */
        
    for (i = 0; i <  num_bytes/4; i++){
        bbcertdata[(BB_ECC_CERT_SIGNED_BYTES/4) + i] = htonl(certsign[i]);
        
    }
        
    /* finally write out BB cert data */
    /* first write out number of certs in big endian */
    number = htonl(3);
    fwrite((void *)&number, 4, 1, certptr);
    fwrite((void *)bbcertdata, 4, sizeof(BbEccCert)/4, certptr);
    

    /* till here signing bb cert */
         
    /* assign the names */
    /* null data first */
    for(i = 0; i < 64; i++){
        issuername[i] = 0;
    }
    for( i = 0; i < 64; i++){
        subjectname[i] = 0;
    }
    /*
    temp_string = "Root-MSCA00010203";
    */
    temp_string = "Root-MSCA00000100";
    for(i = 0; i< strlen(temp_string); i++){
        issuername[i] = temp_string[i];
    }
    /*
    temp_string = "MS0a0b0c0d";
    */
    temp_string = "MS00000101";
    for(i =0; i < strlen(temp_string); i++){
        subjectname[i] = temp_string[i];
    }
#ifdef DEBUG
    for( i =0; i< 64; i++){
        printf("issuername = %02x\n", issuername[i]);
    }
    for( i =0; i< 64; i++){
        printf("subjectname = %02x\n", subjectname[i]);
    }
#endif

    /* the content server cert */
    free(prsa);
    /* compute keys for MSCA for signing MS cert RSA 2048 bits */
    printf("signing the MS cert\n");

    prsa = RSA_new();
    
    num_bits = 2048;
    num_bytes = num_bits/8;
    prsa = RSA_generate_key(num_bits, 3, NULL, NULL);
        
        
    /* write out data */
    rsawriteptr = fopen("mscabindata", "w");
        
    saveRsaData(rsawriteptr, prsa);
    fclose(rsawriteptr);
    
    /* validate */
    if(validate(prsa, 2048) != 0){
      fprintf(stderr,"Key validation failed\n");
    }
    generateCertFromKeyData("msbindata", "mscabindata", subjectname, issuername, certdata);
    
    fwrite((void *)&certdata, 4, 228, certptr);
    /* create custom cert of ms ca cert */
        /* null data */

    for(i = 0; i < 64; i++){
      issuername[i] = 0;
    }
    for( i = 0; i < 64; i++){
      subjectname[i] = 0;
    }
    temp_string = "Root";
    for(i = 0; i< strlen(temp_string); i++){
      issuername[i] = temp_string[i];
    }
    /*
    temp_string = "MSCA00010203";
    */
    temp_string = "MSCA00000100";
    for(i =0; i < strlen(temp_string); i++){
      subjectname[i] = temp_string[i];
    }
    generateCertFromKeyData("mscabindata", argv[1], subjectname, issuername, certdata);

    fwrite((void *)&certdata, 4, 228, certptr);
        
    
    /* manufacturing certs done */
    if(prsa) free(prsa);
    return 0;
}