Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(39)

Unified Diff: chrome/browser/chromeos/attestation/attestation_policy_observer.cc

Issue 14220003: Finished implementing AttestationPolicyObserver. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 7 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: chrome/browser/chromeos/attestation/attestation_policy_observer.cc
diff --git a/chrome/browser/chromeos/attestation/attestation_policy_observer.cc b/chrome/browser/chromeos/attestation/attestation_policy_observer.cc
index 21664cde31c1188311062f51478bc9a4f81ce67d..b274060faefdec296a9718c72fb7653c12af02b7 100644
--- a/chrome/browser/chromeos/attestation/attestation_policy_observer.cc
+++ b/chrome/browser/chromeos/attestation/attestation_policy_observer.cc
@@ -7,7 +7,10 @@
#include <string>
#include "base/bind.h"
+#include "base/callback.h"
+#include "base/time.h"
#include "chrome/browser/chromeos/attestation/attestation_ca_client.h"
+#include "chrome/browser/chromeos/attestation/attestation_key_payload.pb.h"
#include "chrome/browser/chromeos/settings/cros_settings.h"
#include "chrome/browser/policy/cloud/cloud_policy_client.h"
#include "chrome/browser/policy/cloud/cloud_policy_manager.h"
@@ -19,6 +22,7 @@
#include "chromeos/dbus/dbus_thread_manager.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/notification_details.h"
+#include "net/cert/x509_certificate.h"
namespace {
@@ -31,10 +35,13 @@ namespace {
// value - The value returned by the dbus operation.
void DBusBoolRedirectCallback(const base::Closure& on_true,
const base::Closure& on_false,
+ const std::string& method_name,
chromeos::DBusMethodCallStatus status,
bool value) {
- if (status != chromeos::DBUS_METHOD_CALL_SUCCESS)
+ if (status != chromeos::DBUS_METHOD_CALL_SUCCESS) {
+ LOG(WARNING) << "Cryptohome DBus method failed: " << method_name;
Mattias Nissler (ping if slow) 2013/04/23 10:53:01 You probably want to log |status| as well.
dkrahn 2013/04/23 21:17:09 Done.
return;
+ }
const base::Closure& task = value ? on_true : on_false;
if (!task.is_null())
task.Run();
@@ -49,11 +56,14 @@ void DBusBoolRedirectCallback(const base::Closure& on_true,
// data - The data returned by the dbus operation.
void DBusStringCallback(
const base::Callback<void(const std::string&)> on_success,
+ const std::string& method_name,
chromeos::DBusMethodCallStatus status,
bool result,
const std::string& data) {
- if (status != chromeos::DBUS_METHOD_CALL_SUCCESS || !result)
+ if (status != chromeos::DBUS_METHOD_CALL_SUCCESS || !result) {
+ LOG(WARNING) << "Cryptohome DBus method failed: " << method_name;
return;
+ }
on_success.Run(data);
}
@@ -65,6 +75,8 @@ namespace attestation {
const char AttestationPolicyObserver::kEnterpriseMachineKey[] =
"attest-ent-machine";
+const int AttestationPolicyObserver::kExpiryThresholdInDays = 30;
+
AttestationPolicyObserver::AttestationPolicyObserver(
policy::CloudPolicyClient* policy_client)
: cros_settings_(CrosSettings::Get()),
@@ -145,7 +157,10 @@ void AttestationPolicyObserver::Start() {
cryptohome_client_->TpmAttestationDoesKeyExist(
CryptohomeClient::DEVICE_KEY,
kEnterpriseMachineKey,
- base::Bind(DBusBoolRedirectCallback, on_does_exist, on_does_not_exist));
+ base::Bind(DBusBoolRedirectCallback,
+ on_does_exist,
+ on_does_not_exist,
+ "TpmAttestationDoesKeyExist"));
}
void AttestationPolicyObserver::GetNewCertificate() {
@@ -155,7 +170,7 @@ void AttestationPolicyObserver::GetNewCertificate() {
base::Bind(DBusStringCallback,
base::Bind(&AttestationPolicyObserver::UploadCertificate,
weak_factory_.GetWeakPtr()),
- DBUS_METHOD_CALL_SUCCESS));
+ "", DBUS_METHOD_CALL_SUCCESS));
Mattias Nissler (ping if slow) 2013/04/23 10:53:01 Should have a proper identifying name? FWIW, you c
dkrahn 2013/04/23 21:17:09 Good idea, changed to use FROM_HERE.
}
void AttestationPolicyObserver::GetExistingCertificate() {
@@ -164,23 +179,87 @@ void AttestationPolicyObserver::GetExistingCertificate() {
kEnterpriseMachineKey,
base::Bind(DBusStringCallback,
base::Bind(&AttestationPolicyObserver::CheckCertificateExpiry,
- weak_factory_.GetWeakPtr())));
+ weak_factory_.GetWeakPtr()),
+ "TpmAttestationGetCertificate"));
}
void AttestationPolicyObserver::CheckCertificateExpiry(
const std::string& certificate) {
- // TODO(dkrahn): Check if the certificate will expire soon, for now assume no.
- CheckIfUploaded(certificate);
+ scoped_refptr<net::X509Certificate> x509(
+ net::X509Certificate::CreateFromBytes(certificate.data(),
+ certificate.length()));
+ if (!x509.get() || x509->valid_expiry().is_null()) {
+ LOG(WARNING) << "Failed to parse certificate, cannot check expiry.";
+ } else {
+ const base::TimeDelta threshold =
+ base::TimeDelta::FromDays(kExpiryThresholdInDays);
+ if ((base::Time::Now() + threshold) > x509->valid_expiry()) {
+ // The certificate has expired or will soon, replace it.
+ GetNewCertificate();
+ return;
+ }
+ }
+
+ // Get the payload and check if the certificate has already been uploaded.
+ GetKeyPayload(base::Bind(&AttestationPolicyObserver::CheckIfUploaded,
+ weak_factory_.GetWeakPtr(),
+ certificate));
}
void AttestationPolicyObserver::UploadCertificate(
const std::string& certificate) {
- // TODO(dkrahn): Upload the certificate.
+ policy_client_->UploadCertificate(
+ certificate,
+ base::Bind(&AttestationPolicyObserver::OnUploadComplete,
+ weak_factory_.GetWeakPtr()));
}
void AttestationPolicyObserver::CheckIfUploaded(
- const std::string& certificate) {
- // TODO(dkrahn): Check if we've already uploaded the certificate.
+ const std::string& certificate,
+ const std::string& key_payload) {
+ AttestationKeyPayload payload_pb;
+ if (!key_payload.empty() &&
+ payload_pb.ParseFromString(key_payload) &&
+ payload_pb.is_certificate_uploaded()) {
+ // Already uploaded... nothing more to do.
+ return;
+ }
+ UploadCertificate(certificate);
+}
+
+void AttestationPolicyObserver::GetKeyPayload(
+ base::Callback<void(const std::string&)> callback) {
+ cryptohome_client_->TpmAttestationGetKeyPayload(
+ CryptohomeClient::DEVICE_KEY,
+ kEnterpriseMachineKey,
+ base::Bind(DBusStringCallback, callback, "TpmAttestationGetKeyPayload"));
+}
+
+void AttestationPolicyObserver::OnUploadComplete(bool status) {
+ if (!status)
+ return;
+ GetKeyPayload(base::Bind(&AttestationPolicyObserver::MarkAsUploaded,
+ weak_factory_.GetWeakPtr()));
+}
+
+void AttestationPolicyObserver::MarkAsUploaded(const std::string& key_payload) {
+ AttestationKeyPayload payload_pb;
+ if (!key_payload.empty())
+ payload_pb.ParseFromString(key_payload);
+ payload_pb.set_is_certificate_uploaded(true);
+ std::string new_payload;
+ if (!payload_pb.SerializeToString(&new_payload)) {
+ LOG(WARNING) << "Failed to serialize key payload.";
+ return;
+ }
+ cryptohome_client_->TpmAttestationSetKeyPayload(
+ CryptohomeClient::DEVICE_KEY,
+ kEnterpriseMachineKey,
+ new_payload,
+ base::Bind(DBusBoolRedirectCallback,
+ base::Closure(),
+ base::Closure(),
+ "TpmAttestationSetKeyPayload"));
}
} // namespace attestation

Powered by Google App Engine
This is Rietveld 408576698