aboutsummaryrefslogtreecommitdiff
path: root/cast/sender
diff options
context:
space:
mode:
authorbtolsch <btolsch@chromium.org>2019-12-17 18:23:10 -0800
committerCommit Bot <commit-bot@chromium.org>2019-12-18 02:36:32 +0000
commit3fb84816856bd15c694fb275b40e609472064c4f (patch)
tree81c786d9a305a4ec72366b51ba3be57a7a4ae2f9 /cast/sender
parentc310e1bbcb8df5802ea9ea7598a16ea82e122cf9 (diff)
downloadopenscreen-3fb84816856bd15c694fb275b40e609472064c4f.tar.gz
Add receiver authentication steps
This change adds the necessary crypto + messaging steps for a Cast receiver to authenticate itself as such. It also adds an integration test that checks our sender authentication code against this receiver authentication code. Bug: openscreen:91 Change-Id: If298b8781bc95116714eb36fa68ef96ba82742a3 Reviewed-on: https://chromium-review.googlesource.com/c/openscreen/+/1954745 Commit-Queue: Brandon Tolsch <btolsch@chromium.org> Reviewed-by: mark a. foltz <mfoltz@chromium.org>
Diffstat (limited to 'cast/sender')
-rw-r--r--cast/sender/BUILD.gn3
-rw-r--r--cast/sender/channel/cast_auth_util.cc56
-rw-r--r--cast/sender/channel/cast_auth_util.h19
-rw-r--r--cast/sender/channel/cast_auth_util_unittest.cc15
4 files changed, 77 insertions, 16 deletions
diff --git a/cast/sender/BUILD.gn b/cast/sender/BUILD.gn
index f42d555c..ae36bf27 100644
--- a/cast/sender/BUILD.gn
+++ b/cast/sender/BUILD.gn
@@ -22,6 +22,8 @@ source_set("channel") {
public_deps = [
"../../platform",
"../../third_party/boringssl",
+ "../common:certificate",
+ "../common:channel",
]
}
@@ -34,6 +36,7 @@ source_set("unittests") {
deps = [
":channel",
"../../platform",
+ "../../testing/util",
"../../third_party/googletest:gtest",
"../common/certificate/proto:certificate_proto",
"../common/certificate/proto:certificate_unittest_proto",
diff --git a/cast/sender/channel/cast_auth_util.cc b/cast/sender/channel/cast_auth_util.cc
index 90d63f77..44a75b98 100644
--- a/cast/sender/channel/cast_auth_util.cc
+++ b/cast/sender/channel/cast_auth_util.cc
@@ -11,6 +11,7 @@
#include "cast/common/certificate/cast_cert_validator.h"
#include "cast/common/certificate/cast_cert_validator_internal.h"
#include "cast/common/certificate/cast_crl.h"
+#include "cast/common/channel/proto/cast_channel.pb.h"
#include "platform/api/time.h"
#include "platform/base/error.h"
#include "util/logging.h"
@@ -222,18 +223,31 @@ openscreen::Error VerifyTLSCertificateValidity(
return openscreen::Error::None();
}
-ErrorOr<CastDeviceCertPolicy> AuthenticateChallengeReply(
+ErrorOr<CastDeviceCertPolicy> VerifyCredentialsImpl(
+ const AuthResponse& response,
+ const std::string& signature_input,
+ const certificate::CRLPolicy& crl_policy,
+ certificate::TrustStore* cast_trust_store,
+ certificate::TrustStore* crl_trust_store,
+ const certificate::DateTime& verification_time,
+ bool enforce_sha256_checking);
+
+ErrorOr<CastDeviceCertPolicy> AuthenticateChallengeReplyImpl(
const CastMessage& challenge_reply,
X509* peer_cert,
- const AuthContext& auth_context) {
+ const AuthContext& auth_context,
+ const certificate::CRLPolicy& crl_policy,
+ certificate::TrustStore* cast_trust_store,
+ certificate::TrustStore* crl_trust_store,
+ const certificate::DateTime& verification_time) {
DeviceAuthMessage auth_message;
openscreen::Error result = ParseAuthMessage(challenge_reply, &auth_message);
if (!result.ok()) {
return result;
}
- result = VerifyTLSCertificateValidity(
- peer_cert, openscreen::GetWallTimeSinceUnixEpoch());
+ result = VerifyTLSCertificateValidity(peer_cert,
+ DateTimeToSeconds(verification_time));
if (!result.ok()) {
return result;
}
@@ -261,7 +275,35 @@ ErrorOr<CastDeviceCertPolicy> AuthenticateChallengeReply(
OSP_DCHECK_EQ(actual_size, peer_cert_der.size());
peer_cert_der.resize(actual_size);
- return VerifyCredentials(response, nonce_response + peer_cert_der);
+ return VerifyCredentialsImpl(response, nonce_response + peer_cert_der,
+ crl_policy, cast_trust_store, crl_trust_store,
+ verification_time, false);
+}
+
+ErrorOr<CastDeviceCertPolicy> AuthenticateChallengeReply(
+ const CastMessage& challenge_reply,
+ X509* peer_cert,
+ const AuthContext& auth_context) {
+ certificate::DateTime now = {};
+ OSP_CHECK(certificate::DateTimeFromSeconds(
+ openscreen::GetWallTimeSinceUnixEpoch().count(), &now));
+ certificate::CRLPolicy policy = certificate::CRLPolicy::kCrlOptional;
+ return AuthenticateChallengeReplyImpl(
+ challenge_reply, peer_cert, auth_context, policy,
+ /* cast_trust_store */ nullptr, /* crl_trust_store */ nullptr, now);
+}
+
+ErrorOr<CastDeviceCertPolicy> AuthenticateChallengeReplyForTest(
+ const CastMessage& challenge_reply,
+ X509* peer_cert,
+ const AuthContext& auth_context,
+ certificate::CRLPolicy crl_policy,
+ certificate::TrustStore* cast_trust_store,
+ certificate::TrustStore* crl_trust_store,
+ const certificate::DateTime& verification_time) {
+ return AuthenticateChallengeReplyImpl(
+ challenge_reply, peer_cert, auth_context, crl_policy, cast_trust_store,
+ crl_trust_store, verification_time);
}
// This function does the following
@@ -301,8 +343,8 @@ ErrorOr<CastDeviceCertPolicy> VerifyCredentialsImpl(
std::vector<std::string> cert_chain;
cert_chain.push_back(response.client_auth_certificate());
cert_chain.insert(cert_chain.end(),
- response.intermediate_certificate().begin(),
- response.intermediate_certificate().end());
+ response.intermediate_certificates().begin(),
+ response.intermediate_certificates().end());
// Parse the CRL.
std::unique_ptr<certificate::CastCRL> crl;
diff --git a/cast/sender/channel/cast_auth_util.h b/cast/sender/channel/cast_auth_util.h
index 35f1d028..b3ea452f 100644
--- a/cast/sender/channel/cast_auth_util.h
+++ b/cast/sender/channel/cast_auth_util.h
@@ -7,10 +7,10 @@
#include <openssl/x509.h>
+#include <chrono>
#include <string>
#include "cast/common/certificate/cast_cert_validator.h"
-#include "cast/common/channel/proto/cast_channel.pb.h"
#include "platform/base/error.h"
namespace cast {
@@ -61,6 +61,19 @@ ErrorOr<CastDeviceCertPolicy> AuthenticateChallengeReply(
X509* peer_cert,
const AuthContext& auth_context);
+// Exposed for testing only.
+//
+// Overloaded version of AuthenticateChallengeReply that allows modifying the
+// crl policy, trust stores, and verification times.
+ErrorOr<CastDeviceCertPolicy> AuthenticateChallengeReplyForTest(
+ const CastMessage& challenge_reply,
+ X509* peer_cert,
+ const AuthContext& auth_context,
+ certificate::CRLPolicy crl_policy,
+ certificate::TrustStore* cast_trust_store,
+ certificate::TrustStore* crl_trust_store,
+ const certificate::DateTime& verification_time);
+
// Performs a quick check of the TLS certificate for time validity requirements.
openscreen::Error VerifyTLSCertificateValidity(
X509* peer_cert,
@@ -77,8 +90,8 @@ ErrorOr<CastDeviceCertPolicy> VerifyCredentials(
// Exposed for testing only.
//
-// Overloaded version of VerifyCredentials that allows modifying
-// the crl policy, trust stores, and verification times.
+// Overloaded version of VerifyCredentials that allows modifying the crl policy,
+// trust stores, and verification times.
ErrorOr<CastDeviceCertPolicy> VerifyCredentialsForTest(
const AuthResponse& response,
const std::string& signature_input,
diff --git a/cast/sender/channel/cast_auth_util_unittest.cc b/cast/sender/channel/cast_auth_util_unittest.cc
index b8a8e90c..a4b341e2 100644
--- a/cast/sender/channel/cast_auth_util_unittest.cc
+++ b/cast/sender/channel/cast_auth_util_unittest.cc
@@ -13,6 +13,7 @@
#include "cast/common/channel/proto/cast_channel.pb.h"
#include "gtest/gtest.h"
#include "platform/api/time.h"
+#include "testing/util/read_file.h"
#include "util/logging.h"
namespace cast {
@@ -123,8 +124,9 @@ class CastAuthUtilTest : public testing::Test {
AuthResponse response;
response.set_client_auth_certificate(chain[0]);
- for (size_t i = 1; i < chain.size(); ++i)
- response.add_intermediate_certificate(chain[i]);
+ for (size_t i = 1; i < chain.size(); ++i) {
+ response.add_intermediate_certificates(chain[i]);
+ }
response.set_hash_algorithm(digest_algorithm);
switch (digest_algorithm) {
@@ -168,7 +170,7 @@ TEST_F(CastAuthUtilTest, VerifySuccess) {
TEST_F(CastAuthUtilTest, VerifyBadCA) {
std::string signed_data;
AuthResponse auth_response = CreateAuthResponse(&signed_data, SHA256);
- MangleString(auth_response.mutable_intermediate_certificate(0));
+ MangleString(auth_response.mutable_intermediate_certificates(0));
ErrorOr<CastDeviceCertPolicy> result =
VerifyCredentials(auth_response, signed_data);
EXPECT_FALSE(result);
@@ -354,8 +356,9 @@ ErrorOr<CastDeviceCertPolicy> TestVerifyRevocation(
if (certificate_chain.size() > 0) {
response.set_client_auth_certificate(certificate_chain[0]);
- for (size_t i = 1; i < certificate_chain.size(); ++i)
- response.add_intermediate_certificate(certificate_chain[i]);
+ for (size_t i = 1; i < certificate_chain.size(); ++i) {
+ response.add_intermediate_certificates(certificate_chain[i]);
+ }
}
response.set_crl(crl_bundle);
@@ -447,7 +450,7 @@ bool RunTest(const certificate::DeviceCertTest& test_case) {
// These tests are generated by a test generator in google3.
void RunTestSuite(const std::string& test_suite_file_name) {
std::string testsuite_raw =
- certificate::testing::ReadEntireFileToString(test_suite_file_name);
+ openscreen::ReadEntireFileToString(test_suite_file_name);
certificate::DeviceCertTestSuite test_suite;
EXPECT_TRUE(test_suite.ParseFromString(testsuite_raw));
uint16_t successes = 0;