"Fossies" - the Fresh Open Source Software Archive  

Source code changes of the file "nss/gtests/pk11_gtest/pk11_hpke_unittest.cc" between
nss-3.61.tar.gz and nss-3.62.tar.gz

About: NSS is a set of libraries, APIs, utilities, and documentation designed to support cross-platform development of security-enabled client and server applications. It provides a complete implementation of the crypto libraries used by Mozilla and other companies.

pk11_hpke_unittest.cc  (nss-3.61):pk11_hpke_unittest.cc  (nss-3.62)
skipping to change at line 25 skipping to change at line 25
#include "sechash.h" #include "sechash.h"
#include "testvectors/hpke-vectors.h" #include "testvectors/hpke-vectors.h"
#include "util.h" #include "util.h"
namespace nss_test { namespace nss_test {
/* See note in pk11pub.h. */ /* See note in pk11pub.h. */
#ifdef NSS_ENABLE_DRAFT_HPKE #ifdef NSS_ENABLE_DRAFT_HPKE
#include "cpputil.h" #include "cpputil.h"
class Pkcs11HpkeTest : public ::testing::TestWithParam<hpke_vector> { class HpkeTest {
protected: protected:
void ReadVector(const hpke_vector &vec) {
ScopedPK11SymKey vec_psk;
if (!vec.psk.empty()) {
ASSERT_FALSE(vec.psk_id.empty());
vec_psk_id = hex_string_to_bytes(vec.psk_id);
std::vector<uint8_t> psk_bytes = hex_string_to_bytes(vec.psk);
SECItem psk_item = {siBuffer, toUcharPtr(psk_bytes.data()),
static_cast<unsigned int>(psk_bytes.size())};
ScopedPK11SlotInfo slot(PK11_GetInternalSlot());
ASSERT_TRUE(slot);
PK11SymKey *psk_key =
PK11_ImportSymKey(slot.get(), CKM_HKDF_KEY_GEN, PK11_OriginUnwrap,
CKA_WRAP, &psk_item, nullptr);
ASSERT_NE(nullptr, psk_key);
vec_psk_key.reset(psk_key);
}
vec_pkcs8_r = hex_string_to_bytes(vec.pkcs8_r);
vec_pkcs8_e = hex_string_to_bytes(vec.pkcs8_e);
vec_key = hex_string_to_bytes(vec.key);
vec_nonce = hex_string_to_bytes(vec.nonce);
vec_enc = hex_string_to_bytes(vec.enc);
vec_info = hex_string_to_bytes(vec.info);
vec_encryptions = vec.encrypt_vecs;
vec_exports = vec.export_vecs;
}
void CheckEquality(const std::vector<uint8_t> &expected, SECItem *actual) { void CheckEquality(const std::vector<uint8_t> &expected, SECItem *actual) {
if (!actual) { if (!actual) {
EXPECT_TRUE(expected.empty()); EXPECT_TRUE(expected.empty());
return; return;
} }
std::vector<uint8_t> vact(actual->data, actual->data + actual->len); std::vector<uint8_t> vact(actual->data, actual->data + actual->len);
EXPECT_EQ(expected, vact); EXPECT_EQ(expected, vact);
} }
void CheckEquality(SECItem *expected, SECItem *actual) { void CheckEquality(SECItem *expected, SECItem *actual) {
skipping to change at line 105 skipping to change at line 77
if (rv != SECSuccess) { if (rv != SECSuccess) {
return; return;
} }
SECItem *raw = PK11_GetKeyData(expected); SECItem *raw = PK11_GetKeyData(expected);
ASSERT_NE(nullptr, raw); ASSERT_NE(nullptr, raw);
ASSERT_NE(nullptr, raw->data); ASSERT_NE(nullptr, raw->data);
std::vector<uint8_t> expected_vec(raw->data, raw->data + raw->len); std::vector<uint8_t> expected_vec(raw->data, raw->data + raw->len);
CheckEquality(expected_vec, actual); CheckEquality(expected_vec, actual);
} }
void SetupS(const ScopedHpkeContext &cx, const ScopedSECKEYPublicKey &pkE,
const ScopedSECKEYPrivateKey &skE,
const ScopedSECKEYPublicKey &pkR,
const std::vector<uint8_t> &info) {
SECItem info_item = {siBuffer, toUcharPtr(vec_info.data()),
static_cast<unsigned int>(vec_info.size())};
SECStatus rv =
PK11_HPKE_SetupS(cx.get(), pkE.get(), skE.get(), pkR.get(), &info_item);
EXPECT_EQ(SECSuccess, rv);
}
void SetupR(const ScopedHpkeContext &cx, const ScopedSECKEYPublicKey &pkR,
const ScopedSECKEYPrivateKey &skR,
const std::vector<uint8_t> &enc,
const std::vector<uint8_t> &info) {
SECItem enc_item = {siBuffer, toUcharPtr(enc.data()),
static_cast<unsigned int>(enc.size())};
SECItem info_item = {siBuffer, toUcharPtr(vec_info.data()),
static_cast<unsigned int>(vec_info.size())};
SECStatus rv =
PK11_HPKE_SetupR(cx.get(), pkR.get(), skR.get(), &enc_item, &info_item);
EXPECT_EQ(SECSuccess, rv);
}
void Seal(const ScopedHpkeContext &cx, std::vector<uint8_t> &aad_vec, void Seal(const ScopedHpkeContext &cx, std::vector<uint8_t> &aad_vec,
std::vector<uint8_t> &pt_vec, SECItem **out_ct) { std::vector<uint8_t> &pt_vec, std::vector<uint8_t> &out_sealed) {
SECItem aad_item = {siBuffer, toUcharPtr(aad_vec.data()), SECItem aad_item = {siBuffer, toUcharPtr(aad_vec.data()),
static_cast<unsigned int>(aad_vec.size())}; static_cast<unsigned int>(aad_vec.size())};
SECItem pt_item = {siBuffer, toUcharPtr(pt_vec.data()), SECItem pt_item = {siBuffer, toUcharPtr(pt_vec.data()),
static_cast<unsigned int>(pt_vec.size())}; static_cast<unsigned int>(pt_vec.size())};
SECStatus rv = PK11_HPKE_Seal(cx.get(), &aad_item, &pt_item, out_ct); SECItem *sealed_item = nullptr;
EXPECT_EQ(SECSuccess, rv); EXPECT_EQ(SECSuccess,
PK11_HPKE_Seal(cx.get(), &aad_item, &pt_item, &sealed_item));
ASSERT_NE(nullptr, sealed_item);
ScopedSECItem sealed(sealed_item);
out_sealed.assign(sealed->data, sealed->data + sealed->len);
} }
void Open(const ScopedHpkeContext &cx, std::vector<uint8_t> &aad_vec, void Open(const ScopedHpkeContext &cx, std::vector<uint8_t> &aad_vec,
std::vector<uint8_t> &ct_vec, SECItem **out_pt) { std::vector<uint8_t> &ct_vec, std::vector<uint8_t> &out_opened) {
SECItem aad_item = {siBuffer, toUcharPtr(aad_vec.data()), SECItem aad_item = {siBuffer, toUcharPtr(aad_vec.data()),
static_cast<unsigned int>(aad_vec.size())}; static_cast<unsigned int>(aad_vec.size())};
SECItem ct_item = {siBuffer, toUcharPtr(ct_vec.data()), SECItem ct_item = {siBuffer, toUcharPtr(ct_vec.data()),
static_cast<unsigned int>(ct_vec.size())}; static_cast<unsigned int>(ct_vec.size())};
SECStatus rv = PK11_HPKE_Open(cx.get(), &aad_item, &ct_item, out_pt); SECItem *opened_item = nullptr;
EXPECT_EQ(SECSuccess, rv); EXPECT_EQ(SECSuccess,
PK11_HPKE_Open(cx.get(), &aad_item, &ct_item, &opened_item));
ASSERT_NE(nullptr, opened_item);
ScopedSECItem opened(opened_item);
out_opened.assign(opened->data, opened->data + opened->len);
}
void SealOpen(const ScopedHpkeContext &sender,
const ScopedHpkeContext &receiver, std::vector<uint8_t> &msg,
std::vector<uint8_t> &aad, const std::vector<uint8_t> *expect) {
std::vector<uint8_t> sealed;
std::vector<uint8_t> opened;
Seal(sender, aad, msg, sealed);
if (expect) {
EXPECT_EQ(*expect, sealed);
}
Open(receiver, aad, sealed, opened);
EXPECT_EQ(msg, opened);
}
void ExportSecret(const ScopedHpkeContext &receiver,
ScopedPK11SymKey &exported) {
std::vector<uint8_t> context = {'c', 't', 'x', 't'};
SECItem context_item = {siBuffer, context.data(),
static_cast<unsigned int>(context.size())};
PK11SymKey *tmp_exported = nullptr;
ASSERT_EQ(SECSuccess, PK11_HPKE_ExportSecret(receiver.get(), &context_item,
64, &tmp_exported));
exported.reset(tmp_exported);
}
void ExportImportRecvContext(ScopedHpkeContext &scoped_cx,
PK11SymKey *wrapping_key) {
SECItem *tmp_exported = nullptr;
EXPECT_EQ(SECSuccess, PK11_HPKE_ExportContext(scoped_cx.get(), wrapping_key,
&tmp_exported));
EXPECT_NE(nullptr, tmp_exported);
ScopedSECItem context(tmp_exported);
scoped_cx.reset();
HpkeContext *tmp_imported =
PK11_HPKE_ImportContext(context.get(), wrapping_key);
EXPECT_NE(nullptr, tmp_imported);
scoped_cx.reset(tmp_imported);
}
bool GenerateKeyPair(ScopedSECKEYPublicKey &pub_key,
ScopedSECKEYPrivateKey &priv_key) {
ScopedPK11SlotInfo slot(PK11_GetInternalSlot());
if (!slot) {
ADD_FAILURE() << "Couldn't get slot";
return false;
}
unsigned char param_buf[65];
SECItem ecdsa_params = {siBuffer, param_buf, sizeof(param_buf)};
SECOidData *oid_data = SECOID_FindOIDByTag(SEC_OID_CURVE25519);
if (!oid_data) {
ADD_FAILURE() << "Couldn't get oid_data";
return false;
}
ecdsa_params.data[0] = SEC_ASN1_OBJECT_ID;
ecdsa_params.data[1] = oid_data->oid.len;
memcpy(ecdsa_params.data + 2, oid_data->oid.data, oid_data->oid.len);
ecdsa_params.len = oid_data->oid.len + 2;
SECKEYPublicKey *pub_tmp;
SECKEYPrivateKey *priv_tmp;
priv_tmp =
PK11_GenerateKeyPair(slot.get(), CKM_EC_KEY_PAIR_GEN, &ecdsa_params,
&pub_tmp, PR_FALSE, PR_TRUE, nullptr);
if (!pub_tmp || !priv_tmp) {
ADD_FAILURE() << "PK11_GenerateKeyPair failed";
return false;
}
pub_key.reset(pub_tmp);
priv_key.reset(priv_tmp);
return true;
}
void SetUpEphemeralContexts(ScopedHpkeContext &sender,
ScopedHpkeContext &receiver,
HpkeModeId mode = HpkeModeBase,
HpkeKemId kem = HpkeDhKemX25519Sha256,
HpkeKdfId kdf = HpkeKdfHkdfSha256,
HpkeAeadId aead = HpkeAeadAes128Gcm) {
// Generate a PSK, if the mode calls for it.
PRUint8 psk_id_buf[] = {'p', 's', 'k', '-', 'i', 'd'};
SECItem psk_id = {siBuffer, psk_id_buf, sizeof(psk_id_buf)};
SECItem *psk_id_item = (mode == HpkeModePsk) ? &psk_id : nullptr;
ScopedPK11SymKey psk;
if (mode == HpkeModePsk) {
ScopedPK11SlotInfo slot(PK11_GetInternalSlot());
ASSERT_TRUE(slot);
PK11SymKey *tmp_psk =
PK11_KeyGen(slot.get(), CKM_HKDF_DERIVE, nullptr, 16, nullptr);
ASSERT_NE(nullptr, tmp_psk);
psk.reset(tmp_psk);
}
std::vector<uint8_t> info = {'t', 'e', 's', 't', '-', 'i', 'n', 'f', 'o'};
SECItem info_item = {siBuffer, info.data(),
static_cast<unsigned int>(info.size())};
sender.reset(PK11_HPKE_NewContext(kem, kdf, aead, psk.get(), psk_id_item));
receiver.reset(
PK11_HPKE_NewContext(kem, kdf, aead, psk.get(), psk_id_item));
ASSERT_TRUE(sender);
ASSERT_TRUE(receiver);
ScopedSECKEYPublicKey pub_key_r;
ScopedSECKEYPrivateKey priv_key_r;
ASSERT_TRUE(GenerateKeyPair(pub_key_r, priv_key_r));
EXPECT_EQ(SECSuccess, PK11_HPKE_SetupS(sender.get(), nullptr, nullptr,
pub_key_r.get(), &info_item));
const SECItem *enc = PK11_HPKE_GetEncapPubKey(sender.get());
EXPECT_NE(nullptr, enc);
EXPECT_EQ(SECSuccess, PK11_HPKE_SetupR(
receiver.get(), pub_key_r.get(), priv_key_r.get(),
const_cast<SECItem *>(enc), &info_item));
}
};
class TestVectors : public HpkeTest,
public ::testing::TestWithParam<hpke_vector> {
protected:
void ReadVector(const hpke_vector &vec) {
ScopedPK11SymKey vec_psk;
if (!vec.psk.empty()) {
ASSERT_FALSE(vec.psk_id.empty());
vec_psk_id = hex_string_to_bytes(vec.psk_id);
std::vector<uint8_t> psk_bytes = hex_string_to_bytes(vec.psk);
SECItem psk_item = {siBuffer, toUcharPtr(psk_bytes.data()),
static_cast<unsigned int>(psk_bytes.size())};
ScopedPK11SlotInfo slot(PK11_GetInternalSlot());
ASSERT_TRUE(slot);
PK11SymKey *psk_key =
PK11_ImportSymKey(slot.get(), CKM_HKDF_KEY_GEN, PK11_OriginUnwrap,
CKA_WRAP, &psk_item, nullptr);
ASSERT_NE(nullptr, psk_key);
vec_psk_key.reset(psk_key);
}
vec_pkcs8_r = hex_string_to_bytes(vec.pkcs8_r);
vec_pkcs8_e = hex_string_to_bytes(vec.pkcs8_e);
vec_key = hex_string_to_bytes(vec.key);
vec_nonce = hex_string_to_bytes(vec.nonce);
vec_enc = hex_string_to_bytes(vec.enc);
vec_info = hex_string_to_bytes(vec.info);
vec_encryptions = vec.encrypt_vecs;
vec_exports = vec.export_vecs;
} }
void TestExports(const ScopedHpkeContext &sender, void TestExports(const ScopedHpkeContext &sender,
const ScopedHpkeContext &receiver) { const ScopedHpkeContext &receiver) {
SECStatus rv;
for (auto &vec : vec_exports) { for (auto &vec : vec_exports) {
std::vector<uint8_t> context = hex_string_to_bytes(vec.ctxt); std::vector<uint8_t> context = hex_string_to_bytes(vec.ctxt);
std::vector<uint8_t> expected = hex_string_to_bytes(vec.exported); std::vector<uint8_t> expected = hex_string_to_bytes(vec.exported);
SECItem context_item = {siBuffer, toUcharPtr(context.data()), SECItem context_item = {siBuffer, toUcharPtr(context.data()),
static_cast<unsigned int>(context.size())}; static_cast<unsigned int>(context.size())};
PK11SymKey *actual_r = nullptr; PK11SymKey *actual_r = nullptr;
PK11SymKey *actual_s = nullptr; PK11SymKey *actual_s = nullptr;
rv = PK11_HPKE_ExportSecret(sender.get(), &context_item, vec.len, ASSERT_EQ(SECSuccess, PK11_HPKE_ExportSecret(sender.get(), &context_item,
&actual_s); vec.len, &actual_s));
ASSERT_EQ(SECSuccess, rv); ASSERT_EQ(SECSuccess,
rv = PK11_HPKE_ExportSecret(receiver.get(), &context_item, vec.len, PK11_HPKE_ExportSecret(receiver.get(), &context_item, vec.len,
&actual_r); &actual_r));
ASSERT_EQ(SECSuccess, rv);
ScopedPK11SymKey scoped_act_s(actual_s); ScopedPK11SymKey scoped_act_s(actual_s);
ScopedPK11SymKey scoped_act_r(actual_r); ScopedPK11SymKey scoped_act_r(actual_r);
CheckEquality(expected, scoped_act_s.get()); CheckEquality(expected, scoped_act_s.get());
CheckEquality(expected, scoped_act_r.get()); CheckEquality(expected, scoped_act_r.get());
} }
} }
void TestEncryptions(const ScopedHpkeContext &sender, void TestEncryptions(const ScopedHpkeContext &sender,
const ScopedHpkeContext &receiver) { const ScopedHpkeContext &receiver) {
for (auto &enc_vec : vec_encryptions) { for (auto &enc_vec : vec_encryptions) {
std::vector<uint8_t> msg = hex_string_to_bytes(enc_vec.pt); std::vector<uint8_t> msg = hex_string_to_bytes(enc_vec.pt);
std::vector<uint8_t> aad = hex_string_to_bytes(enc_vec.aad); std::vector<uint8_t> aad = hex_string_to_bytes(enc_vec.aad);
std::vector<uint8_t> expect_ct = hex_string_to_bytes(enc_vec.ct); std::vector<uint8_t> expect_ct = hex_string_to_bytes(enc_vec.ct);
SECItem *act_ct = nullptr; SealOpen(sender, receiver, msg, aad, &expect_ct);
Seal(sender, aad, msg, &act_ct);
CheckEquality(expect_ct, act_ct);
ScopedSECItem scoped_ct(act_ct);
SECItem *act_pt = nullptr;
Open(receiver, aad, expect_ct, &act_pt);
CheckEquality(msg, act_pt);
ScopedSECItem scoped_pt(act_pt);
} }
} }
void ImportKeyPairs(const ScopedHpkeContext &sender, void ImportKeyPairs(const ScopedHpkeContext &sender,
const ScopedHpkeContext &receiver) { const ScopedHpkeContext &receiver) {
ScopedPK11SlotInfo slot(PK11_GetInternalSlot()); ScopedPK11SlotInfo slot(PK11_GetInternalSlot());
if (!slot) { if (!slot) {
ADD_FAILURE() << "No slot"; ADD_FAILURE() << "No slot";
return; return;
} }
SECItem pkcs8_e_item = {siBuffer, toUcharPtr(vec_pkcs8_e.data()), SECItem pkcs8_e_item = {siBuffer, toUcharPtr(vec_pkcs8_e.data()),
static_cast<unsigned int>(vec_pkcs8_e.size())}; static_cast<unsigned int>(vec_pkcs8_e.size())};
SECKEYPrivateKey *sk_e = nullptr; SECKEYPrivateKey *sk_e = nullptr;
SECStatus rv = PK11_ImportDERPrivateKeyInfoAndReturnKey( EXPECT_EQ(SECSuccess, PK11_ImportDERPrivateKeyInfoAndReturnKey(
slot.get(), &pkcs8_e_item, nullptr, nullptr, false, false, KU_ALL, slot.get(), &pkcs8_e_item, nullptr, nullptr,
&sk_e, nullptr); false, false, KU_ALL, &sk_e, nullptr));
EXPECT_EQ(SECSuccess, rv);
skE_derived.reset(sk_e); skE_derived.reset(sk_e);
SECKEYPublicKey *pk_e = SECKEY_ConvertToPublicKey(skE_derived.get()); SECKEYPublicKey *pk_e = SECKEY_ConvertToPublicKey(skE_derived.get());
ASSERT_NE(nullptr, pk_e); ASSERT_NE(nullptr, pk_e);
pkE_derived.reset(pk_e); pkE_derived.reset(pk_e);
SECItem pkcs8_r_item = {siBuffer, toUcharPtr(vec_pkcs8_r.data()), SECItem pkcs8_r_item = {siBuffer, toUcharPtr(vec_pkcs8_r.data()),
static_cast<unsigned int>(vec_pkcs8_r.size())}; static_cast<unsigned int>(vec_pkcs8_r.size())};
SECKEYPrivateKey *sk_r = nullptr; SECKEYPrivateKey *sk_r = nullptr;
rv = PK11_ImportDERPrivateKeyInfoAndReturnKey( EXPECT_EQ(SECSuccess, PK11_ImportDERPrivateKeyInfoAndReturnKey(
slot.get(), &pkcs8_r_item, nullptr, nullptr, false, false, KU_ALL, slot.get(), &pkcs8_r_item, nullptr, nullptr,
&sk_r, nullptr); false, false, KU_ALL, &sk_r, nullptr));
EXPECT_EQ(SECSuccess, rv);
skR_derived.reset(sk_r); skR_derived.reset(sk_r);
SECKEYPublicKey *pk_r = SECKEY_ConvertToPublicKey(skR_derived.get()); SECKEYPublicKey *pk_r = SECKEY_ConvertToPublicKey(skR_derived.get());
ASSERT_NE(nullptr, pk_r); ASSERT_NE(nullptr, pk_r);
pkR_derived.reset(pk_r); pkR_derived.reset(pk_r);
} }
void SetupS(const ScopedHpkeContext &cx, const ScopedSECKEYPublicKey &pkE,
const ScopedSECKEYPrivateKey &skE,
const ScopedSECKEYPublicKey &pkR,
const std::vector<uint8_t> &info) {
SECItem info_item = {siBuffer, toUcharPtr(vec_info.data()),
static_cast<unsigned int>(vec_info.size())};
EXPECT_EQ(SECSuccess, PK11_HPKE_SetupS(cx.get(), pkE.get(), skE.get(),
pkR.get(), &info_item));
}
void SetupR(const ScopedHpkeContext &cx, const ScopedSECKEYPublicKey &pkR,
const ScopedSECKEYPrivateKey &skR,
const std::vector<uint8_t> &enc,
const std::vector<uint8_t> &info) {
SECItem enc_item = {siBuffer, toUcharPtr(enc.data()),
static_cast<unsigned int>(enc.size())};
SECItem info_item = {siBuffer, toUcharPtr(vec_info.data()),
static_cast<unsigned int>(vec_info.size())};
EXPECT_EQ(SECSuccess, PK11_HPKE_SetupR(cx.get(), pkR.get(), skR.get(),
&enc_item, &info_item));
}
void SetupSenderReceiver(const ScopedHpkeContext &sender, void SetupSenderReceiver(const ScopedHpkeContext &sender,
const ScopedHpkeContext &receiver) { const ScopedHpkeContext &receiver) {
SetupS(sender, pkE_derived, skE_derived, pkR_derived, vec_info); SetupS(sender, pkE_derived, skE_derived, pkR_derived, vec_info);
uint8_t buf[32]; // Curve25519 only, fixed size. uint8_t buf[32]; // Curve25519 only, fixed size.
SECItem encap_item = {siBuffer, const_cast<uint8_t *>(buf), sizeof(buf)}; SECItem encap_item = {siBuffer, const_cast<uint8_t *>(buf), sizeof(buf)};
SECStatus rv = PK11_HPKE_Serialize(pkE_derived.get(), encap_item.data, ASSERT_EQ(SECSuccess,
&encap_item.len, encap_item.len); PK11_HPKE_Serialize(pkE_derived.get(), encap_item.data,
ASSERT_EQ(SECSuccess, rv); &encap_item.len, encap_item.len));
CheckEquality(vec_enc, &encap_item); CheckEquality(vec_enc, &encap_item);
SetupR(receiver, pkR_derived, skR_derived, vec_enc, vec_info); SetupR(receiver, pkR_derived, skR_derived, vec_enc, vec_info);
} }
bool GenerateKeyPair(ScopedSECKEYPublicKey &pub_key,
ScopedSECKEYPrivateKey &priv_key) {
unsigned char param_buf[65];
ScopedPK11SlotInfo slot(PK11_GetInternalSlot());
if (!slot) {
ADD_FAILURE() << "Couldn't get slot";
return false;
}
SECItem ecdsa_params = {siBuffer, param_buf, sizeof(param_buf)};
SECOidData *oid_data = SECOID_FindOIDByTag(SEC_OID_CURVE25519);
if (!oid_data) {
ADD_FAILURE() << "Couldn't get oid_data";
return false;
}
ecdsa_params.data[0] = SEC_ASN1_OBJECT_ID;
ecdsa_params.data[1] = oid_data->oid.len;
memcpy(ecdsa_params.data + 2, oid_data->oid.data, oid_data->oid.len);
ecdsa_params.len = oid_data->oid.len + 2;
SECKEYPublicKey *pub_tmp;
SECKEYPrivateKey *priv_tmp;
priv_tmp =
PK11_GenerateKeyPair(slot.get(), CKM_EC_KEY_PAIR_GEN, &ecdsa_params,
&pub_tmp, PR_FALSE, PR_TRUE, nullptr);
if (!pub_tmp || !priv_tmp) {
ADD_FAILURE() << "PK11_GenerateKeyPair failed";
return false;
}
pub_key.reset(pub_tmp);
priv_key.reset(priv_tmp);
return true;
}
void RunTestVector(const hpke_vector &vec) { void RunTestVector(const hpke_vector &vec) {
ReadVector(vec); ReadVector(vec);
SECItem psk_id_item = {siBuffer, toUcharPtr(vec_psk_id.data()), SECItem psk_id_item = {siBuffer, toUcharPtr(vec_psk_id.data()),
static_cast<unsigned int>(vec_psk_id.size())}; static_cast<unsigned int>(vec_psk_id.size())};
PK11SymKey *psk = vec_psk_key ? vec_psk_key.get() : nullptr; PK11SymKey *psk = vec_psk_key ? vec_psk_key.get() : nullptr;
SECItem *psk_id = psk ? &psk_id_item : nullptr; SECItem *psk_id = psk ? &psk_id_item : nullptr;
ScopedHpkeContext sender( ScopedHpkeContext sender(
PK11_HPKE_NewContext(vec.kem_id, vec.kdf_id, vec.aead_id, psk, psk_id)); PK11_HPKE_NewContext(vec.kem_id, vec.kdf_id, vec.aead_id, psk, psk_id));
ScopedHpkeContext receiver( ScopedHpkeContext receiver(
skipping to change at line 310 skipping to change at line 387
std::vector<uint8_t> vec_key; std::vector<uint8_t> vec_key;
std::vector<uint8_t> vec_nonce; std::vector<uint8_t> vec_nonce;
std::vector<hpke_encrypt_vector> vec_encryptions; std::vector<hpke_encrypt_vector> vec_encryptions;
std::vector<hpke_export_vector> vec_exports; std::vector<hpke_export_vector> vec_exports;
ScopedSECKEYPublicKey pkE_derived; ScopedSECKEYPublicKey pkE_derived;
ScopedSECKEYPublicKey pkR_derived; ScopedSECKEYPublicKey pkR_derived;
ScopedSECKEYPrivateKey skE_derived; ScopedSECKEYPrivateKey skE_derived;
ScopedSECKEYPrivateKey skR_derived; ScopedSECKEYPrivateKey skR_derived;
}; };
TEST_P(Pkcs11HpkeTest, TestVectors) { RunTestVector(GetParam()); } TEST_P(TestVectors, TestVectors) { RunTestVector(GetParam()); }
INSTANTIATE_TEST_SUITE_P(Pkcs11HpkeTests, Pkcs11HpkeTest, INSTANTIATE_TEST_SUITE_P(Pk11Hpke, TestVectors,
::testing::ValuesIn(kHpkeTestVectors)); ::testing::ValuesIn(kHpkeTestVectors));
TEST_F(Pkcs11HpkeTest, BadEncapsulatedPubKey) { class ModeParameterizedTest
: public HpkeTest,
public ::testing::TestWithParam<
std::tuple<HpkeModeId, HpkeKemId, HpkeKdfId, HpkeAeadId>> {};
static const HpkeModeId kHpkeModesAll[] = {HpkeModeBase, HpkeModePsk};
static const HpkeKemId kHpkeKemIdsAll[] = {HpkeDhKemX25519Sha256};
static const HpkeKdfId kHpkeKdfIdsAll[] = {HpkeKdfHkdfSha256, HpkeKdfHkdfSha384,
HpkeKdfHkdfSha512};
static const HpkeAeadId kHpkeAeadIdsAll[] = {HpkeAeadAes128Gcm,
HpkeAeadChaCha20Poly1305};
INSTANTIATE_TEST_SUITE_P(
Pk11Hpke, ModeParameterizedTest,
::testing::Combine(::testing::ValuesIn(kHpkeModesAll),
::testing::ValuesIn(kHpkeKemIdsAll),
::testing::ValuesIn(kHpkeKdfIdsAll),
::testing::ValuesIn(kHpkeAeadIdsAll)));
TEST_F(ModeParameterizedTest, BadEncapsulatedPubKey) {
ScopedHpkeContext sender( ScopedHpkeContext sender(
PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256, PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256,
HpkeAeadAes128Gcm, nullptr, nullptr)); HpkeAeadAes128Gcm, nullptr, nullptr));
ScopedHpkeContext receiver( ScopedHpkeContext receiver(
PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256, PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256,
HpkeAeadAes128Gcm, nullptr, nullptr)); HpkeAeadAes128Gcm, nullptr, nullptr));
SECItem empty = {siBuffer, nullptr, 0}; SECItem empty = {siBuffer, nullptr, 0};
uint8_t buf[100]; uint8_t buf[100];
SECItem short_encap = {siBuffer, buf, 1}; SECItem short_encap = {siBuffer, buf, 1};
SECItem long_encap = {siBuffer, buf, sizeof(buf)}; SECItem long_encap = {siBuffer, buf, sizeof(buf)};
SECKEYPublicKey *tmp_pub_key; SECKEYPublicKey *tmp_pub_key;
ScopedSECKEYPublicKey pub_key; ScopedSECKEYPublicKey pub_key;
ScopedSECKEYPrivateKey priv_key; ScopedSECKEYPrivateKey priv_key;
ASSERT_TRUE(GenerateKeyPair(pub_key, priv_key)); ASSERT_TRUE(GenerateKeyPair(pub_key, priv_key));
// Decapsulating an empty buffer should fail. // Decapsulating an empty buffer should fail.
SECStatus rv = EXPECT_EQ(SECFailure, PK11_HPKE_Deserialize(sender.get(), empty.data,
PK11_HPKE_Deserialize(sender.get(), empty.data, empty.len, &tmp_pub_key); empty.len, &tmp_pub_key));
EXPECT_EQ(SECFailure, rv);
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());
// Decapsulating anything else will succeed, but the setup will fail. // Decapsulating anything short will succeed, but the setup will fail.
rv = PK11_HPKE_Deserialize(sender.get(), short_encap.data, short_encap.len, EXPECT_EQ(SECSuccess, PK11_HPKE_Deserialize(sender.get(), short_encap.data,
&tmp_pub_key); short_encap.len, &tmp_pub_key));
ScopedSECKEYPublicKey bad_pub_key(tmp_pub_key); ScopedSECKEYPublicKey bad_pub_key(tmp_pub_key);
EXPECT_EQ(SECSuccess, rv);
rv = PK11_HPKE_SetupS(receiver.get(), pub_key.get(), priv_key.get(), EXPECT_EQ(SECFailure,
bad_pub_key.get(), &empty); PK11_HPKE_SetupS(receiver.get(), pub_key.get(), priv_key.get(),
EXPECT_EQ(SECFailure, rv); bad_pub_key.get(), &empty));
EXPECT_EQ(SEC_ERROR_INVALID_KEY, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_KEY, PORT_GetError());
// Test the same for a receiver. // Test the same for a receiver.
rv = PK11_HPKE_SetupR(sender.get(), pub_key.get(), priv_key.get(), &empty, EXPECT_EQ(SECFailure, PK11_HPKE_SetupR(sender.get(), pub_key.get(),
&empty); priv_key.get(), &empty, &empty));
EXPECT_EQ(SECFailure, rv);
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());
EXPECT_EQ(SECFailure, PK11_HPKE_SetupR(sender.get(), pub_key.get(),
rv = PK11_HPKE_SetupR(sender.get(), pub_key.get(), priv_key.get(), priv_key.get(), &short_encap, &empty));
&short_encap, &empty);
EXPECT_EQ(SECFailure, rv);
EXPECT_EQ(SEC_ERROR_INVALID_KEY, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_KEY, PORT_GetError());
// Encapsulated key too long // Encapsulated key too long
rv = PK11_HPKE_Deserialize(sender.get(), long_encap.data, long_encap.len, EXPECT_EQ(SECSuccess, PK11_HPKE_Deserialize(sender.get(), long_encap.data,
&tmp_pub_key); long_encap.len, &tmp_pub_key));
bad_pub_key.reset(tmp_pub_key); bad_pub_key.reset(tmp_pub_key);
EXPECT_EQ(SECSuccess, rv); EXPECT_EQ(SECFailure,
PK11_HPKE_SetupS(receiver.get(), pub_key.get(), priv_key.get(),
rv = PK11_HPKE_SetupS(receiver.get(), pub_key.get(), priv_key.get(), bad_pub_key.get(), &empty));
bad_pub_key.get(), &empty);
EXPECT_EQ(SECFailure, rv);
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());
rv = PK11_HPKE_SetupR(sender.get(), pub_key.get(), priv_key.get(), EXPECT_EQ(SECFailure, PK11_HPKE_SetupR(sender.get(), pub_key.get(),
&long_encap, &empty); priv_key.get(), &long_encap, &empty));
EXPECT_EQ(SECFailure, rv);
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());
} }
// Vectors used fixed keypairs on each end. Make sure the TEST_P(ModeParameterizedTest, ContextExportImportEncrypt) {
// ephemeral (particularly sender) path works. std::vector<uint8_t> msg = {'s', 'e', 'c', 'r', 'e', 't'};
TEST_F(Pkcs11HpkeTest, EphemeralKeys) { std::vector<uint8_t> aad = {'a', 'a', 'd'};
unsigned char info[] = {"info"};
unsigned char msg[] = {"secret"}; ScopedHpkeContext sender;
unsigned char aad[] = {"aad"}; ScopedHpkeContext receiver;
SECItem info_item = {siBuffer, info, sizeof(info)}; SetUpEphemeralContexts(sender, receiver, std::get<0>(GetParam()),
SECItem msg_item = {siBuffer, msg, sizeof(msg)}; std::get<1>(GetParam()), std::get<2>(GetParam()),
SECItem aad_item = {siBuffer, aad, sizeof(aad)}; std::get<3>(GetParam()));
SealOpen(sender, receiver, msg, aad, nullptr);
ExportImportRecvContext(receiver, nullptr);
SealOpen(sender, receiver, msg, aad, nullptr);
}
ScopedHpkeContext sender( TEST_P(ModeParameterizedTest, ContextExportImportExport) {
PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256, ScopedHpkeContext sender;
HpkeAeadAes128Gcm, nullptr, nullptr)); ScopedHpkeContext receiver;
ScopedHpkeContext receiver( ScopedPK11SymKey sender_export;
PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256, ScopedPK11SymKey receiver_export;
HpkeAeadAes128Gcm, nullptr, nullptr)); ScopedPK11SymKey receiver_reexport;
ASSERT_TRUE(sender); SetUpEphemeralContexts(sender, receiver, std::get<0>(GetParam()),
ASSERT_TRUE(receiver); std::get<1>(GetParam()), std::get<2>(GetParam()),
std::get<3>(GetParam()));
ExportSecret(sender, sender_export);
ExportSecret(receiver, receiver_export);
CheckEquality(sender_export.get(), receiver_export.get());
ExportImportRecvContext(receiver, nullptr);
ExportSecret(receiver, receiver_reexport);
CheckEquality(receiver_export.get(), receiver_reexport.get());
}
ScopedSECKEYPublicKey pub_key_r; TEST_P(ModeParameterizedTest, ContextExportImportWithWrap) {
ScopedSECKEYPrivateKey priv_key_r; std::vector<uint8_t> msg = {'s', 'e', 'c', 'r', 'e', 't'};
ASSERT_TRUE(GenerateKeyPair(pub_key_r, priv_key_r)); std::vector<uint8_t> aad = {'a', 'a', 'd'};
SECStatus rv = PK11_HPKE_SetupS(sender.get(), nullptr, nullptr,
pub_key_r.get(), &info_item);
EXPECT_EQ(SECSuccess, rv);
const SECItem *enc = PK11_HPKE_GetEncapPubKey(sender.get());
EXPECT_NE(nullptr, enc);
rv = PK11_HPKE_SetupR(receiver.get(), pub_key_r.get(), priv_key_r.get(),
const_cast<SECItem *>(enc), &info_item);
EXPECT_EQ(SECSuccess, rv);
SECItem *tmp_sealed = nullptr; // Generate a wrapping key, then use it for export.
rv = PK11_HPKE_Seal(sender.get(), &aad_item, &msg_item, &tmp_sealed); ScopedPK11SlotInfo slot(PK11_GetInternalSlot());
EXPECT_EQ(SECSuccess, rv); ASSERT_TRUE(slot);
ScopedSECItem sealed(tmp_sealed); ScopedPK11SymKey kek(
PK11_KeyGen(slot.get(), CKM_AES_CBC, nullptr, 16, nullptr));
ASSERT_NE(nullptr, kek);
ScopedHpkeContext sender;
ScopedHpkeContext receiver;
SetUpEphemeralContexts(sender, receiver, std::get<0>(GetParam()),
std::get<1>(GetParam()), std::get<2>(GetParam()),
std::get<3>(GetParam()));
SealOpen(sender, receiver, msg, aad, nullptr);
ExportImportRecvContext(receiver, kek.get());
SealOpen(sender, receiver, msg, aad, nullptr);
}
SECItem *tmp_unsealed = nullptr; TEST_P(ModeParameterizedTest, ExportSenderContext) {
rv = PK11_HPKE_Open(receiver.get(), &aad_item, sealed.get(), &tmp_unsealed); std::vector<uint8_t> msg = {'s', 'e', 'c', 'r', 'e', 't'};
EXPECT_EQ(SECSuccess, rv); std::vector<uint8_t> aad = {'a', 'a', 'd'};
CheckEquality(&msg_item, tmp_unsealed);
ScopedSECItem unsealed(tmp_unsealed); ScopedHpkeContext sender;
ScopedHpkeContext receiver;
SetUpEphemeralContexts(sender, receiver, std::get<0>(GetParam()),
std::get<1>(GetParam()), std::get<2>(GetParam()),
std::get<3>(GetParam()));
SECItem *tmp_exported = nullptr;
EXPECT_EQ(SECFailure,
PK11_HPKE_ExportContext(sender.get(), nullptr, &tmp_exported));
EXPECT_EQ(nullptr, tmp_exported);
EXPECT_EQ(SEC_ERROR_NOT_A_RECIPIENT, PORT_GetError());
}
TEST_P(ModeParameterizedTest, ContextUnwrapBadKey) {
std::vector<uint8_t> msg = {'s', 'e', 'c', 'r', 'e', 't'};
std::vector<uint8_t> aad = {'a', 'a', 'd'};
// Once more // Generate a wrapping key, then use it for export.
tmp_sealed = nullptr; ScopedPK11SlotInfo slot(PK11_GetInternalSlot());
rv = PK11_HPKE_Seal(sender.get(), &aad_item, &msg_item, &tmp_sealed); ASSERT_TRUE(slot);
EXPECT_EQ(SECSuccess, rv); ScopedPK11SymKey kek(
ASSERT_NE(nullptr, sealed); PK11_KeyGen(slot.get(), CKM_AES_CBC, nullptr, 16, nullptr));
sealed.reset(tmp_sealed); ASSERT_NE(nullptr, kek);
tmp_unsealed = nullptr; ScopedPK11SymKey not_kek(
rv = PK11_HPKE_Open(receiver.get(), &aad_item, sealed.get(), &tmp_unsealed); PK11_KeyGen(slot.get(), CKM_AES_CBC, nullptr, 16, nullptr));
EXPECT_EQ(SECSuccess, rv); ASSERT_NE(nullptr, not_kek);
CheckEquality(&msg_item, tmp_unsealed); ScopedHpkeContext sender;
unsealed.reset(tmp_unsealed); ScopedHpkeContext receiver;
SetUpEphemeralContexts(sender, receiver, std::get<0>(GetParam()),
std::get<1>(GetParam()), std::get<2>(GetParam()),
std::get<3>(GetParam()));
SECItem *tmp_exported = nullptr;
EXPECT_EQ(SECSuccess,
PK11_HPKE_ExportContext(receiver.get(), kek.get(), &tmp_exported));
EXPECT_NE(nullptr, tmp_exported);
ScopedSECItem context(tmp_exported);
EXPECT_EQ(nullptr, PK11_HPKE_ImportContext(context.get(), not_kek.get()));
EXPECT_EQ(SEC_ERROR_BAD_DATA, PORT_GetError());
}
TEST_P(ModeParameterizedTest, EphemeralKeys) {
std::vector<uint8_t> msg = {'s', 'e', 'c', 'r', 'e', 't'};
std::vector<uint8_t> aad = {'a', 'a', 'd'};
SECItem msg_item = {siBuffer, msg.data(),
static_cast<unsigned int>(msg.size())};
SECItem aad_item = {siBuffer, aad.data(),
static_cast<unsigned int>(aad.size())};
ScopedHpkeContext sender;
ScopedHpkeContext receiver;
SetUpEphemeralContexts(sender, receiver, std::get<0>(GetParam()),
std::get<1>(GetParam()), std::get<2>(GetParam()),
std::get<3>(GetParam()));
SealOpen(sender, receiver, msg, aad, nullptr);
// Seal for negative tests // Seal for negative tests
tmp_sealed = nullptr; SECItem *tmp_sealed = nullptr;
tmp_unsealed = nullptr; SECItem *tmp_unsealed = nullptr;
rv = PK11_HPKE_Seal(sender.get(), &aad_item, &msg_item, &tmp_sealed); EXPECT_EQ(SECSuccess,
EXPECT_EQ(SECSuccess, rv); PK11_HPKE_Seal(sender.get(), &aad_item, &msg_item, &tmp_sealed));
ASSERT_NE(nullptr, sealed); ASSERT_NE(nullptr, tmp_sealed);
sealed.reset(tmp_sealed); ScopedSECItem sealed(tmp_sealed);
// Drop AAD // Drop AAD
rv = PK11_HPKE_Open(receiver.get(), nullptr, sealed.get(), &tmp_unsealed); EXPECT_EQ(SECFailure, PK11_HPKE_Open(receiver.get(), nullptr, sealed.get(),
EXPECT_EQ(SECFailure, rv); &tmp_unsealed));
EXPECT_EQ(SEC_ERROR_BAD_DATA, PORT_GetError());
EXPECT_EQ(nullptr, tmp_unsealed); EXPECT_EQ(nullptr, tmp_unsealed);
// Modify AAD // Modify AAD
aad_item.data[0] ^= 0xff; aad_item.data[0] ^= 0xff;
rv = PK11_HPKE_Open(receiver.get(), &aad_item, sealed.get(), &tmp_unsealed); EXPECT_EQ(SECFailure, PK11_HPKE_Open(receiver.get(), &aad_item, sealed.get(),
EXPECT_EQ(SECFailure, rv); &tmp_unsealed));
EXPECT_EQ(SEC_ERROR_BAD_DATA, PORT_GetError());
EXPECT_EQ(nullptr, tmp_unsealed); EXPECT_EQ(nullptr, tmp_unsealed);
aad_item.data[0] ^= 0xff; aad_item.data[0] ^= 0xff;
// Modify ciphertext // Modify ciphertext
sealed->data[0] ^= 0xff; sealed->data[0] ^= 0xff;
rv = PK11_HPKE_Open(receiver.get(), &aad_item, sealed.get(), &tmp_unsealed); EXPECT_EQ(SECFailure, PK11_HPKE_Open(receiver.get(), &aad_item, sealed.get(),
EXPECT_EQ(SECFailure, rv); &tmp_unsealed));
EXPECT_EQ(SEC_ERROR_BAD_DATA, PORT_GetError());
EXPECT_EQ(nullptr, tmp_unsealed); EXPECT_EQ(nullptr, tmp_unsealed);
sealed->data[0] ^= 0xff; sealed->data[0] ^= 0xff;
rv = PK11_HPKE_Open(receiver.get(), &aad_item, sealed.get(), &tmp_unsealed); EXPECT_EQ(SECSuccess, PK11_HPKE_Open(receiver.get(), &aad_item, sealed.get(),
EXPECT_EQ(SECSuccess, rv); &tmp_unsealed));
EXPECT_NE(nullptr, tmp_unsealed); EXPECT_NE(nullptr, tmp_unsealed);
unsealed.reset(tmp_unsealed); ScopedSECItem unsealed(tmp_unsealed);
CheckEquality(&msg_item, unsealed.get());
} }
TEST_F(Pkcs11HpkeTest, InvalidContextParams) { TEST_F(ModeParameterizedTest, InvalidContextParams) {
HpkeContext *cx = HpkeContext *cx =
PK11_HPKE_NewContext(static_cast<HpkeKemId>(1), HpkeKdfHkdfSha256, PK11_HPKE_NewContext(static_cast<HpkeKemId>(0xff), HpkeKdfHkdfSha256,
HpkeAeadChaCha20Poly1305, nullptr, nullptr); HpkeAeadChaCha20Poly1305, nullptr, nullptr);
EXPECT_EQ(nullptr, cx); EXPECT_EQ(nullptr, cx);
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());
cx = PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, static_cast<HpkeKdfId>(2), cx = PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, static_cast<HpkeKdfId>(0xff),
HpkeAeadChaCha20Poly1305, nullptr, nullptr); HpkeAeadChaCha20Poly1305, nullptr, nullptr);
EXPECT_EQ(nullptr, cx); EXPECT_EQ(nullptr, cx);
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());
cx = PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256, cx = PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256,
static_cast<HpkeAeadId>(4), nullptr, nullptr); static_cast<HpkeAeadId>(0xff), nullptr, nullptr);
EXPECT_EQ(nullptr, cx); EXPECT_EQ(nullptr, cx);
EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_ARGS, PORT_GetError());
} }
TEST_F(Pkcs11HpkeTest, InvalidReceiverKeyType) { TEST_F(ModeParameterizedTest, InvalidReceiverKeyType) {
ScopedHpkeContext sender( ScopedHpkeContext sender(
PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256, PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256,
HpkeAeadChaCha20Poly1305, nullptr, nullptr)); HpkeAeadChaCha20Poly1305, nullptr, nullptr));
ASSERT_TRUE(!!sender); ASSERT_TRUE(!!sender);
ScopedPK11SlotInfo slot(PK11_GetInternalSlot()); ScopedPK11SlotInfo slot(PK11_GetInternalSlot());
if (!slot) { if (!slot) {
ADD_FAILURE() << "No slot"; ADD_FAILURE() << "No slot";
return; return;
} }
skipping to change at line 510 skipping to change at line 660
SECKEYPublicKey *pub_tmp; SECKEYPublicKey *pub_tmp;
ScopedSECKEYPublicKey pub_key; ScopedSECKEYPublicKey pub_key;
ScopedSECKEYPrivateKey priv_key( ScopedSECKEYPrivateKey priv_key(
PK11_GenerateKeyPair(slot.get(), CKM_RSA_PKCS_KEY_PAIR_GEN, &rsa_param, PK11_GenerateKeyPair(slot.get(), CKM_RSA_PKCS_KEY_PAIR_GEN, &rsa_param,
&pub_tmp, PR_FALSE, PR_FALSE, nullptr)); &pub_tmp, PR_FALSE, PR_FALSE, nullptr));
ASSERT_NE(nullptr, priv_key); ASSERT_NE(nullptr, priv_key);
ASSERT_NE(nullptr, pub_tmp); ASSERT_NE(nullptr, pub_tmp);
pub_key.reset(pub_tmp); pub_key.reset(pub_tmp);
SECItem info_item = {siBuffer, nullptr, 0}; SECItem info_item = {siBuffer, nullptr, 0};
SECStatus rv = PK11_HPKE_SetupS(sender.get(), nullptr, nullptr, pub_key.get(), EXPECT_EQ(SECFailure, PK11_HPKE_SetupS(sender.get(), nullptr, nullptr,
&info_item); pub_key.get(), &info_item));
EXPECT_EQ(SECFailure, rv);
EXPECT_EQ(SEC_ERROR_BAD_KEY, PORT_GetError()); EXPECT_EQ(SEC_ERROR_BAD_KEY, PORT_GetError());
// Try with an unexpected curve // Try with an unexpected curve
StackSECItem ecParams; StackSECItem ecParams;
SECOidData *oidData = SECOID_FindOIDByTag(SEC_OID_ANSIX962_EC_PRIME256V1); SECOidData *oidData = SECOID_FindOIDByTag(SEC_OID_ANSIX962_EC_PRIME256V1);
ASSERT_NE(oidData, nullptr); ASSERT_NE(oidData, nullptr);
if (!SECITEM_AllocItem(nullptr, &ecParams, (2 + oidData->oid.len))) { if (!SECITEM_AllocItem(nullptr, &ecParams, (2 + oidData->oid.len))) {
FAIL() << "Couldn't allocate memory for OID."; FAIL() << "Couldn't allocate memory for OID.";
} }
ecParams.data[0] = SEC_ASN1_OBJECT_ID; ecParams.data[0] = SEC_ASN1_OBJECT_ID;
ecParams.data[1] = oidData->oid.len; ecParams.data[1] = oidData->oid.len;
memcpy(ecParams.data + 2, oidData->oid.data, oidData->oid.len); memcpy(ecParams.data + 2, oidData->oid.data, oidData->oid.len);
priv_key.reset(PK11_GenerateKeyPair(slot.get(), CKM_EC_KEY_PAIR_GEN, priv_key.reset(PK11_GenerateKeyPair(slot.get(), CKM_EC_KEY_PAIR_GEN,
&ecParams, &pub_tmp, PR_FALSE, PR_FALSE, &ecParams, &pub_tmp, PR_FALSE, PR_FALSE,
nullptr)); nullptr));
ASSERT_NE(nullptr, priv_key); ASSERT_NE(nullptr, priv_key);
ASSERT_NE(nullptr, pub_tmp); ASSERT_NE(nullptr, pub_tmp);
pub_key.reset(pub_tmp); pub_key.reset(pub_tmp);
rv = PK11_HPKE_SetupS(sender.get(), nullptr, nullptr, pub_key.get(), EXPECT_EQ(SECFailure, PK11_HPKE_SetupS(sender.get(), nullptr, nullptr,
&info_item); pub_key.get(), &info_item));
EXPECT_EQ(SECFailure, rv);
EXPECT_EQ(SEC_ERROR_BAD_KEY, PORT_GetError()); EXPECT_EQ(SEC_ERROR_BAD_KEY, PORT_GetError());
} }
#else #else
TEST(Pkcs11HpkeTest, EnsureNotImplemented) { TEST(HpkeTest, EnsureNotImplemented) {
ScopedHpkeContext cx( ScopedHpkeContext cx(
PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256, PK11_HPKE_NewContext(HpkeDhKemX25519Sha256, HpkeKdfHkdfSha256,
HpkeAeadChaCha20Poly1305, nullptr, nullptr)); HpkeAeadChaCha20Poly1305, nullptr, nullptr));
EXPECT_FALSE(cx.get()); EXPECT_FALSE(cx.get());
EXPECT_EQ(SEC_ERROR_INVALID_ALGORITHM, PORT_GetError()); EXPECT_EQ(SEC_ERROR_INVALID_ALGORITHM, PORT_GetError());
} }
#endif // NSS_ENABLE_DRAFT_HPKE #endif // NSS_ENABLE_DRAFT_HPKE
} // namespace nss_test } // namespace nss_test
 End of changes. 47 change blocks. 
230 lines changed or deleted 378 lines changed or added

Home  |  About  |  Features  |  All  |  Newest  |  Dox  |  Diffs  |  RSS Feeds  |  Screenshots  |  Comments  |  Imprint  |  Privacy  |  HTTP(S)