Pass Config pointer into AuthManager AuthManager needs to have logic for re-claming devices. This requires persistent storage for secret and owner. It's going to be easier to handle logic there than outside. BUG=25766815 Change-Id: Icc417f23715b48461098503fd241cee534d2225c Reviewed-on: https://weave-review.googlesource.com/1949 Reviewed-by: Vitaly Buka <vitalybuka@google.com>
diff --git a/src/device_manager.cc b/src/device_manager.cc index cb575b8..88256da 100644 --- a/src/device_manager.cc +++ b/src/device_manager.cc
@@ -33,15 +33,8 @@ config_->Load(); if (http_server) { - auth_manager_.reset( - new privet::AuthManager(config_->GetSettings().secret, - http_server->GetHttpsCertificateFingerprint())); - - if (auth_manager_->GetSecret() != config_->GetSettings().secret) { - // There is no Config::OnChangedCallback registered. - Config::Transaction transaction(config_.get()); - transaction.set_secret(auth_manager_->GetSecret()); - } + auth_manager_.reset(new privet::AuthManager( + config_.get(), http_server->GetHttpsCertificateFingerprint())); } device_info_.reset(new DeviceRegistrationInfo(
diff --git a/src/privet/auth_manager.cc b/src/privet/auth_manager.cc index 92c33a7..3a2f5e0 100644 --- a/src/privet/auth_manager.cc +++ b/src/privet/auth_manager.cc
@@ -7,6 +7,7 @@ #include <base/rand_util.h> #include <base/strings/string_number_conversions.h> +#include "src/config.h" #include "src/data_encoding.h" #include "src/privet/openssl_utils.h" #include "src/string_utils.h" @@ -73,17 +74,36 @@ DISALLOW_COPY_AND_ASSIGN(Caveat); }; +std::vector<uint8_t> CreateSecret() { + std::vector<uint8_t> secret(kSha256OutputSize); + base::RandBytes(secret.data(), secret.size()); + return secret; +} + } // namespace +AuthManager::AuthManager(Config* config, + const std::vector<uint8_t>& certificate_fingerprint) + : config_{config}, certificate_fingerprint_{certificate_fingerprint} { + SetSecret(config_ ? config_->GetSettings().secret : std::vector<uint8_t>{}); +} + AuthManager::AuthManager(const std::vector<uint8_t>& secret, const std::vector<uint8_t>& certificate_fingerprint, base::Clock* clock) - : clock_{clock ? clock : &default_clock_}, - secret_{secret}, - certificate_fingerprint_{certificate_fingerprint} { - if (secret_.size() != kSha256OutputSize) { - secret_.resize(kSha256OutputSize); - base::RandBytes(secret_.data(), secret_.size()); + : AuthManager(nullptr, certificate_fingerprint) { + SetSecret(secret); + if (clock) + clock_ = clock; +} + +void AuthManager::SetSecret(const std::vector<uint8_t>& secret) { + secret_ = secret.size() == kSha256OutputSize ? secret : CreateSecret(); + if (config_ && config_->GetSettings().secret != secret_) { + Config::Transaction change{config_}; + change.set_secret(secret); + change.set_root_client_token_owner(RootClientTokenOwner::kNone); + change.Commit(); } } @@ -112,7 +132,7 @@ std::vector<uint8_t> AuthManager::ClaimRootClientAuthToken() { pending_claims_.push_back( - std::unique_ptr<AuthManager>{new AuthManager{{}, {}, clock_}}); + std::unique_ptr<AuthManager>{new AuthManager{nullptr, {}}}); if (pending_claims_.size() > kMaxPendingClaims) pending_claims_.pop_front(); return pending_claims_.back()->GetRootClientAuthToken(); @@ -144,6 +164,7 @@ scope.GetCaveat(), issued.GetCaveat(), }; + CHECK_EQ(kSha256OutputSize, secret_.size()); UwMacaroon macaroon{}; CHECK(uw_macaroon_new_from_root_key_( &macaroon, secret_.data(), secret_.size(), caveats, arraysize(caveats))); @@ -167,6 +188,7 @@ return false; } + CHECK_EQ(kSha256OutputSize, secret_.size()); return uw_macaroon_verify_(&macaroon, secret_.data(), secret_.size()); }
diff --git a/src/privet/auth_manager.h b/src/privet/auth_manager.h index 8fcadfc..dd4ad3d 100644 --- a/src/privet/auth_manager.h +++ b/src/privet/auth_manager.h
@@ -16,10 +16,17 @@ #include "src/privet/privet_types.h" namespace weave { + +class Config; + namespace privet { class AuthManager { public: + AuthManager(Config* config, + const std::vector<uint8_t>& certificate_fingerprint); + + // Constructor for tests. AuthManager(const std::vector<uint8_t>& secret, const std::vector<uint8_t>& certificate_fingerprint, base::Clock* clock = nullptr); @@ -43,8 +50,11 @@ bool IsValidAuthToken(const std::vector<uint8_t>& token) const; private: + void SetSecret(const std::vector<uint8_t>& secret); + + Config* config_{nullptr}; base::DefaultClock default_clock_; - base::Clock* clock_{nullptr}; + base::Clock* clock_{&default_clock_}; std::vector<uint8_t> secret_; std::vector<uint8_t> certificate_fingerprint_;
diff --git a/src/privet/security_manager_unittest.cc b/src/privet/security_manager_unittest.cc index d9f5c56..7c26026 100644 --- a/src/privet/security_manager_unittest.cc +++ b/src/privet/security_manager_unittest.cc
@@ -104,11 +104,11 @@ test::MockClock clock_; AuthManager auth_manager_{ {}, - {{ + { 59, 47, 77, 247, 129, 187, 188, 158, 172, 105, 246, 93, 102, 83, 8, 138, 176, 141, 37, 63, 223, 40, 153, 121, 134, 23, 120, 106, 24, 205, 7, 135, - }}, + }, &clock_}; SecurityManager security_{&auth_manager_, {PairingType::kEmbeddedCode},