Skip to content

Commit

Permalink
#10 want to be able to make openssh certs with ed25519
Browse files Browse the repository at this point in the history
#11 openssh RSA certs being produced with SHA256 signatures
Reviewed by: Cody Mello <[email protected]>
  • Loading branch information
Alex Wilson committed Jul 28, 2016
1 parent bf3f83c commit 079f792
Show file tree
Hide file tree
Showing 5 changed files with 58 additions and 8 deletions.
13 changes: 11 additions & 2 deletions lib/certificate.js
Original file line number Diff line number Diff line change
Expand Up @@ -128,10 +128,19 @@ Certificate.prototype.isSignedByKey = function (issuerKey) {
};

Certificate.prototype.signWith = function (key) {
utils.assertCompatible(key, PrivateKey, [1, 2], 'key');
var fmts = Object.keys(formats);
var didOne = false;
for (var i = 0; i < fmts.length; ++i) {
if (fmts[i] !== 'pem')
formats[fmts[i]].sign(this, key);
if (fmts[i] !== 'pem') {
var ret = formats[fmts[i]].sign(this, key);
if (ret === true)
didOne = true;
}
}
if (!didOne) {
throw (new Error('Failed to sign the certificate for any ' +
'available certificate formats'));
}
};

Expand Down
21 changes: 17 additions & 4 deletions lib/formats/openssh-cert.js
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,8 @@ function fromBuffer(data, algo, partial) {
var innerAlgo = sshbuf.readString();
if (algo !== undefined && innerAlgo !== algo)
throw (new Error('SSH certificate algorithm mismatch'));
if (algo === undefined)
algo = innerAlgo;

var cert = {};
cert.signatures = {};
Expand Down Expand Up @@ -168,15 +170,22 @@ function dateToInt64(date) {
}

function sign(cert, key) {
assert.ok(PrivateKey.isPrivateKey(key, [1, 2]));
if (cert.signatures.openssh === undefined)
cert.signatures.openssh = {};
try {
var blob = toBuffer(cert, true);
} catch (e) {
delete (cert.signatures.openssh);
return (false);
}
var sig = cert.signatures.openssh;

var blob = toBuffer(cert, true);
var signer = key.createSign();
var hashAlgo = undefined;
if (key.type === 'rsa' || key.type === 'dsa')
hashAlgo = 'sha1';
var signer = key.createSign(hashAlgo);
signer.write(blob);
sig.signature = signer.sign();
return (true);
}

function write(cert, options) {
Expand Down Expand Up @@ -262,6 +271,8 @@ function getAlg(certType) {
return ('dsa');
if (certType.match(ECDSA_ALGO))
return ('ecdsa');
if (certType === '[email protected]')
return ('ed25519');
throw (new Error('Unsupported cert type ' + certType));
}

Expand All @@ -272,5 +283,7 @@ function getCertType(key) {
return ('[email protected]');
if (key.type === 'ecdsa')
return ('ecdsa-sha2-' + key.curve + '[email protected]');
if (key.type === 'ed25519')
return ('[email protected]');
throw (new Error('Unsupported key type ' + key.type));
}
5 changes: 4 additions & 1 deletion lib/formats/x509.js
Original file line number Diff line number Diff line change
Expand Up @@ -338,7 +338,8 @@ function sign(cert, key) {
var sig = cert.signatures.x509;

sig.algo = key.type + '-' + key.defaultHashAlgorithm();
assert.string(SIGN_ALGS[sig.algo]);
if (SIGN_ALGS[sig.algo] === undefined)
return (false);

var der = new asn1.BerWriter();
writeTBSCert(cert, der);
Expand All @@ -348,6 +349,8 @@ function sign(cert, key) {
var signer = key.createSign();
signer.write(blob);
cert.signatures.x509.signature = signer.sign();

return (true);
}

function write(cert, options) {
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "sshpk",
"version": "1.9.0",
"version": "1.9.1",
"description": "A library for finding and using SSH public keys",
"main": "lib/index.js",
"scripts": {
Expand Down
25 changes: 25 additions & 0 deletions test/certs.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ var GEORGE_KEY, GEORGE_SSH, GEORGE_X509;
var BARRY_KEY;
var JIM_KEY, JIM_SSH, JIM_X509;
var EC_KEY, EC_KEY2;
var SUE_KEY;

test('setup', function (t) {
var d = fs.readFileSync(path.join(testDir, 'id_dsa'));
Expand All @@ -34,6 +35,10 @@ test('setup', function (t) {
EC_KEY = sshpk.parsePrivateKey(d);
d = fs.readFileSync(path.join(testDir, 'id_ecdsa2'));
EC2_KEY = sshpk.parsePrivateKey(d);

d = fs.readFileSync(path.join(testDir, 'id_ed25519'));
SUE_KEY = sshpk.parsePrivateKey(d);

t.end();
});

Expand Down Expand Up @@ -169,6 +174,26 @@ test('create ecdsa signed, loopback', function (t) {
t.end();
});

test('create ed25519 self-signed, loopback', function (t) {
var id = sshpk.identityForHost('foobar.com');
var cert = sshpk.createSelfSignedCertificate(id, SUE_KEY);

t.throws(function () {
cert.toBuffer('pem');
});
t.throws(function () {
cert.toBuffer('x509');
});

var ossh = cert.toBuffer('openssh');
var cert3 = sshpk.parseCertificate(ossh, 'openssh');
t.ok(SUE_KEY.fingerprint().matches(cert3.subjectKey));
t.ok(cert3.subjects[0].equals(cert.subjects[0]));
t.strictEqual(cert3.subjects[0].hostname, 'foobar.com');

t.end();
});

test('subjectaltname', function (t) {
var ids = [
sshpk.identityForHost('foobar.com'),
Expand Down

0 comments on commit 079f792

Please sign in to comment.