aboutsummaryrefslogtreecommitdiff
path: root/cc/config
diff options
context:
space:
mode:
authorcinlin <cinlin@google.com>2023-03-14 19:57:58 -0700
committerCopybara-Service <copybara-worker@google.com>2023-03-14 19:59:07 -0700
commite3f5a133dd1e794c71bbf6c4cd269260ace58d10 (patch)
treef61d554dcdb89a62a1cd25115d9634307f5b8fbd /cc/config
parentcec227e3a284606a95692cf3a9da188d09548727 (diff)
downloadtink-e3f5a133dd1e794c71bbf6c4cd269260ace58d10.tar.gz
Define crypto::tink::ConfigFips140_2(). #tinkApiChange
PiperOrigin-RevId: 516701128
Diffstat (limited to 'cc/config')
-rw-r--r--cc/config/BUILD.bazel52
-rw-r--r--cc/config/CMakeLists.txt51
-rw-r--r--cc/config/fips_140_2.cc134
-rw-r--r--cc/config/fips_140_2.h33
-rw-r--r--cc/config/fips_140_2_test.cc138
5 files changed, 408 insertions, 0 deletions
diff --git a/cc/config/BUILD.bazel b/cc/config/BUILD.bazel
index e377fd61f..7ecb7b8e4 100644
--- a/cc/config/BUILD.bazel
+++ b/cc/config/BUILD.bazel
@@ -103,3 +103,55 @@ cc_test(
"@com_google_googletest//:gtest_main",
],
)
+
+cc_library(
+ name = "fips_140_2",
+ srcs = ["fips_140_2.cc"],
+ hdrs = ["fips_140_2.h"],
+ include_prefix = "tink/config",
+ deps = [
+ "//:configuration",
+ "//aead:aead_wrapper",
+ "//aead:aes_ctr_hmac_aead_key_manager",
+ "//aead:aes_gcm_key_manager",
+ "//internal:configuration_impl",
+ "//mac:hmac_key_manager",
+ "//mac:mac_wrapper",
+ "//mac/internal:chunked_mac_wrapper",
+ "//prf:hmac_prf_key_manager",
+ "//prf:prf_set_wrapper",
+ "//signature:ecdsa_sign_key_manager",
+ "//signature:ecdsa_verify_key_manager",
+ "//signature:public_key_sign_wrapper",
+ "//signature:public_key_verify_wrapper",
+ "//signature:rsa_ssa_pkcs1_sign_key_manager",
+ "//signature:rsa_ssa_pkcs1_verify_key_manager",
+ "//signature:rsa_ssa_pss_sign_key_manager",
+ "//signature:rsa_ssa_pss_verify_key_manager",
+ "@com_google_absl//absl/log:check",
+ ],
+)
+
+cc_test(
+ name = "fips_140_2_test",
+ srcs = ["fips_140_2_test.cc"],
+ deps = [
+ ":fips_140_2",
+ "//aead:aead_key_templates",
+ "//aead:aes_ctr_hmac_aead_key_manager",
+ "//aead:aes_gcm_key_manager",
+ "//internal:configuration_impl",
+ "//internal:fips_utils",
+ "//internal:registry_impl",
+ "//mac:aes_cmac_key_manager",
+ "//mac:hmac_key_manager",
+ "//prf:hmac_prf_key_manager",
+ "//proto:tink_cc_proto",
+ "//signature:ecdsa_verify_key_manager",
+ "//signature:rsa_ssa_pkcs1_verify_key_manager",
+ "//signature:rsa_ssa_pss_verify_key_manager",
+ "//util:test_matchers",
+ "//util:test_util",
+ "@com_google_googletest//:gtest_main",
+ ],
+)
diff --git a/cc/config/CMakeLists.txt b/cc/config/CMakeLists.txt
index 7fb341bdc..38a51df5f 100644
--- a/cc/config/CMakeLists.txt
+++ b/cc/config/CMakeLists.txt
@@ -87,3 +87,54 @@ tink_cc_test(
tink::util::status
tink::util::test_matchers
)
+
+tink_cc_library(
+ NAME fips_140_2
+ SRCS
+ fips_140_2.cc
+ fips_140_2.h
+ DEPS
+ absl::check
+ tink::core::configuration
+ tink::aead::aead_wrapper
+ tink::aead::aes_ctr_hmac_aead_key_manager
+ tink::aead::aes_gcm_key_manager
+ tink::internal::configuration_impl
+ tink::mac::hmac_key_manager
+ tink::mac::mac_wrapper
+ tink::mac::internal::chunked_mac_wrapper
+ tink::prf::hmac_prf_key_manager
+ tink::prf::prf_set_wrapper
+ tink::signature::ecdsa_sign_key_manager
+ tink::signature::ecdsa_verify_key_manager
+ tink::signature::public_key_sign_wrapper
+ tink::signature::public_key_verify_wrapper
+ tink::signature::rsa_ssa_pkcs1_sign_key_manager
+ tink::signature::rsa_ssa_pkcs1_verify_key_manager
+ tink::signature::rsa_ssa_pss_sign_key_manager
+ tink::signature::rsa_ssa_pss_verify_key_manager
+)
+
+tink_cc_test(
+ NAME fips_140_2_test
+ SRCS
+ fips_140_2_test.cc
+ DEPS
+ tink::config::fips_140_2
+ gmock
+ tink::aead::aead_key_templates
+ tink::aead::aes_ctr_hmac_aead_key_manager
+ tink::aead::aes_gcm_key_manager
+ tink::internal::configuration_impl
+ tink::internal::fips_utils
+ tink::internal::registry_impl
+ tink::mac::aes_cmac_key_manager
+ tink::mac::hmac_key_manager
+ tink::prf::hmac_prf_key_manager
+ tink::signature::ecdsa_verify_key_manager
+ tink::signature::rsa_ssa_pkcs1_verify_key_manager
+ tink::signature::rsa_ssa_pss_verify_key_manager
+ tink::util::test_matchers
+ tink::util::test_util
+ tink::proto::tink_cc_proto
+)
diff --git a/cc/config/fips_140_2.cc b/cc/config/fips_140_2.cc
new file mode 100644
index 000000000..792b6803a
--- /dev/null
+++ b/cc/config/fips_140_2.cc
@@ -0,0 +1,134 @@
+// Copyright 2023 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+///////////////////////////////////////////////////////////////////////////////
+
+#include "tink/config/fips_140_2.h"
+
+#include "absl/log/check.h"
+#include "tink/aead/aead_wrapper.h"
+#include "tink/aead/aes_ctr_hmac_aead_key_manager.h"
+#include "tink/aead/aes_gcm_key_manager.h"
+#include "tink/configuration.h"
+#include "tink/internal/configuration_impl.h"
+#include "tink/internal/fips_utils.h"
+#include "tink/mac/hmac_key_manager.h"
+#include "tink/mac/internal/chunked_mac_wrapper.h"
+#include "tink/mac/mac_wrapper.h"
+#include "tink/prf/hmac_prf_key_manager.h"
+#include "tink/prf/prf_set_wrapper.h"
+#include "tink/signature/ecdsa_verify_key_manager.h"
+#include "tink/signature/public_key_sign_wrapper.h"
+#include "tink/signature/public_key_verify_wrapper.h"
+#include "tink/signature/rsa_ssa_pkcs1_sign_key_manager.h"
+#include "tink/signature/rsa_ssa_pkcs1_verify_key_manager.h"
+#include "tink/signature/rsa_ssa_pss_sign_key_manager.h"
+#include "tink/signature/rsa_ssa_pss_verify_key_manager.h"
+#include "tink/signature/ecdsa_sign_key_manager.h"
+
+namespace crypto {
+namespace tink {
+namespace {
+
+util::Status RegisterMac(Configuration& config) {
+ util::Status status = internal::ConfigurationImpl::RegisterPrimitiveWrapper(
+ absl::make_unique<MacWrapper>(), config);
+ if (!status.ok()) {
+ return status;
+ }
+ status = internal::ConfigurationImpl::RegisterPrimitiveWrapper(
+ absl::make_unique<internal::ChunkedMacWrapper>(), config);
+ if (!status.ok()) {
+ return status;
+ }
+
+ return internal::ConfigurationImpl::RegisterKeyTypeManager(
+ absl::make_unique<HmacKeyManager>(), config);
+}
+
+util::Status RegisterAead(Configuration& config) {
+ util::Status status = internal::ConfigurationImpl::RegisterPrimitiveWrapper(
+ absl::make_unique<AeadWrapper>(), config);
+ if (!status.ok()) {
+ return status;
+ }
+
+ status = internal::ConfigurationImpl::RegisterKeyTypeManager(
+ absl::make_unique<AesCtrHmacAeadKeyManager>(), config);
+ if (!status.ok()) {
+ return status;
+ }
+ return internal::ConfigurationImpl::RegisterKeyTypeManager(
+ absl::make_unique<AesGcmKeyManager>(), config);
+}
+
+util::Status RegisterPrf(Configuration& config) {
+ util::Status status = internal::ConfigurationImpl::RegisterPrimitiveWrapper(
+ absl::make_unique<PrfSetWrapper>(), config);
+ if (!status.ok()) {
+ return status;
+ }
+
+ return internal::ConfigurationImpl::RegisterKeyTypeManager(
+ absl::make_unique<HmacPrfKeyManager>(), config);
+}
+
+util::Status RegisterSignature(Configuration& config) {
+ util::Status status = internal::ConfigurationImpl::RegisterPrimitiveWrapper(
+ absl::make_unique<PublicKeySignWrapper>(), config);
+ if (!status.ok()) {
+ return status;
+ }
+ status = internal::ConfigurationImpl::RegisterPrimitiveWrapper(
+ absl::make_unique<PublicKeyVerifyWrapper>(), config);
+ if (!status.ok()) {
+ return status;
+ }
+
+ status = internal::ConfigurationImpl::RegisterAsymmetricKeyManagers(
+ absl::make_unique<EcdsaSignKeyManager>(),
+ absl::make_unique<EcdsaVerifyKeyManager>(), config);
+ if (!status.ok()) {
+ return status;
+ }
+ status = internal::ConfigurationImpl::RegisterAsymmetricKeyManagers(
+ absl::make_unique<RsaSsaPssSignKeyManager>(),
+ absl::make_unique<RsaSsaPssVerifyKeyManager>(), config);
+ if (!status.ok()) {
+ return status;
+ }
+ return internal::ConfigurationImpl::RegisterAsymmetricKeyManagers(
+ absl::make_unique<RsaSsaPkcs1SignKeyManager>(),
+ absl::make_unique<RsaSsaPkcs1VerifyKeyManager>(), config);
+}
+
+} // namespace
+
+const Configuration& ConfigFips140_2() {
+ static const Configuration* instance = [] {
+ internal::SetFipsRestricted();
+
+ static Configuration* config = new Configuration();
+ CHECK_OK(RegisterMac(*config));
+ CHECK_OK(RegisterAead(*config));
+ CHECK_OK(RegisterPrf(*config));
+ CHECK_OK(RegisterSignature(*config));
+
+ return config;
+ }();
+ return *instance;
+}
+
+} // namespace tink
+} // namespace crypto
diff --git a/cc/config/fips_140_2.h b/cc/config/fips_140_2.h
new file mode 100644
index 000000000..ae4b93d48
--- /dev/null
+++ b/cc/config/fips_140_2.h
@@ -0,0 +1,33 @@
+// Copyright 2023 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+///////////////////////////////////////////////////////////////////////////////
+
+#ifndef TINK_CONFIG_FIPS_140_2_H_
+#define TINK_CONFIG_FIPS_140_2_H_
+
+#include "tink/configuration.h"
+
+namespace crypto {
+namespace tink {
+
+// Allows primitive generation using FIPS 140-2-compliant key types. Importing
+// this Configuration restricts Tink to FIPS globally and requires BoringSSL to
+// be built with the BoringCrypto module.
+const Configuration& ConfigFips140_2();
+
+} // namespace tink
+} // namespace crypto
+
+#endif // TINK_CONFIG_FIPS_140_2_H_
diff --git a/cc/config/fips_140_2_test.cc b/cc/config/fips_140_2_test.cc
new file mode 100644
index 000000000..d4c79282a
--- /dev/null
+++ b/cc/config/fips_140_2_test.cc
@@ -0,0 +1,138 @@
+// Copyright 2023 Google LLC
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+///////////////////////////////////////////////////////////////////////////////
+
+#include "tink/config/fips_140_2.h"
+
+#include <memory>
+#include <string>
+
+#include "gmock/gmock.h"
+#include "gtest/gtest.h"
+#include "tink/aead/aead_key_templates.h"
+#include "tink/aead/aes_ctr_hmac_aead_key_manager.h"
+#include "tink/aead/aes_gcm_key_manager.h"
+#include "tink/internal/configuration_impl.h"
+#include "tink/internal/fips_utils.h"
+#include "tink/internal/registry_impl.h"
+#include "tink/mac/aes_cmac_key_manager.h"
+#include "tink/mac/hmac_key_manager.h"
+#include "tink/prf/hmac_prf_key_manager.h"
+#include "tink/signature/ecdsa_verify_key_manager.h"
+#include "tink/signature/rsa_ssa_pkcs1_verify_key_manager.h"
+#include "tink/signature/rsa_ssa_pss_verify_key_manager.h"
+#include "tink/util/test_matchers.h"
+#include "tink/util/test_util.h"
+#include "proto/tink.pb.h"
+
+namespace crypto {
+namespace tink {
+namespace {
+
+using ::crypto::tink::test::IsOk;
+using ::crypto::tink::test::IsOkAndHolds;
+using ::google::crypto::tink::KeyData;
+using ::google::crypto::tink::Keyset;
+using ::google::crypto::tink::KeyStatusType;
+using ::google::crypto::tink::OutputPrefixType;
+using ::testing::Not;
+
+class Fips1402Test : public ::testing::Test {
+ protected:
+ void TearDown() override { internal::UnSetFipsRestricted(); }
+};
+
+TEST_F(Fips1402Test, ConfigFips1402) {
+ if (!FIPS_mode()) {
+ GTEST_SKIP() << "Only test in FIPS mode";
+ }
+
+ const internal::RegistryImpl& registry =
+ internal::ConfigurationImpl::get_registry(ConfigFips140_2());
+ EXPECT_THAT(registry.get_key_manager<Mac>(HmacKeyManager().get_key_type()),
+ IsOk());
+ EXPECT_THAT(
+ registry.get_key_manager<Aead>(AesCtrHmacAeadKeyManager().get_key_type()),
+ IsOk());
+ EXPECT_THAT(registry.get_key_manager<Aead>(AesGcmKeyManager().get_key_type()),
+ IsOk());
+ EXPECT_THAT(registry.get_key_manager<Prf>(HmacPrfKeyManager().get_key_type()),
+ IsOk());
+ EXPECT_THAT(registry.get_key_manager<PublicKeyVerify>(
+ EcdsaVerifyKeyManager().get_key_type()),
+ IsOk());
+ EXPECT_THAT(registry.get_key_manager<PublicKeyVerify>(
+ RsaSsaPssVerifyKeyManager().get_key_type()),
+ IsOk());
+ EXPECT_THAT(registry.get_key_manager<PublicKeyVerify>(
+ RsaSsaPkcs1VerifyKeyManager().get_key_type()),
+ IsOk());
+}
+
+TEST_F(Fips1402Test, NonFipsKeyManagerIsNotPresent) {
+ if (!FIPS_mode()) {
+ GTEST_SKIP() << "Only test in FIPS mode";
+ }
+
+ const internal::RegistryImpl& registry =
+ internal::ConfigurationImpl::get_registry(ConfigFips140_2());
+ EXPECT_THAT(registry.get_key_manager<Mac>(AesCmacKeyManager().get_key_type()),
+ Not(IsOk()));
+}
+
+TEST_F(Fips1402Test, ConfigFips1402FailsInNonFipsMode) {
+ if (FIPS_mode()) {
+ GTEST_SKIP() << "Only test in non-FIPS mode";
+ }
+
+ EXPECT_DEATH_IF_SUPPORTED(
+ ConfigFips140_2(), "BoringSSL not built with the BoringCrypto module.");
+}
+
+TEST_F(Fips1402Test, NewKeyDataAndWrapKeysetSucceeds) {
+ if (!FIPS_mode()) {
+ GTEST_SKIP() << "Only test in FIPS mode";
+ }
+
+ const internal::RegistryImpl& registry =
+ internal::ConfigurationImpl::get_registry(ConfigFips140_2());
+
+ util::StatusOr<std::unique_ptr<KeyData>> key_data =
+ registry.NewKeyData(AeadKeyTemplates::Aes128Gcm());
+ ASSERT_THAT(key_data, IsOk());
+
+ Keyset keyset;
+ uint32_t key_id = 0;
+ test::AddKeyData(**key_data, key_id, OutputPrefixType::TINK,
+ KeyStatusType::ENABLED, &keyset);
+ keyset.set_primary_key_id(key_id);
+
+ absl::flat_hash_map<std::string, std::string> annotations;
+ util::StatusOr<std::unique_ptr<Aead>> aead =
+ registry.WrapKeyset<Aead>(keyset, annotations);
+ ASSERT_THAT(aead, IsOk());
+
+ std::string plaintext = "plaintext";
+ std::string ad = "ad";
+ util::StatusOr<std::string> ciphertext = (*aead)->Encrypt(plaintext, ad);
+ ASSERT_THAT(ciphertext, IsOk());
+
+ util::StatusOr<std::string> decrypted = (*aead)->Decrypt(*ciphertext, ad);
+ EXPECT_THAT(decrypted, IsOkAndHolds(plaintext));
+}
+
+} // namespace
+} // namespace tink
+} // namespace crypto