Switch crypto::SignatureVerifier to base::span.
Bug: 830085, 559302 Change-Id: I5dc2bc41154846fd69e276c8d64727ecd6764052 Reviewed-on: https://chromium-review.googlesource.com/919318 Commit-Queue: David Benjamin <davidben@chromium.org> Reviewed-by: Maksim Ivanov <emaxx@chromium.org> Reviewed-by: Ilya Sherman <isherman@chromium.org> Reviewed-by: Sorin Jianu <sorin@chromium.org> Reviewed-by: Kinuko Yasuda <kinuko@chromium.org> Reviewed-by: Istiaque Ahmed <lazyboy@chromium.org> Reviewed-by: Daniel Cheng <dcheng@chromium.org> Reviewed-by: Ryan Sleevi <rsleevi@chromium.org> Cr-Commit-Position: refs/heads/master@{#550795}
This commit is contained in:

committed by
Commit Bot

parent
53e13c2003
commit
8ed9231998
chrome/browser/extensions
components
client_update_protocol
crx_file
policy
core
common
variations
content/browser/web_package
crypto
ec_signature_creator_unittest.ccsignature_creator_unittest.ccsignature_verifier.ccsignature_verifier.hsignature_verifier_unittest.cc
extensions/browser
net/quic/chromium/crypto
@ -259,16 +259,12 @@ bool InstallSigner::VerifySignature(const InstallSignature& signature) {
|
||||
return false;
|
||||
|
||||
crypto::SignatureVerifier verifier;
|
||||
if (!verifier.VerifyInit(
|
||||
crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
reinterpret_cast<const uint8_t*>(signature.signature.data()),
|
||||
signature.signature.size(),
|
||||
reinterpret_cast<const uint8_t*>(public_key.data()),
|
||||
public_key.size()))
|
||||
if (!verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
base::as_bytes<const char>(signature.signature),
|
||||
base::as_bytes<const char>(public_key)))
|
||||
return false;
|
||||
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(signed_data.data()),
|
||||
signed_data.size());
|
||||
verifier.VerifyUpdate(base::as_bytes<const char>(signed_data));
|
||||
return verifier.VerifyFinal();
|
||||
}
|
||||
|
||||
|
@ -170,9 +170,8 @@ bool Ecdsa::ValidateResponse(const base::StringPiece& response_body,
|
||||
|
||||
// Initialize the signature verifier.
|
||||
crypto::SignatureVerifier verifier;
|
||||
if (!verifier.VerifyInit(crypto::SignatureVerifier::ECDSA_SHA256,
|
||||
&signature.front(), signature.size(),
|
||||
&public_key_.front(), public_key_.size())) {
|
||||
if (!verifier.VerifyInit(crypto::SignatureVerifier::ECDSA_SHA256, signature,
|
||||
public_key_)) {
|
||||
DVLOG(1) << "Couldn't init SignatureVerifier.";
|
||||
return false;
|
||||
}
|
||||
@ -182,8 +181,7 @@ bool Ecdsa::ValidateResponse(const base::StringPiece& response_body,
|
||||
// * The buffer that the server signed does not match the buffer that the
|
||||
// client assembled -- implying that either request body or response body
|
||||
// was modified, or a different nonce value was used.
|
||||
verifier.VerifyUpdate(&signed_message_hash.front(),
|
||||
signed_message_hash.size());
|
||||
verifier.VerifyUpdate(signed_message_hash);
|
||||
return verifier.VerifyFinal();
|
||||
}
|
||||
|
||||
|
@ -76,7 +76,7 @@ bool ReadHashAndVerifyArchive(base::File* file,
|
||||
size_t len = 0;
|
||||
while ((len = ReadAndHashBuffer(buffer, arraysize(buffer), file, hash)) > 0) {
|
||||
for (auto& verifier : verifiers)
|
||||
verifier->VerifyUpdate(buffer, len);
|
||||
verifier->VerifyUpdate(base::make_span(buffer, len));
|
||||
}
|
||||
for (auto& verifier : verifiers) {
|
||||
if (!verifier->VerifyFinal())
|
||||
@ -163,16 +163,12 @@ VerifierResult VerifyCrx3(
|
||||
auto v = std::make_unique<crypto::SignatureVerifier>();
|
||||
static_assert(sizeof(unsigned char) == sizeof(uint8_t),
|
||||
"Unsupported char size.");
|
||||
if (!v->VerifyInit(
|
||||
proof_type.second, reinterpret_cast<const uint8_t*>(sig.data()),
|
||||
sig.size(), reinterpret_cast<const uint8_t*>(key.data()),
|
||||
key.size()))
|
||||
if (!v->VerifyInit(proof_type.second, base::as_bytes<const char>(sig),
|
||||
base::as_bytes<const char>(key)))
|
||||
return VerifierResult::ERROR_SIGNATURE_INITIALIZATION_FAILED;
|
||||
v->VerifyUpdate(kSignatureContext, arraysize(kSignatureContext));
|
||||
v->VerifyUpdate(header_size_octets, arraysize(header_size_octets));
|
||||
v->VerifyUpdate(
|
||||
reinterpret_cast<const uint8_t*>(signed_header_data_str.data()),
|
||||
signed_header_data_str.size());
|
||||
v->VerifyUpdate(kSignatureContext);
|
||||
v->VerifyUpdate(header_size_octets);
|
||||
v->VerifyUpdate(base::as_bytes<const char>(signed_header_data_str));
|
||||
verifiers.push_back(std::move(v));
|
||||
}
|
||||
}
|
||||
@ -221,9 +217,8 @@ VerifierResult VerifyCrx2(
|
||||
return VerifierResult::ERROR_HEADER_INVALID;
|
||||
std::vector<std::unique_ptr<crypto::SignatureVerifier>> verifiers;
|
||||
verifiers.push_back(std::make_unique<crypto::SignatureVerifier>());
|
||||
if (!verifiers[0]->VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
sig.data(), sig.size(), key.data(),
|
||||
key.size())) {
|
||||
if (!verifiers[0]->VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1, sig,
|
||||
key)) {
|
||||
return VerifierResult::ERROR_SIGNATURE_INITIALIZATION_FAILED;
|
||||
}
|
||||
|
||||
|
@ -569,15 +569,12 @@ bool CloudPolicyValidatorBase::VerifySignature(const std::string& data,
|
||||
return false;
|
||||
}
|
||||
|
||||
if (!verifier.VerifyInit(
|
||||
algorithm, reinterpret_cast<const uint8_t*>(signature.c_str()),
|
||||
signature.size(), reinterpret_cast<const uint8_t*>(key.c_str()),
|
||||
key.size())) {
|
||||
if (!verifier.VerifyInit(algorithm, base::as_bytes<const char>(signature),
|
||||
base::as_bytes<const char>(key))) {
|
||||
DLOG(ERROR) << "Invalid verification signature/key format";
|
||||
return false;
|
||||
}
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(data.c_str()),
|
||||
data.size());
|
||||
verifier.VerifyUpdate(base::as_bytes<const char>(data));
|
||||
return verifier.VerifyFinal();
|
||||
}
|
||||
|
||||
|
@ -62,14 +62,11 @@ VerifySignatureResult VerifySeedSignature(
|
||||
|
||||
crypto::SignatureVerifier verifier;
|
||||
if (!verifier.VerifyInit(crypto::SignatureVerifier::ECDSA_SHA256,
|
||||
reinterpret_cast<const uint8_t*>(signature.data()),
|
||||
signature.size(), kPublicKey,
|
||||
arraysize(kPublicKey))) {
|
||||
base::as_bytes<const char>(signature), kPublicKey)) {
|
||||
return VerifySignatureResult::INVALID_SIGNATURE;
|
||||
}
|
||||
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(seed_bytes.data()),
|
||||
seed_bytes.size());
|
||||
verifier.VerifyUpdate(base::as_bytes<const char>(seed_bytes));
|
||||
if (!verifier.VerifyFinal())
|
||||
return VerifySignatureResult::INVALID_SEED;
|
||||
|
||||
|
@ -169,14 +169,13 @@ bool VerifySignature(
|
||||
// TODO(crbug.com/803774): This is missing the digitalSignature key usage bit
|
||||
// check.
|
||||
crypto::SignatureVerifier verifier;
|
||||
if (!verifier.VerifyInit(
|
||||
crypto::SignatureVerifier::RSA_PSS_SHA256, sig.data(), sig.size(),
|
||||
reinterpret_cast<const uint8_t*>(spki.data()), spki.size())) {
|
||||
if (!verifier.VerifyInit(crypto::SignatureVerifier::RSA_PSS_SHA256, sig,
|
||||
base::as_bytes<const char>(spki))) {
|
||||
signed_exchange_utils::RunErrorMessageCallbackAndEndTraceEvent(
|
||||
"VerifySignature", error_message_callback, "VerifyInit failed.");
|
||||
return false;
|
||||
}
|
||||
verifier.VerifyUpdate(msg.data(), msg.size());
|
||||
verifier.VerifyUpdate(msg);
|
||||
if (!verifier.VerifyFinal()) {
|
||||
signed_exchange_utils::RunErrorMessageCallbackAndEndTraceEvent(
|
||||
"VerifySignature", error_message_callback, "VerifyFinal failed.");
|
||||
|
@ -44,11 +44,9 @@ TEST(ECSignatureCreatorTest, BasicTest) {
|
||||
ASSERT_TRUE(key_original->ExportPublicKey(&public_key_info));
|
||||
|
||||
crypto::SignatureVerifier verifier;
|
||||
ASSERT_TRUE(verifier.VerifyInit(
|
||||
crypto::SignatureVerifier::ECDSA_SHA256, &signature[0], signature.size(),
|
||||
&public_key_info.front(), public_key_info.size()));
|
||||
ASSERT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::ECDSA_SHA256,
|
||||
signature, public_key_info));
|
||||
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(data.c_str()),
|
||||
data.size());
|
||||
verifier.VerifyUpdate(base::as_bytes<const char>(data));
|
||||
ASSERT_TRUE(verifier.VerifyFinal());
|
||||
}
|
||||
|
@ -44,12 +44,10 @@ TEST(SignatureCreatorTest, BasicTest) {
|
||||
ASSERT_TRUE(key_original->ExportPublicKey(&public_key_info));
|
||||
|
||||
crypto::SignatureVerifier verifier;
|
||||
ASSERT_TRUE(verifier.VerifyInit(
|
||||
crypto::SignatureVerifier::RSA_PKCS1_SHA1, &signature.front(),
|
||||
signature.size(), &public_key_info.front(), public_key_info.size()));
|
||||
ASSERT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
signature, public_key_info));
|
||||
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(data.c_str()),
|
||||
data.size());
|
||||
verifier.VerifyUpdate(base::as_bytes<const char>(data));
|
||||
ASSERT_TRUE(verifier.VerifyFinal());
|
||||
}
|
||||
|
||||
@ -78,12 +76,10 @@ TEST(SignatureCreatorTest, SignDigestTest) {
|
||||
|
||||
// Verify the input data.
|
||||
crypto::SignatureVerifier verifier;
|
||||
ASSERT_TRUE(verifier.VerifyInit(
|
||||
crypto::SignatureVerifier::RSA_PKCS1_SHA1, &signature.front(),
|
||||
signature.size(), &public_key_info.front(), public_key_info.size()));
|
||||
ASSERT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
signature, public_key_info));
|
||||
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(data.c_str()),
|
||||
data.size());
|
||||
verifier.VerifyUpdate(base::as_bytes<const char>(data));
|
||||
ASSERT_TRUE(verifier.VerifyFinal());
|
||||
}
|
||||
|
||||
@ -113,11 +109,9 @@ TEST(SignatureCreatorTest, SignSHA256DigestTest) {
|
||||
|
||||
// Verify the input data.
|
||||
crypto::SignatureVerifier verifier;
|
||||
ASSERT_TRUE(verifier.VerifyInit(
|
||||
crypto::SignatureVerifier::RSA_PKCS1_SHA256, &signature.front(),
|
||||
signature.size(), &public_key_info.front(), public_key_info.size()));
|
||||
ASSERT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA256,
|
||||
signature, public_key_info));
|
||||
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(data.c_str()),
|
||||
data.size());
|
||||
verifier.VerifyUpdate(base::as_bytes<const char>(data));
|
||||
ASSERT_TRUE(verifier.VerifyFinal());
|
||||
}
|
||||
|
@ -27,10 +27,8 @@ SignatureVerifier::SignatureVerifier() = default;
|
||||
SignatureVerifier::~SignatureVerifier() = default;
|
||||
|
||||
bool SignatureVerifier::VerifyInit(SignatureAlgorithm signature_algorithm,
|
||||
const uint8_t* signature,
|
||||
size_t signature_len,
|
||||
const uint8_t* public_key_info,
|
||||
size_t public_key_info_len) {
|
||||
base::span<const uint8_t> signature,
|
||||
base::span<const uint8_t> public_key_info) {
|
||||
OpenSSLErrStackTracer err_tracer(FROM_HERE);
|
||||
|
||||
int pkey_type = EVP_PKEY_NONE;
|
||||
@ -57,10 +55,10 @@ bool SignatureVerifier::VerifyInit(SignatureAlgorithm signature_algorithm,
|
||||
return false;
|
||||
|
||||
verify_context_.reset(new VerifyContext);
|
||||
signature_.assign(signature, signature + signature_len);
|
||||
signature_.assign(signature.data(), signature.data() + signature.size());
|
||||
|
||||
CBS cbs;
|
||||
CBS_init(&cbs, public_key_info, public_key_info_len);
|
||||
CBS_init(&cbs, public_key_info.data(), public_key_info.size());
|
||||
bssl::UniquePtr<EVP_PKEY> public_key(EVP_parse_public_key(&cbs));
|
||||
if (!public_key || CBS_len(&cbs) != 0 ||
|
||||
EVP_PKEY_id(public_key.get()) != pkey_type) {
|
||||
@ -85,12 +83,11 @@ bool SignatureVerifier::VerifyInit(SignatureAlgorithm signature_algorithm,
|
||||
return true;
|
||||
}
|
||||
|
||||
void SignatureVerifier::VerifyUpdate(const uint8_t* data_part,
|
||||
size_t data_part_len) {
|
||||
void SignatureVerifier::VerifyUpdate(base::span<const uint8_t> data_part) {
|
||||
DCHECK(verify_context_);
|
||||
OpenSSLErrStackTracer err_tracer(FROM_HERE);
|
||||
int rv = EVP_DigestVerifyUpdate(verify_context_->ctx.get(), data_part,
|
||||
data_part_len);
|
||||
int rv = EVP_DigestVerifyUpdate(verify_context_->ctx.get(), data_part.data(),
|
||||
data_part.size());
|
||||
DCHECK_EQ(rv, 1);
|
||||
}
|
||||
|
||||
|
@ -10,6 +10,7 @@
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
|
||||
#include "base/containers/span.h"
|
||||
#include "build/build_config.h"
|
||||
#include "crypto/crypto_export.h"
|
||||
|
||||
@ -46,13 +47,11 @@ class CRYPTO_EXPORT SignatureVerifier {
|
||||
// algorithm AlgorithmIdentifier,
|
||||
// subjectPublicKey BIT STRING }
|
||||
bool VerifyInit(SignatureAlgorithm signature_algorithm,
|
||||
const uint8_t* signature,
|
||||
size_t signature_len,
|
||||
const uint8_t* public_key_info,
|
||||
size_t public_key_info_len);
|
||||
base::span<const uint8_t> signature,
|
||||
base::span<const uint8_t> public_key_info);
|
||||
|
||||
// Feeds a piece of the data to the signature verifier.
|
||||
void VerifyUpdate(const uint8_t* data_part, size_t data_part_len);
|
||||
void VerifyUpdate(base::span<const uint8_t> data_part);
|
||||
|
||||
// Concludes a signature verification operation. Returns true if the
|
||||
// signature is valid. Returns false if the signature is invalid or an
|
||||
|
@ -188,75 +188,55 @@ TEST(SignatureVerifierTest, BasicTest) {
|
||||
// We use the signature verifier to perform four signature verification
|
||||
// tests.
|
||||
crypto::SignatureVerifier verifier;
|
||||
bool ok;
|
||||
|
||||
// Test 1: feed all of the data to the verifier at once (a single
|
||||
// VerifyUpdate call).
|
||||
ok = verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1, signature,
|
||||
sizeof(signature), public_key_info,
|
||||
sizeof(public_key_info));
|
||||
EXPECT_TRUE(ok);
|
||||
verifier.VerifyUpdate(tbs_certificate, sizeof(tbs_certificate));
|
||||
ok = verifier.VerifyFinal();
|
||||
EXPECT_TRUE(ok);
|
||||
EXPECT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
signature, public_key_info));
|
||||
verifier.VerifyUpdate(tbs_certificate);
|
||||
EXPECT_TRUE(verifier.VerifyFinal());
|
||||
|
||||
// Test 2: feed the data to the verifier in three parts (three VerifyUpdate
|
||||
// calls).
|
||||
ok = verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1, signature,
|
||||
sizeof(signature), public_key_info,
|
||||
sizeof(public_key_info));
|
||||
EXPECT_TRUE(ok);
|
||||
verifier.VerifyUpdate(tbs_certificate, 256);
|
||||
verifier.VerifyUpdate(tbs_certificate + 256, 256);
|
||||
verifier.VerifyUpdate(tbs_certificate + 512, sizeof(tbs_certificate) - 512);
|
||||
ok = verifier.VerifyFinal();
|
||||
EXPECT_TRUE(ok);
|
||||
EXPECT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
signature, public_key_info));
|
||||
verifier.VerifyUpdate(base::make_span(tbs_certificate, 256));
|
||||
verifier.VerifyUpdate(base::make_span(tbs_certificate + 256, 256));
|
||||
verifier.VerifyUpdate(
|
||||
base::make_span(tbs_certificate + 512, sizeof(tbs_certificate) - 512));
|
||||
EXPECT_TRUE(verifier.VerifyFinal());
|
||||
|
||||
// Test 3: verify the signature with incorrect data.
|
||||
uint8_t bad_tbs_certificate[sizeof(tbs_certificate)];
|
||||
memcpy(bad_tbs_certificate, tbs_certificate, sizeof(tbs_certificate));
|
||||
bad_tbs_certificate[10] += 1; // Corrupt one byte of the data.
|
||||
ok = verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1, signature,
|
||||
sizeof(signature), public_key_info,
|
||||
sizeof(public_key_info));
|
||||
EXPECT_TRUE(ok);
|
||||
verifier.VerifyUpdate(bad_tbs_certificate, sizeof(bad_tbs_certificate));
|
||||
ok = verifier.VerifyFinal();
|
||||
EXPECT_FALSE(ok);
|
||||
EXPECT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
signature, public_key_info));
|
||||
verifier.VerifyUpdate(bad_tbs_certificate);
|
||||
EXPECT_FALSE(verifier.VerifyFinal());
|
||||
|
||||
// Test 4: verify a bad signature.
|
||||
uint8_t bad_signature[sizeof(signature)];
|
||||
memcpy(bad_signature, signature, sizeof(signature));
|
||||
bad_signature[10] += 1; // Corrupt one byte of the signature.
|
||||
ok = verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
bad_signature, sizeof(bad_signature),
|
||||
public_key_info, sizeof(public_key_info));
|
||||
|
||||
// A crypto library (e.g., NSS) may detect that the signature is corrupted
|
||||
// and cause VerifyInit to return false, so it is fine for 'ok' to be false.
|
||||
if (ok) {
|
||||
verifier.VerifyUpdate(tbs_certificate, sizeof(tbs_certificate));
|
||||
ok = verifier.VerifyFinal();
|
||||
EXPECT_FALSE(ok);
|
||||
}
|
||||
EXPECT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
bad_signature, public_key_info));
|
||||
verifier.VerifyUpdate(tbs_certificate);
|
||||
EXPECT_FALSE(verifier.VerifyFinal());
|
||||
|
||||
// Test 5: import an invalid key.
|
||||
uint8_t bad_public_key_info[sizeof(public_key_info)];
|
||||
memcpy(bad_public_key_info, public_key_info, sizeof(public_key_info));
|
||||
bad_public_key_info[0] += 1; // Corrupt part of the SPKI syntax.
|
||||
ok = verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1, signature,
|
||||
sizeof(signature), bad_public_key_info,
|
||||
sizeof(bad_public_key_info));
|
||||
EXPECT_FALSE(ok);
|
||||
EXPECT_FALSE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
signature, bad_public_key_info));
|
||||
|
||||
// Test 6: import a key with extra data.
|
||||
uint8_t long_public_key_info[sizeof(public_key_info) + 5];
|
||||
memset(long_public_key_info, 0, sizeof(long_public_key_info));
|
||||
memcpy(long_public_key_info, public_key_info, sizeof(public_key_info));
|
||||
ok = verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1, signature,
|
||||
sizeof(signature), long_public_key_info,
|
||||
sizeof(long_public_key_info));
|
||||
EXPECT_FALSE(ok);
|
||||
EXPECT_FALSE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PKCS1_SHA1,
|
||||
signature, long_public_key_info));
|
||||
}
|
||||
|
||||
// The following RSA-PSS tests were generated via the following OpenSSL
|
||||
@ -394,35 +374,30 @@ TEST(SignatureVerifierTest, VerifyRSAPSS) {
|
||||
// Verify the test vector.
|
||||
crypto::SignatureVerifier verifier;
|
||||
ASSERT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PSS_SHA256,
|
||||
kPSSSignatureGood, sizeof(kPSSSignatureGood),
|
||||
kPSSPublicKey, sizeof(kPSSPublicKey)));
|
||||
verifier.VerifyUpdate(kPSSMessage, sizeof(kPSSMessage));
|
||||
kPSSSignatureGood, kPSSPublicKey));
|
||||
verifier.VerifyUpdate(kPSSMessage);
|
||||
EXPECT_TRUE(verifier.VerifyFinal());
|
||||
|
||||
// Verify the test vector byte-by-byte.
|
||||
ASSERT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PSS_SHA256,
|
||||
kPSSSignatureGood, sizeof(kPSSSignatureGood),
|
||||
kPSSPublicKey, sizeof(kPSSPublicKey)));
|
||||
kPSSSignatureGood, kPSSPublicKey));
|
||||
for (uint8_t b : kPSSMessage) {
|
||||
verifier.VerifyUpdate(&b, 1);
|
||||
verifier.VerifyUpdate(base::make_span(&b, 1));
|
||||
}
|
||||
EXPECT_TRUE(verifier.VerifyFinal());
|
||||
|
||||
// The bad salt length does not verify.
|
||||
ASSERT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PSS_SHA256,
|
||||
kPSSSignatureBadSaltLength,
|
||||
sizeof(kPSSSignatureBadSaltLength),
|
||||
kPSSPublicKey, sizeof(kPSSPublicKey)));
|
||||
verifier.VerifyUpdate(kPSSMessage, sizeof(kPSSMessage));
|
||||
kPSSSignatureBadSaltLength, kPSSPublicKey));
|
||||
verifier.VerifyUpdate(kPSSMessage);
|
||||
EXPECT_FALSE(verifier.VerifyFinal());
|
||||
|
||||
// Corrupt the message.
|
||||
std::vector<uint8_t> message(std::begin(kPSSMessage), std::end(kPSSMessage));
|
||||
message[0] ^= 1;
|
||||
ASSERT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PSS_SHA256,
|
||||
kPSSSignatureGood, sizeof(kPSSSignatureGood),
|
||||
kPSSPublicKey, sizeof(kPSSPublicKey)));
|
||||
verifier.VerifyUpdate(message.data(), message.size());
|
||||
kPSSSignatureGood, kPSSPublicKey));
|
||||
verifier.VerifyUpdate(message);
|
||||
EXPECT_FALSE(verifier.VerifyFinal());
|
||||
|
||||
// Corrupt the signature.
|
||||
@ -430,8 +405,7 @@ TEST(SignatureVerifierTest, VerifyRSAPSS) {
|
||||
std::end(kPSSSignatureGood));
|
||||
signature[0] ^= 1;
|
||||
ASSERT_TRUE(verifier.VerifyInit(crypto::SignatureVerifier::RSA_PSS_SHA256,
|
||||
signature.data(), signature.size(),
|
||||
kPSSPublicKey, sizeof(kPSSPublicKey)));
|
||||
verifier.VerifyUpdate(kPSSMessage, sizeof(kPSSMessage));
|
||||
signature, kPSSPublicKey));
|
||||
verifier.VerifyUpdate(kPSSMessage);
|
||||
EXPECT_FALSE(verifier.VerifyFinal());
|
||||
}
|
||||
|
@ -46,8 +46,7 @@ std::unique_ptr<VerifiedContents> GetVerifiedContents(
|
||||
bool delete_invalid_file) {
|
||||
base::AssertBlockingAllowed();
|
||||
DCHECK(GetExtensionFileTaskRunner()->RunsTasksInCurrentSequence());
|
||||
auto verified_contents = std::make_unique<VerifiedContents>(
|
||||
key.verifier_key.data, key.verifier_key.size);
|
||||
auto verified_contents = std::make_unique<VerifiedContents>(key.verifier_key);
|
||||
base::FilePath verified_contents_path =
|
||||
file_util::GetVerifiedContentsPath(key.extension_root);
|
||||
if (!verified_contents->InitFrom(verified_contents_path)) {
|
||||
@ -65,12 +64,14 @@ std::unique_ptr<VerifiedContents> GetVerifiedContents(
|
||||
ContentHash::ExtensionKey::ExtensionKey(const ExtensionId& extension_id,
|
||||
const base::FilePath& extension_root,
|
||||
const base::Version& extension_version,
|
||||
const ContentVerifierKey& verifier_key)
|
||||
ContentVerifierKey verifier_key)
|
||||
: extension_id(extension_id),
|
||||
extension_root(extension_root),
|
||||
extension_version(extension_version),
|
||||
verifier_key(verifier_key) {}
|
||||
|
||||
ContentHash::ExtensionKey::~ExtensionKey() = default;
|
||||
|
||||
ContentHash::ExtensionKey::ExtensionKey(
|
||||
const ContentHash::ExtensionKey& other) = default;
|
||||
|
||||
|
@ -62,7 +62,8 @@ class ContentHash : public base::RefCountedThreadSafe<ContentHash> {
|
||||
ExtensionKey(const ExtensionId& extension_id,
|
||||
const base::FilePath& extension_root,
|
||||
const base::Version& extension_version,
|
||||
const ContentVerifierKey& verifier_key);
|
||||
ContentVerifierKey verifier_key);
|
||||
~ExtensionKey();
|
||||
|
||||
ExtensionKey(const ExtensionKey& other);
|
||||
ExtensionKey& operator=(const ExtensionKey& other);
|
||||
|
@ -5,19 +5,11 @@
|
||||
#ifndef EXTENSIONS_BROWSER_CONTENT_VERIFIER_CONTENT_VERIFIER_KEY_H_
|
||||
#define EXTENSIONS_BROWSER_CONTENT_VERIFIER_CONTENT_VERIFIER_KEY_H_
|
||||
|
||||
#include <stdint.h>
|
||||
#include "base/containers/span.h"
|
||||
|
||||
namespace extensions {
|
||||
|
||||
// A pointer to the bytes of a public key, and the number of bytes for content
|
||||
// verification.
|
||||
struct ContentVerifierKey {
|
||||
const uint8_t* data;
|
||||
size_t size;
|
||||
|
||||
ContentVerifierKey(const uint8_t* data, size_t size)
|
||||
: data(data), size(size) {}
|
||||
};
|
||||
using ContentVerifierKey = base::span<const uint8_t>;
|
||||
|
||||
} // namespace extensions
|
||||
|
||||
|
@ -62,10 +62,8 @@ const DictionaryValue* FindDictionaryWithValue(const ListValue* list,
|
||||
|
||||
namespace extensions {
|
||||
|
||||
VerifiedContents::VerifiedContents(const uint8_t* public_key,
|
||||
size_t public_key_size)
|
||||
VerifiedContents::VerifiedContents(base::span<const uint8_t> public_key)
|
||||
: public_key_(public_key),
|
||||
public_key_size_(public_key_size),
|
||||
valid_signature_(false), // Guilty until proven innocent.
|
||||
block_size_(0) {}
|
||||
|
||||
@ -301,22 +299,17 @@ bool VerifiedContents::VerifySignature(const std::string& protected_value,
|
||||
crypto::SignatureVerifier signature_verifier;
|
||||
if (!signature_verifier.VerifyInit(
|
||||
crypto::SignatureVerifier::RSA_PKCS1_SHA256,
|
||||
reinterpret_cast<const uint8_t*>(signature_bytes.data()),
|
||||
signature_bytes.size(), public_key_, public_key_size_)) {
|
||||
base::as_bytes<const char>(signature_bytes), public_key_)) {
|
||||
VLOG(1) << "Could not verify signature - VerifyInit failure";
|
||||
return false;
|
||||
}
|
||||
|
||||
signature_verifier.VerifyUpdate(
|
||||
reinterpret_cast<const uint8_t*>(protected_value.data()),
|
||||
protected_value.size());
|
||||
signature_verifier.VerifyUpdate(base::as_bytes<const char>(protected_value));
|
||||
|
||||
std::string dot(".");
|
||||
signature_verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(dot.data()),
|
||||
dot.size());
|
||||
signature_verifier.VerifyUpdate(base::as_bytes<const char>(dot));
|
||||
|
||||
signature_verifier.VerifyUpdate(
|
||||
reinterpret_cast<const uint8_t*>(payload.data()), payload.size());
|
||||
signature_verifier.VerifyUpdate(base::as_bytes<const char>(payload));
|
||||
|
||||
if (!signature_verifier.VerifyFinal()) {
|
||||
VLOG(1) << "Could not verify signature - VerifyFinal failure";
|
||||
|
@ -11,6 +11,7 @@
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include "base/containers/span.h"
|
||||
#include "base/files/file_path.h"
|
||||
#include "base/macros.h"
|
||||
#include "base/version.h"
|
||||
@ -24,7 +25,7 @@ namespace extensions {
|
||||
class VerifiedContents {
|
||||
public:
|
||||
// Note: the public_key must remain valid for the lifetime of this object.
|
||||
VerifiedContents(const uint8_t* public_key, size_t public_key_size);
|
||||
explicit VerifiedContents(base::span<const uint8_t> public_key);
|
||||
~VerifiedContents();
|
||||
|
||||
// Returns true if we successfully parsed the verified_contents.json file at
|
||||
@ -58,8 +59,7 @@ class VerifiedContents {
|
||||
const std::string& signature_bytes);
|
||||
|
||||
// The public key we should use for signature verification.
|
||||
const uint8_t* public_key_;
|
||||
const size_t public_key_size_;
|
||||
base::span<const uint8_t> public_key_;
|
||||
|
||||
// Indicates whether the signature was successfully validated or not.
|
||||
bool valid_signature_;
|
||||
|
@ -53,8 +53,7 @@ TEST(VerifiedContents, Simple) {
|
||||
// Initialize the VerifiedContents object.
|
||||
std::string public_key;
|
||||
ASSERT_TRUE(GetPublicKey(path.AppendASCII(kPublicKeyPem), &public_key));
|
||||
VerifiedContents contents(reinterpret_cast<const uint8_t*>(public_key.data()),
|
||||
public_key.size());
|
||||
VerifiedContents contents(base::as_bytes<const char>(public_key));
|
||||
base::FilePath verified_contents_path =
|
||||
path.AppendASCII("verified_contents.json");
|
||||
|
||||
@ -147,8 +146,7 @@ TEST(VerifiedContents, FailsOnBase64) {
|
||||
// Initialize the VerifiedContents object.
|
||||
std::string public_key;
|
||||
ASSERT_TRUE(GetPublicKey(path.AppendASCII(kPublicKeyPem), &public_key));
|
||||
VerifiedContents contents(reinterpret_cast<const uint8_t*>(public_key.data()),
|
||||
public_key.size());
|
||||
VerifiedContents contents(base::as_bytes<const char>(public_key));
|
||||
|
||||
base::FilePath verified_contents_path =
|
||||
path.AppendASCII("verified_contents_base64.json");
|
||||
|
@ -535,23 +535,21 @@ bool ProofVerifierChromium::Job::VerifySignature(
|
||||
}
|
||||
|
||||
crypto::SignatureVerifier verifier;
|
||||
if (!verifier.VerifyInit(
|
||||
algorithm, reinterpret_cast<const uint8_t*>(signature.data()),
|
||||
signature.size(), reinterpret_cast<const uint8_t*>(spki.data()),
|
||||
spki.size())) {
|
||||
if (!verifier.VerifyInit(algorithm, base::as_bytes<const char>(signature),
|
||||
base::as_bytes<const char>(spki))) {
|
||||
DLOG(WARNING) << "VerifyInit failed";
|
||||
return false;
|
||||
}
|
||||
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(kProofSignatureLabel),
|
||||
sizeof(kProofSignatureLabel));
|
||||
verifier.VerifyUpdate(
|
||||
base::make_span(reinterpret_cast<const uint8_t*>(kProofSignatureLabel),
|
||||
sizeof(kProofSignatureLabel)));
|
||||
uint32_t len = chlo_hash.length();
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(&len), sizeof(len));
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(chlo_hash.data()),
|
||||
len);
|
||||
verifier.VerifyUpdate(
|
||||
base::make_span(reinterpret_cast<const uint8_t*>(&len), sizeof(len)));
|
||||
verifier.VerifyUpdate(base::as_bytes<const char>(chlo_hash));
|
||||
|
||||
verifier.VerifyUpdate(reinterpret_cast<const uint8_t*>(signed_data.data()),
|
||||
signed_data.size());
|
||||
verifier.VerifyUpdate(base::as_bytes<const char>(signed_data));
|
||||
|
||||
if (!verifier.VerifyFinal()) {
|
||||
DLOG(WARNING) << "VerifyFinal failed";
|
||||
|
Reference in New Issue
Block a user