importRSAKeyandCert.js

Summary

Example for importing a RSA key from pkcs8 file and X.509 cert from pem file


Class Summary
KeyImport  

/**
 *  ---------
 * |.##> <##.|  SmartCard-HSM Support Scripts
 * |#       #|
 * |#       #|  Copyright (c) 2011-2015 CardContact Software & System Consulting
 * |'##> <##'|  Andreas Schwier, 32429 Minden, Germany (www.cardcontact.de)
 *  ---------
 *
 * Consult your license package for usage terms and conditions.
 *
 * @fileoverview Example for importing a RSA key from pkcs8 file and X.509 cert from pem file
 */

var SmartCardHSM = require('scsh/sc-hsm/SmartCardHSM').SmartCardHSM;
var SmartCardHSMInitializer = require("scsh/sc-hsm/SmartCardHSM").SmartCardHSMInitializer;
var DKEK = require('scsh/sc-hsm/DKEK').DKEK;
var SmartCardHSMKeySpecGenerator = require("scsh/sc-hsm/SmartCardHSM").SmartCardHSMKeySpecGenerator;
var HSMKeyStore = require("scsh/sc-hsm/HSMKeyStore").HSMKeyStore;
var PKIXCommon = require('scsh/x509/PKIXCommon').PKIXCommon;
var PKCS8 = require('scsh/pkcs/PKCS8').PKCS8;
var File = require('scsh/file/File').File;
var X509CertificateGenerator = require("scsh/x509/X509CertificateGenerator").X509CertificateGenerator;



function KeyImport(card) {
	this.crypto = new Crypto();
	this.card = card;
	this.sc = new SmartCardHSM(card);
	this.dkekshare = new ByteString("0000000000000000000000000000000000000000000000000000000000000000", HEX);
}


KeyImport.prototype.issueCert = function(priKey, pubKey) {
	var generator = new X509CertificateGenerator(this.crypto);

	generator.reset();
	generator.setSerialNumber(new ByteString("01", HEX));
	generator.setSignatureAlgorithm(Crypto.RSA);
	var issuer = { C:"UT", O:"ACME Corporation", CN:"Test-CA" };
	generator.setIssuer(issuer);
	var t = new Date();
	generator.setNotBefore(t);
	generator.setNotAfter(PKIXCommon.addDays(t, 180));
	var subject = { C:"UT", O:"Utopia CA", OU:"ACME Corporation", CN:"Joe Doe" };
	generator.setSubject(subject);

	generator.setPublicKey(pubKey);

	generator.addKeyUsageExtension(	PKIXCommon.digitalSignature |
							PKIXCommon.keyCertSign |
							PKIXCommon.cRLSign );

	generator.addBasicConstraintsExtension(true, 0);
	generator.addSubjectKeyIdentifierExtension();
	generator.addAuthorityKeyIdentifierExtension(pubKey);

	var cert = generator.generateX509Certificate(priKey);

	print(cert);
	return cert;
}



KeyImport.prototype.createTestKey = function() {
	var prk = new Key();
	prk.setType(Key.PRIVATE);
	var puk = new Key();
	puk.setType(Key.PUBLIC);
	puk.setSize(2048);
	this.crypto.generateKeyPair(Crypto.RSA, puk, prk);

	var p8 = PKCS8.encodeKeyUsingPKCS8Format(prk);
	print(p8.toString(BASE64));

	var cert = this.issueCert(prk, puk);
	print(cert.getBytes().toString(BASE64));
}



KeyImport.prototype.readKey = function(filename) {
	var f = new File(filename);
	var c = f.readAllAsString();
//	print(c);
	var bin = PKIXCommon.parsePEM("PRIVATE KEY", c);
	return PKCS8.decodeKeyFromPKCS8Format(bin);
}



KeyImport.prototype.readCert = function(filename) {
	var cert = new X509(filename);
	print(cert);
	return cert;
}



KeyImport.prototype.initializeHSM = function() {
	print("Initialize with a single key domain");
	var sci = new SmartCardHSMInitializer(this.card);
	sci.setKeyDomains(1);
	sci.initialize();

	print("Create DKEK domain with DKEK " + this.dkekshare.toString(HEX));
	if (this.dkekshare.byteAt(0) == 0) {
		print("WARNING: This seems to be the default dummy DKEK. Please change to a secure value");
		print("         when used in production.");

	}
	var sc = new SmartCardHSM(this.card);
	sc.createDKEKKeyDomain(0, 1);
	sc.importKeyShare(0, this.dkekshare);
}



KeyImport.prototype.importKeyAndCert = function(key, cert) {
	// Create DKEK encoder and import share
	var dkek = new DKEK(this.crypto);
	dkek.importDKEKShare(this.dkekshare);

	var puk = cert.getPublicKey();
	var keysize = puk.getComponent(Key.MODULUS).length * 8;
	var skid = cert.getSubjectKeyIdentifier();

	var blob = dkek.encodeKey(key, puk);
//	dkek.dumpKeyBLOB(blob);

	print("Importing key and certificate");
	var ks = new HSMKeyStore(this.sc);
	var hnd = ks.importRSAKey("ImportedRSAKey", blob, keysize, skid);
	ks.storeEndEntityCertificate(hnd, cert);
}



// Create card access object
var card = new Card(_scsh3.reader);

card.reset(Card.RESET_COLD);


var keyimport = new KeyImport(card);

// keyimport.createTestKey();

if ((typeof(pkcs8file) == "undefined") || (pkcs8file == null)) {
	var pkcs8file = "";
}

pkcs8file = Dialog.prompt("Select PKCS#8 file with private key", pkcs8file, null, "*.pkcs8");
assert(pkcs8file != null, "User abort");

var key = keyimport.readKey(pkcs8file);

print(key.getSize());



if ((typeof(certfile) == "undefined") || (certfile == null)) {
	var certfile = "";
}

certfile = Dialog.prompt("Select file with X.509 certificate in PEM format", certfile, null, "*.pem");
assert(certfile != null, "User abort");

var cert = keyimport.readCert(certfile);

print(cert);
keyimport.initializeHSM();
keyimport.importKeyAndCert(key, cert);


Documentation generated by JSDoc on Sat Feb 24 15:17:19 2024