Commit 54e0bebf authored by Adam Langley's avatar Adam Langley Committed by Commit Bot

webauthn: add histogram for attestation prompt events.

Change-Id: Ib6c4ae24146e435585fe1ba064e26002d49b8f9c
Reviewed-on: https://chromium-review.googlesource.com/1224953Reviewed-by: default avatarSteven Holte <holte@chromium.org>
Reviewed-by: default avatarBalazs Engedy <engedy@chromium.org>
Commit-Queue: Adam Langley <agl@chromium.org>
Cr-Commit-Position: refs/heads/master@{#591526}
parent d120ebf1
...@@ -12,6 +12,7 @@ ...@@ -12,6 +12,7 @@
#include "base/base64url.h" #include "base/base64url.h"
#include "base/json/json_writer.h" #include "base/json/json_writer.h"
#include "base/logging.h" #include "base/logging.h"
#include "base/metrics/histogram_macros.h"
#include "base/rand_util.h" #include "base/rand_util.h"
#include "base/strings/string_piece.h" #include "base/strings/string_piece.h"
#include "base/timer/timer.h" #include "base/timer/timer.h"
...@@ -67,6 +68,29 @@ const char kGetType[] = "webauthn.get"; ...@@ -67,6 +68,29 @@ const char kGetType[] = "webauthn.get";
namespace { namespace {
// AttestationPromptResult enumerates events related to attestation prompts.
// These values are recorded in an UMA histogram and so should not be
// reassigned.
enum class AttestationPromptResult {
// kQueried indicates that the embedder was queried in order to determine
// whether attestation information should be returned to the origin.
kQueried = 0,
// kTimeout indicates that a timeout occured while awaiting the result of an
// attestation query.
kTimeout = 1,
// kAllowed indicates that the query to the embedder was resolved positively.
// (E.g. the user clicked to allow, or the embedded allowed immediately by
// policy.)
kAllowed = 2,
// kBlocked indicates that the query to the embedder was resolved negatively.
// (E.g. the user clicked to block, or closed the dialog.)
kBlocked = 3,
// kAbandoned indications that the user closed the tab or navigated away while
// the attestation prompt was showing.
kAbandoned = 4,
kMaxValue = kAbandoned,
};
// Ensure that the origin's effective domain is a valid domain. // Ensure that the origin's effective domain is a valid domain.
// Only the domain format of host is valid. // Only the domain format of host is valid.
// Reference https://url.spec.whatwg.org/#valid-domain-string and // Reference https://url.spec.whatwg.org/#valid-domain-string and
...@@ -770,6 +794,9 @@ void AuthenticatorImpl::OnRegisterResponse( ...@@ -770,6 +794,9 @@ void AuthenticatorImpl::OnRegisterResponse(
if (attestation_preference_ != if (attestation_preference_ !=
blink::mojom::AttestationConveyancePreference::NONE) { blink::mojom::AttestationConveyancePreference::NONE) {
UMA_HISTOGRAM_ENUMERATION("WebAuthentication.AttestationPromptResult",
AttestationPromptResult::kQueried);
awaiting_attestation_response_ = true;
request_delegate_->ShouldReturnAttestation( request_delegate_->ShouldReturnAttestation(
relying_party_id_, relying_party_id_,
base::BindOnce( base::BindOnce(
...@@ -794,6 +821,7 @@ void AuthenticatorImpl::OnRegisterResponse( ...@@ -794,6 +821,7 @@ void AuthenticatorImpl::OnRegisterResponse(
void AuthenticatorImpl::OnRegisterResponseAttestationDecided( void AuthenticatorImpl::OnRegisterResponseAttestationDecided(
device::AuthenticatorMakeCredentialResponse response_data, device::AuthenticatorMakeCredentialResponse response_data,
bool attestation_permitted) { bool attestation_permitted) {
awaiting_attestation_response_ = false;
if (!request_) { if (!request_) {
// The request has already been cleaned up, probably because a navigation // The request has already been cleaned up, probably because a navigation
// occured while the permissions prompt was pending. // occured while the permissions prompt was pending.
...@@ -804,6 +832,8 @@ void AuthenticatorImpl::OnRegisterResponseAttestationDecided( ...@@ -804,6 +832,8 @@ void AuthenticatorImpl::OnRegisterResponseAttestationDecided(
blink::mojom::AttestationConveyancePreference::NONE); blink::mojom::AttestationConveyancePreference::NONE);
if (!attestation_permitted) { if (!attestation_permitted) {
UMA_HISTOGRAM_ENUMERATION("WebAuthentication.AttestationPromptResult",
AttestationPromptResult::kBlocked);
InvokeCallbackAndCleanup( InvokeCallbackAndCleanup(
std::move(make_credential_response_callback_), std::move(make_credential_response_callback_),
blink::mojom::AuthenticatorStatus::NOT_ALLOWED_ERROR, nullptr, blink::mojom::AuthenticatorStatus::NOT_ALLOWED_ERROR, nullptr,
...@@ -811,6 +841,8 @@ void AuthenticatorImpl::OnRegisterResponseAttestationDecided( ...@@ -811,6 +841,8 @@ void AuthenticatorImpl::OnRegisterResponseAttestationDecided(
return; return;
} }
UMA_HISTOGRAM_ENUMERATION("WebAuthentication.AttestationPromptResult",
AttestationPromptResult::kAllowed);
bool include_attestation = true; bool include_attestation = true;
// The check for IsAttestationCertificateInappropriatelyIdentifying is // The check for IsAttestationCertificateInappropriatelyIdentifying is
...@@ -916,6 +948,12 @@ void AuthenticatorImpl::FailWithNotAllowedErrorAndCleanup() { ...@@ -916,6 +948,12 @@ void AuthenticatorImpl::FailWithNotAllowedErrorAndCleanup() {
void AuthenticatorImpl::OnTimeout() { void AuthenticatorImpl::OnTimeout() {
DCHECK(request_delegate_); DCHECK(request_delegate_);
if (awaiting_attestation_response_) {
UMA_HISTOGRAM_ENUMERATION("WebAuthentication.AttestationPromptResult",
AttestationPromptResult::kTimeout);
awaiting_attestation_response_ = false;
}
request_delegate_->DidFailWithInterestingReason( request_delegate_->DidFailWithInterestingReason(
AuthenticatorRequestClientDelegate::InterestingFailureReason::kTimeout); AuthenticatorRequestClientDelegate::InterestingFailureReason::kTimeout);
...@@ -956,6 +994,12 @@ void AuthenticatorImpl::InvokeCallbackAndCleanup( ...@@ -956,6 +994,12 @@ void AuthenticatorImpl::InvokeCallbackAndCleanup(
} }
void AuthenticatorImpl::Cleanup() { void AuthenticatorImpl::Cleanup() {
if (awaiting_attestation_response_) {
UMA_HISTOGRAM_ENUMERATION("WebAuthentication.AttestationPromptResult",
AttestationPromptResult::kAbandoned);
awaiting_attestation_response_ = false;
}
timer_->Stop(); timer_->Stop();
request_.reset(); request_.reset();
request_delegate_.reset(); request_delegate_.reset();
......
...@@ -186,6 +186,9 @@ class CONTENT_EXPORT AuthenticatorImpl : public blink::mojom::Authenticator, ...@@ -186,6 +186,9 @@ class CONTENT_EXPORT AuthenticatorImpl : public blink::mojom::Authenticator,
// retried with this value. // retried with this value.
base::Optional<std::array<uint8_t, crypto::kSHA256Length>> base::Optional<std::array<uint8_t, crypto::kSHA256Length>>
alternative_application_parameter_; alternative_application_parameter_;
// awaiting_attestation_response_ is true if the embedder has been queried
// about an attestsation decision and the response is still pending.
bool awaiting_attestation_response_ = false;
// Owns pipes to this Authenticator from |render_frame_host_|. // Owns pipes to this Authenticator from |render_frame_host_|.
mojo::Binding<blink::mojom::Authenticator> binding_; mojo::Binding<blink::mojom::Authenticator> binding_;
......
...@@ -51048,6 +51048,14 @@ Full version information for the fingerprint enum values: ...@@ -51048,6 +51048,14 @@ Full version information for the fingerprint enum values:
<int value="2" label="Source Node start()"/> <int value="2" label="Source Node start()"/>
</enum> </enum>
<enum name="WebAuthenticationAttestationPromptResult">
<int value="0" label="Queried"/>
<int value="1" label="Timeout"/>
<int value="2" label="Allowed"/>
<int value="3" label="Blocked"/>
<int value="4" label="Abandoned"/>
</enum>
<enum name="WebBluetoothConnectGATTOutcome"> <enum name="WebBluetoothConnectGATTOutcome">
<int value="0" label="Success"/> <int value="0" label="Success"/>
<int value="1" label="Device no longer in range"/> <int value="1" label="Device no longer in range"/>
...@@ -114244,6 +114244,20 @@ uploading your change for review. ...@@ -114244,6 +114244,20 @@ uploading your change for review.
</summary> </summary>
</histogram> </histogram>
<histogram name="WebAuthentication.AttestationPromptResult"
enum="WebAuthenticationAttestationPromptResult">
<owner>agl@chromium.org</owner>
<summary>
Tracks events related to prompting users for permission to pass WebAuthn
attestation information back to origins. &quot;Queried&quot; means that the
embedder was queried for a decision. (Since such decisions can be resolved
by enterprise policy, that doesn't imply that a user saw a permissions
prompt in every case.) Then one of four things can happen: a timeout, a
positive or negative resolution, or the request is abandoned. The latter
case occurs when, for example, the tab is closed or the user navigates away.
</summary>
</histogram>
<histogram name="WebController.CertVerificationErrorsCacheHit" <histogram name="WebController.CertVerificationErrorsCacheHit"
enum="BooleanCacheHit"> enum="BooleanCacheHit">
<owner>eugenebut@chromium.org</owner> <owner>eugenebut@chromium.org</owner>
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment