Revise check on key revocation sub packet: throwing the exception should only be done on single keys and not discard the whole armored block with possibly multiple keys. Evaluate only self-signatures.

This commit is contained in:
Thomas Oberndörfer 2018-11-28 16:46:17 +01:00
parent 47e6e2fc28
commit a7bae10fe8

View File

@ -105,6 +105,7 @@ Key.prototype.packetlist2structure = function(packetlist) {
continue; continue;
} }
if (packetlist[i].issuerKeyId.equals(primaryKeyId)) { if (packetlist[i].issuerKeyId.equals(primaryKeyId)) {
checkRevocationKey(packetlist[i], primaryKeyId);
user.selfCertifications.push(packetlist[i]); user.selfCertifications.push(packetlist[i]);
} else { } else {
user.otherCertifications.push(packetlist[i]); user.otherCertifications.push(packetlist[i]);
@ -118,6 +119,7 @@ Key.prototype.packetlist2structure = function(packetlist) {
} }
break; break;
case enums.signature.key: case enums.signature.key:
checkRevocationKey(packetlist[i], primaryKeyId);
this.directSignatures.push(packetlist[i]); this.directSignatures.push(packetlist[i]);
break; break;
case enums.signature.subkey_binding: case enums.signature.subkey_binding:
@ -125,6 +127,7 @@ Key.prototype.packetlist2structure = function(packetlist) {
util.print_debug('Dropping subkey binding signature without preceding subkey packet'); util.print_debug('Dropping subkey binding signature without preceding subkey packet');
continue; continue;
} }
checkRevocationKey(packetlist[i], primaryKeyId);
subKey.bindingSignatures.push(packetlist[i]); subKey.bindingSignatures.push(packetlist[i]);
break; break;
case enums.signature.key_revocation: case enums.signature.key_revocation:
@ -1237,11 +1240,6 @@ export async function read(data) {
try { try {
const packetlist = new packet.List(); const packetlist = new packet.List();
await packetlist.read(data); await packetlist.read(data);
if (packetlist.filterByTag(enums.packet.signature).some(
signature => signature.revocationKeyClass !== null
)) {
throw new Error('This key is intended to be revoked with an authorized key, which OpenPGP.js does not support.');
}
const keyIndex = packetlist.indexOfTag(enums.packet.publicKey, enums.packet.secretKey); const keyIndex = packetlist.indexOfTag(enums.packet.publicKey, enums.packet.secretKey);
if (keyIndex.length === 0) { if (keyIndex.length === 0) {
throw new Error('No key packet found'); throw new Error('No key packet found');
@ -1632,6 +1630,19 @@ function getExpirationTime(keyPacket, signature) {
return expirationTime ? new Date(expirationTime) : Infinity; return expirationTime ? new Date(expirationTime) : Infinity;
} }
/**
* Check if signature has revocation key sub packet (not supported by OpenPGP.js)
* and throw error if found
* @param {module:packet.Signature} signature The certificate or signature to check
* @param {type/keyid} keyId Check only certificates or signatures from a certain issuer key ID
*/
function checkRevocationKey(signature, keyId) {
if (signature.revocationKeyClass !== null &&
signature.issuerKeyId.equals(keyId)) {
throw new Error('This key is intended to be revoked with an authorized key, which OpenPGP.js does not support.');
}
}
/** /**
* Returns the preferred signature hash algorithm of a key * Returns the preferred signature hash algorithm of a key
* @param {module:key.Key} key (optional) the key to get preferences from * @param {module:key.Key} key (optional) the key to get preferences from