mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-12-18 04:44:17 +00:00
Bug 1265211
- Fix intermittent U2F Test r=mgoodwin
- The u2futil.js script's verifySignature method was causing an intermittent in test_frame_register_sign.html due to incomplete ASN.1 decoding. Since we're calready pulling in an ASN.1 parsing library, this changes that code to do a complete parse and santizize, which should cover all cases. MozReview-Commit-ID: 9kDWT2KUFdq --HG-- extra : transplant_source : %A9CD%CD%E7E%11s%0A%82ls%5B%7B%80jQ%FC%FE%0B
This commit is contained in:
parent
5d60c22c60
commit
fa14e077d5
@ -4,6 +4,10 @@
|
||||
<title>Test for Utility Methods for other FIDO Universal Second Factor tests</title>
|
||||
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
|
||||
<script type="text/javascript" src="/tests/dom/u2f/tests/u2futil.js"></script>
|
||||
<script type="text/javascript" src="pkijs/common.js"></script>
|
||||
<script type="text/javascript" src="pkijs/asn1.js"></script>
|
||||
<script type="text/javascript" src="pkijs/x509_schema.js"></script>
|
||||
<script type="text/javascript" src="pkijs/x509_simpl.js"></script>
|
||||
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
|
||||
</head>
|
||||
<body>
|
||||
|
@ -130,29 +130,33 @@ function assembleRegistrationSignedData(appParam, challengeParam, keyHandle, pub
|
||||
return signedData;
|
||||
}
|
||||
|
||||
function verifySignature(key, data, derSig) {
|
||||
if (derSig.byteLength < 70) {
|
||||
console.log("bad sig: " + hexEncode(derSig))
|
||||
throw "Invalid signature length: " + derSig.byteLength;
|
||||
function sanitizeSigArray(arr) {
|
||||
// ECDSA signature fields into WebCrypto must be exactly 32 bytes long, so
|
||||
// this method strips leading padding bytes, if added, and also appends
|
||||
// padding zeros, if needed.
|
||||
if (arr.length > 32) {
|
||||
arr = arr.slice(arr.length - 32)
|
||||
}
|
||||
var ret = new Uint8Array(32);
|
||||
ret.set(arr, ret.length - arr.length);
|
||||
return ret;
|
||||
}
|
||||
|
||||
// Poor man's ASN.1 decode
|
||||
// R and S are always 32 bytes. If ether has a DER
|
||||
// length > 32, it's just zeros we can chop off.
|
||||
var lenR = derSig[3];
|
||||
var lenS = derSig[3 + lenR + 2];
|
||||
var padR = lenR - 32;
|
||||
var padS = lenS - 32;
|
||||
var sig = new Uint8Array(64);
|
||||
derSig.slice(4 + padR, 4 + lenR).map((x, i) => sig[i] = x);
|
||||
derSig.slice(4 + lenR + 2 + padS, 4 + lenR + 2 + lenS).map(
|
||||
(x, i) => sig[32 + i] = x
|
||||
);
|
||||
function verifySignature(key, data, derSig) {
|
||||
var sigAsn1 = org.pkijs.fromBER(derSig.buffer);
|
||||
var sigR = new Uint8Array(sigAsn1.result.value_block.value[0].value_block.value_hex);
|
||||
var sigS = new Uint8Array(sigAsn1.result.value_block.value[1].value_block.value_hex);
|
||||
|
||||
console.log("data: " + hexEncode(data));
|
||||
console.log("der: " + hexEncode(derSig));
|
||||
console.log("raw: " + hexEncode(sig));
|
||||
// The resulting R and S values from the ASN.1 Sequence must be fit into 32
|
||||
// bytes. Sometimes they have leading zeros, sometimes they're too short, it
|
||||
// all depends on what lib generated the signature.
|
||||
var R = sanitizeSigArray(sigR);
|
||||
var S = sanitizeSigArray(sigS);
|
||||
|
||||
var sigData = new Uint8Array(R.length + S.length);
|
||||
sigData.set(R);
|
||||
sigData.set(S, R.length);
|
||||
|
||||
var alg = {name: "ECDSA", hash: "SHA-256"};
|
||||
return crypto.subtle.verify(alg, key, sig, data);
|
||||
return crypto.subtle.verify(alg, key, sigData, data);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user