Commit 9225524c authored by Jacob Dufault's avatar Jacob Dufault Committed by Commit Bot

cros: Cryptohome stubs needed for PIN sign-in.

Also extend fake_cryptohome_client to support multiple keys, checking keys, and
removing keys. The implementation is still not entirely correct, but good enough
for testing PIN.

Bug: 826773
Change-Id: I3f789c87095b663ca3ab6fb8becae5e924f02a5a
Reviewed-on: https://chromium-review.googlesource.com/1054247Reviewed-by: default avatarRyo Hashimoto <hashimoto@chromium.org>
Commit-Queue: Jacob Dufault <jdufault@chromium.org>
Cr-Commit-Position: refs/heads/master@{#559228}
parent 40c6f213
......@@ -174,6 +174,15 @@ bool KeyDefinition::ProviderData::operator==(const ProviderData& other) const {
(!has_bytes || (*bytes == *other.bytes));
}
bool KeyDefinition::Policy::operator==(const Policy& other) const {
return low_entropy_credential == other.low_entropy_credential &&
auth_locked == other.auth_locked;
}
bool KeyDefinition::Policy::operator!=(const Policy& other) const {
return !(*this == other);
}
KeyDefinition KeyDefinition::CreateForPassword(
const std::string& secret,
const std::string& label,
......@@ -206,7 +215,8 @@ KeyDefinition::~KeyDefinition() = default;
bool KeyDefinition::operator==(const KeyDefinition& other) const {
if (type != other.type || label != other.label ||
privileges != other.privileges || revision != other.revision ||
privileges != other.privileges || policy != other.policy ||
revision != other.revision ||
challenge_response_keys != other.challenge_response_keys ||
authorization_data.size() != other.authorization_data.size() ||
provider_data.size() != other.provider_data.size()) {
......
......@@ -126,6 +126,14 @@ struct CHROMEOS_EXPORT KeyDefinition {
std::unique_ptr<std::string> bytes;
};
struct Policy {
bool operator==(const Policy& other) const;
bool operator!=(const Policy& other) const;
bool low_entropy_credential = false;
bool auth_locked = false;
};
// Creates an instance with the TYPE_PASSWORD type.
static KeyDefinition CreateForPassword(const std::string& secret,
const std::string& label,
......@@ -147,6 +155,7 @@ struct CHROMEOS_EXPORT KeyDefinition {
std::string label;
// Privileges associated with key. Combination of |AuthKeyPrivileges| values.
int privileges = 0;
Policy policy;
int revision = 0;
std::string secret;
std::vector<chromeos::ChallengeResponseKey> challenge_response_keys;
......
......@@ -170,6 +170,11 @@ std::vector<KeyDefinition> GetKeyDataReplyToKeyDefinitions(
if (privileges.authorized_update())
key_definition.privileges |= PRIV_AUTHORIZED_UPDATE;
// Extract |policy|.
key_definition.policy.low_entropy_credential =
it->policy().low_entropy_credential();
key_definition.policy.auth_locked = it->policy().auth_locked();
// Extract |authorization_data|.
for (RepeatedPtrField<KeyAuthorizationData>::const_iterator auth_it =
it->authorization_data().begin();
......
......@@ -910,6 +910,13 @@ class CryptohomeClientImpl : public CryptohomeClient {
weak_ptr_factory_.GetWeakPtr(), std::move(callback)));
}
void GetSupportedKeyPolicies(
const cryptohome::GetSupportedKeyPoliciesRequest& request,
DBusMethodCallback<cryptohome::BaseReply> callback) override {
CallCryptohomeMethod(cryptohome::kCryptohomeGetSupportedKeyPolicies,
request, std::move(callback));
}
protected:
void Init(dbus::Bus* bus) override {
proxy_ = bus->GetObjectProxy(
......
......@@ -27,6 +27,7 @@ class CheckKeyRequest;
class FlushAndSignBootAttributesRequest;
class GetBootAttributeRequest;
class GetKeyDataRequest;
class GetSupportedKeyPoliciesRequest;
class MigrateToDircryptoRequest;
class MountRequest;
class RemoveFirmwareManagementParametersRequest;
......@@ -579,6 +580,11 @@ class CHROMEOS_EXPORT CryptohomeClient : public DBusClient {
const cryptohome::Identification& cryptohome_id,
DBusMethodCallback<bool> callback) = 0;
// Calls GetSupportedKeyPolicies to determine which type of keys can be added.
virtual void GetSupportedKeyPolicies(
const cryptohome::GetSupportedKeyPoliciesRequest& request,
DBusMethodCallback<cryptohome::BaseReply> callback) = 0;
protected:
// Create() should be used instead.
CryptohomeClient();
......
......@@ -59,8 +59,7 @@ FakeCryptohomeClient::FakeCryptohomeClient()
FakeCryptohomeClient::~FakeCryptohomeClient() = default;
void FakeCryptohomeClient::Init(dbus::Bus* bus) {
}
void FakeCryptohomeClient::Init(dbus::Bus* bus) {}
void FakeCryptohomeClient::AddObserver(Observer* observer) {
observer_list_.AddObserver(observer);
......@@ -511,10 +510,17 @@ void FakeCryptohomeClient::GetKeyDataEx(
const auto it = key_data_map_.find(cryptohome_id);
if (it == key_data_map_.end()) {
reply.set_error(cryptohome::CRYPTOHOME_ERROR_ACCOUNT_NOT_FOUND);
} else if (it->second.empty()) {
reply.set_error(cryptohome::CRYPTOHOME_ERROR_KEY_NOT_FOUND);
} else {
auto key = FindKey(it->second, auth.key().data().label());
if (key != it->second.end()) {
cryptohome::GetKeyDataReply* key_data_reply =
reply.MutableExtension(cryptohome::GetKeyDataReply::reply);
*key_data_reply->add_key_data() = it->second;
*key_data_reply->add_key_data() = key->second.data();
} else {
reply.set_error(cryptohome::CRYPTOHOME_ERROR_KEY_NOT_FOUND);
}
}
ReturnProtobufMethodCallback(reply, std::move(callback));
}
......@@ -524,7 +530,25 @@ void FakeCryptohomeClient::CheckKeyEx(
const cryptohome::AuthorizationRequest& auth,
const cryptohome::CheckKeyRequest& request,
DBusMethodCallback<cryptohome::BaseReply> callback) {
ReturnProtobufMethodCallback(cryptohome::BaseReply(), std::move(callback));
cryptohome::BaseReply reply;
if (enable_auth_check_) {
const auto it = key_data_map_.find(cryptohome_id);
if (it == key_data_map_.end()) {
reply.set_error(cryptohome::CRYPTOHOME_ERROR_ACCOUNT_NOT_FOUND);
} else if (it->second.empty()) {
reply.set_error(cryptohome::CRYPTOHOME_ERROR_KEY_NOT_FOUND);
} else {
auto key = FindKey(it->second, auth.key().data().label());
if (key == it->second.end()) {
reply.set_error(cryptohome::CRYPTOHOME_ERROR_KEY_NOT_FOUND);
} else if (key->second.secret() != auth.key().secret()) {
reply.set_error(cryptohome::CRYPTOHOME_ERROR_AUTHORIZATION_KEY_FAILED);
}
}
}
ReturnProtobufMethodCallback(reply, std::move(callback));
}
void FakeCryptohomeClient::MountEx(
......@@ -553,7 +577,7 @@ void FakeCryptohomeClient::AddKeyEx(
const cryptohome::AuthorizationRequest& auth,
const cryptohome::AddKeyRequest& request,
DBusMethodCallback<cryptohome::BaseReply> callback) {
key_data_map_.insert(std::make_pair(cryptohome_id, request.key().data()));
key_data_map_[cryptohome_id][request.key().data().label()] = request.key();
ReturnProtobufMethodCallback(cryptohome::BaseReply(), std::move(callback));
}
......@@ -562,6 +586,12 @@ void FakeCryptohomeClient::RemoveKeyEx(
const cryptohome::AuthorizationRequest& auth,
const cryptohome::RemoveKeyRequest& request,
DBusMethodCallback<cryptohome::BaseReply> callback) {
const auto it = key_data_map_.find(cryptohome_id);
if (it != key_data_map_.end()) {
auto key = FindKey(it->second, request.key().data().label());
if (key != it->second.end())
it->second.erase(key);
}
ReturnProtobufMethodCallback(cryptohome::BaseReply(), std::move(callback));
}
......@@ -630,6 +660,16 @@ void FakeCryptohomeClient::NeedsDircryptoMigration(
base::BindOnce(std::move(callback), needs_dircrypto_migration_));
}
void FakeCryptohomeClient::GetSupportedKeyPolicies(
const cryptohome::GetSupportedKeyPoliciesRequest& request,
DBusMethodCallback<cryptohome::BaseReply> callback) {
cryptohome::BaseReply reply;
cryptohome::GetSupportedKeyPoliciesReply* attr_reply =
reply.MutableExtension(cryptohome::GetSupportedKeyPoliciesReply::reply);
attr_reply->set_low_entropy_credentials(supports_low_entropy_credentials_);
ReturnProtobufMethodCallback(reply, std::move(callback));
}
void FakeCryptohomeClient::SetServiceIsAvailable(bool is_available) {
service_is_available_ = is_available;
if (!is_available)
......@@ -792,4 +832,16 @@ bool FakeCryptohomeClient::LoadInstallAttributes() {
return true;
}
std::map<std::string, cryptohome::Key>::const_iterator
FakeCryptohomeClient::FindKey(
const std::map<std::string, cryptohome::Key>& keys,
const std::string& label) {
// Wildcard label.
if (label.empty())
return keys.begin();
// Specific label
return keys.find(label);
}
} // namespace chromeos
......@@ -200,6 +200,9 @@ class CHROMEOS_EXPORT FakeCryptohomeClient : public CryptohomeClient {
DBusMethodCallback<cryptohome::BaseReply> callback) override;
void NeedsDircryptoMigration(const cryptohome::Identification& cryptohome_id,
DBusMethodCallback<bool> callback) override;
void GetSupportedKeyPolicies(
const cryptohome::GetSupportedKeyPoliciesRequest& request,
DBusMethodCallback<cryptohome::BaseReply> callback) override;
/////////// Test helpers ////////////
......@@ -245,6 +248,14 @@ class CHROMEOS_EXPORT FakeCryptohomeClient : public CryptohomeClient {
tpm_attestation_does_key_exist_should_succeed_ = should_succeed;
}
void set_supports_low_entropy_credentials(bool supports) {
supports_low_entropy_credentials_ = supports;
}
void set_enable_auth_check(bool enable_auth_check) {
enable_auth_check_ = enable_auth_check;
}
void SetTpmAttestationUserCertificate(
const cryptohome::Identification& cryptohome_id,
const std::string& key_name,
......@@ -321,6 +332,11 @@ class CHROMEOS_EXPORT FakeCryptohomeClient : public CryptohomeClient {
// Loads install attributes from the stub file.
bool LoadInstallAttributes();
// Finds a key matching the given label. Wildcard labels are supported.
std::map<std::string, cryptohome::Key>::const_iterator FindKey(
const std::map<std::string, cryptohome::Key>& keys,
const std::string& label);
bool service_is_available_;
base::ObserverList<Observer> observer_list_;
......@@ -336,7 +352,8 @@ class CHROMEOS_EXPORT FakeCryptohomeClient : public CryptohomeClient {
std::map<std::string, std::vector<uint8_t>> install_attrs_;
bool locked_;
std::map<cryptohome::Identification, cryptohome::KeyData> key_data_map_;
std::map<cryptohome::Identification, std::map<std::string, cryptohome::Key>>
key_data_map_;
// User attestation certificate mapped by cryptohome_id and key_name.
std::map<std::pair<cryptohome::Identification, std::string>, std::string>
......@@ -355,6 +372,9 @@ class CHROMEOS_EXPORT FakeCryptohomeClient : public CryptohomeClient {
bool tpm_attestation_is_enrolled_ = true;
bool tpm_attestation_is_prepared_ = true;
bool tpm_attestation_does_key_exist_should_succeed_ = true;
bool supports_low_entropy_credentials_ = false;
// Controls if CheckKeyEx actually checks the key.
bool enable_auth_check_ = false;
// MountEx fields.
cryptohome::CryptohomeErrorCode cryptohome_error_ =
......
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