Bug 1522145 - Web Authentication - Support additional Windows Hello Algorithms r=keeler

Support Main Algorithms

Differential Revision: https://phabricator.services.mozilla.com/D17363

--HG--
extra : moz-landing-system : lando
This commit is contained in:
Akshay Kumar 2019-01-24 18:38:49 +00:00
parent a439a717c0
commit 85743771de
4 changed files with 54 additions and 33 deletions

View File

@ -4,6 +4,7 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "WebAuthnCoseIdentifiers.h"
#include "mozilla/dom/U2FHIDTokenManager.h"
#include "mozilla/dom/WebAuthnUtil.h"
#include "mozilla/ipc/BackgroundParent.h"
@ -140,6 +141,31 @@ RefPtr<U2FRegisterPromise> U2FHIDTokenManager::Register(
if (requirePlatformAttachment) {
registerFlags |= U2F_FLAG_REQUIRE_PLATFORM_ATTACHMENT;
}
nsTArray<CoseAlg> coseAlgos;
for (const auto& coseAlg : extra.coseAlgs()) {
switch (static_cast<CoseAlgorithmIdentifier>(coseAlg.alg())) {
case CoseAlgorithmIdentifier::ES256:
coseAlgos.AppendElement(coseAlg);
break;
default:
continue;
}
}
// Only if no algorithms were specified, default to the only CTAP 1 / U2F
// protocol-supported algorithm. Ultimately this logic must move into
// u2f-hid-rs in a fashion that doesn't break the tests.
if (extra.coseAlgs().IsEmpty()) {
coseAlgos.AppendElement(
static_cast<int32_t>(CoseAlgorithmIdentifier::ES256));
}
// If there are no acceptable/supported algorithms, reject the promise.
if (coseAlgos.IsEmpty()) {
return U2FRegisterPromise::CreateAndReject(NS_ERROR_DOM_NOT_SUPPORTED_ERR,
__func__);
}
}
CryptoBuffer rpIdHash, clientDataHash;

View File

@ -4,6 +4,7 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "WebAuthnCoseIdentifiers.h"
#include "mozilla/dom/U2FSoftTokenManager.h"
#include "CryptoBuffer.h"
#include "mozilla/Base64.h"
@ -602,6 +603,30 @@ RefPtr<U2FRegisterPromise> U2FSoftTokenManager::Register(
return U2FRegisterPromise::CreateAndReject(NS_ERROR_DOM_NOT_ALLOWED_ERR,
__func__);
}
nsTArray<CoseAlg> coseAlgos;
for (const auto& coseAlg : extra.coseAlgs()) {
switch (static_cast<CoseAlgorithmIdentifier>(coseAlg.alg())) {
case CoseAlgorithmIdentifier::ES256:
coseAlgos.AppendElement(coseAlg);
break;
default:
continue;
}
}
// Only if no algorithms were specified, default to the one the soft token
// supports.
if (extra.coseAlgs().IsEmpty()) {
coseAlgos.AppendElement(
static_cast<int32_t>(CoseAlgorithmIdentifier::ES256));
}
// If there are no acceptable/supported algorithms, reject the promise.
if (coseAlgos.IsEmpty()) {
return U2FRegisterPromise::CreateAndReject(NS_ERROR_DOM_NOT_SUPPORTED_ERR,
__func__);
}
}
CryptoBuffer rpIdHash, clientDataHash;

View File

@ -15,18 +15,6 @@ namespace dom {
// From https://www.iana.org/assignments/cose/cose.xhtml#algorithms
enum class CoseAlgorithmIdentifier : int32_t { ES256 = -7 };
static nsresult CoseAlgorithmToWebCryptoId(const int32_t& aId,
/* out */ nsString& aName) {
switch (static_cast<CoseAlgorithmIdentifier>(aId)) {
case CoseAlgorithmIdentifier::ES256:
aName.AssignLiteral(JWK_ALG_ECDSA_P_256);
break;
default:
return NS_ERROR_DOM_NOT_SUPPORTED_ERR;
}
return NS_OK;
}
} // namespace dom
} // namespace mozilla

View File

@ -268,16 +268,10 @@ already_AddRefed<Promise> WebAuthnManager::MakeCredential(
return promise.forget();
}
// TODO: Move this logic into U2FTokenManager in Bug 1409220.
// Process each element of mPubKeyCredParams using the following steps, to
// produce a new sequence coseAlgos.
nsTArray<PublicKeyCredentialParameters> acceptableParams;
nsTArray<CoseAlg> coseAlgos;
for (size_t a = 0; a < aOptions.mPubKeyCredParams.Length(); ++a) {
// Let current be the currently selected element of
// mPubKeyCredParams.
// If current.type does not contain a PublicKeyCredentialType
// supported by this implementation, then stop processing current and move
// on to the next element in mPubKeyCredParams.
@ -286,24 +280,12 @@ already_AddRefed<Promise> WebAuthnManager::MakeCredential(
continue;
}
nsString algName;
if (NS_FAILED(CoseAlgorithmToWebCryptoId(aOptions.mPubKeyCredParams[a].mAlg,
algName))) {
continue;
}
if (!acceptableParams.AppendElement(aOptions.mPubKeyCredParams[a],
mozilla::fallible)) {
promise->MaybeReject(NS_ERROR_OUT_OF_MEMORY);
return promise.forget();
}
coseAlgos.AppendElement(aOptions.mPubKeyCredParams[a].mAlg);
}
// If acceptableParams is empty and mPubKeyCredParams was not empty, cancel
// the timer started in step 2, reject promise with a DOMException whose name
// is "NotSupportedError", and terminate this algorithm.
if (acceptableParams.IsEmpty() && !aOptions.mPubKeyCredParams.IsEmpty()) {
// If there are algorithms specified, but none are Public_key algorithms,
// reject the promise.
if (coseAlgos.IsEmpty() && !aOptions.mPubKeyCredParams.IsEmpty()) {
promise->MaybeReject(NS_ERROR_DOM_NOT_SUPPORTED_ERR);
return promise.forget();
}