aboutsummaryrefslogtreecommitdiff
path: root/nearby/presence/np_cpp_ffi/nearby_protocol.cc
diff options
context:
space:
mode:
Diffstat (limited to 'nearby/presence/np_cpp_ffi/nearby_protocol.cc')
-rw-r--r--nearby/presence/np_cpp_ffi/nearby_protocol.cc349
1 files changed, 266 insertions, 83 deletions
diff --git a/nearby/presence/np_cpp_ffi/nearby_protocol.cc b/nearby/presence/np_cpp_ffi/nearby_protocol.cc
index 106eb77..c2f8566 100644
--- a/nearby/presence/np_cpp_ffi/nearby_protocol.cc
+++ b/nearby/presence/np_cpp_ffi/nearby_protocol.cc
@@ -27,7 +27,7 @@ namespace nearby_protocol {
static void panic_handler(PanicReason reason);
struct PanicHandler {
- void (*handler)(PanicReason);
+ void (* handler)(PanicReason);
bool set_by_client;
};
@@ -43,7 +43,7 @@ static void panic_handler(PanicReason reason) {
std::abort();
}
-static void _assert_panic(bool condition, const char *func, const char *file,
+static void _assert_panic(bool condition, const char* func, const char* file,
int line) {
if (!condition) {
std::cout << "Assert failed: \n function: " << func << "\n file: " << file
@@ -54,7 +54,7 @@ static void _assert_panic(bool condition, const char *func, const char *file,
#define assert_panic(e) _assert_panic(e, __func__, __ASSERT_FILE_NAME, __LINE__)
-bool GlobalConfig::SetPanicHandler(void (*handler)(PanicReason)) {
+bool GlobalConfig::SetPanicHandler(void (* handler)(PanicReason)) {
if (!gPanicHandler.set_by_client) {
gPanicHandler.handler = handler;
gPanicHandler.set_by_client = true;
@@ -80,15 +80,15 @@ void GlobalConfig::SetMaxNumCredentialBooks(uint32_t max_num_credential_books) {
void GlobalConfig::SetMaxNumDeserializedV0Advertisements(
uint32_t max_num_deserialized_v0_advertisements) {
np_ffi::internal::
- np_ffi_global_config_set_max_num_deserialized_v0_advertisements(
- max_num_deserialized_v0_advertisements);
+ np_ffi_global_config_set_max_num_deserialized_v0_advertisements(
+ max_num_deserialized_v0_advertisements);
}
void GlobalConfig::SetMaxNumDeserializedV1Advertisements(
uint32_t max_num_deserialized_v1_advertisements) {
np_ffi::internal::
- np_ffi_global_config_set_max_num_deserialized_v1_advertisements(
- max_num_deserialized_v1_advertisements);
+ np_ffi_global_config_set_max_num_deserialized_v1_advertisements(
+ max_num_deserialized_v1_advertisements);
}
absl::StatusOr<CredentialSlab> CredentialSlab::TryCreate() {
@@ -96,16 +96,16 @@ absl::StatusOr<CredentialSlab> CredentialSlab::TryCreate() {
auto kind = np_ffi::internal::np_ffi_CreateCredentialSlabResult_kind(result);
switch (kind) {
- case CreateCredentialSlabResultKind::Success: {
- auto slab = CredentialSlab(
- np_ffi::internal::np_ffi_CreateCredentialSlabResult_into_SUCCESS(
- result));
- return slab;
- }
- case CreateCredentialSlabResultKind::NoSpaceLeft: {
- return absl::ResourceExhaustedError(
- "No space left to create credential slab");
- }
+ case CreateCredentialSlabResultKind::Success: {
+ auto slab = CredentialSlab(
+ np_ffi::internal::np_ffi_CreateCredentialSlabResult_into_SUCCESS(
+ result));
+ return slab;
+ }
+ case CreateCredentialSlabResultKind::NoSpaceLeft: {
+ return absl::ResourceExhaustedError(
+ "No space left to create credential slab");
+ }
}
}
@@ -117,13 +117,13 @@ CredentialSlab::~CredentialSlab() {
}
}
-CredentialSlab::CredentialSlab(CredentialSlab &&other) noexcept
+CredentialSlab::CredentialSlab(CredentialSlab&& other) noexcept
: credential_slab_(other.credential_slab_), moved_(other.moved_) {
other.credential_slab_ = {};
other.moved_ = true;
}
-CredentialSlab &CredentialSlab::operator=(CredentialSlab &&other) noexcept {
+CredentialSlab& CredentialSlab::operator=(CredentialSlab&& other) noexcept {
if (this != &other) {
if (!this->moved_) {
auto result = np_ffi::internal::np_ffi_deallocate_credential_slab(
@@ -140,24 +140,58 @@ CredentialSlab &CredentialSlab::operator=(CredentialSlab &&other) noexcept {
return *this;
}
-absl::StatusOr<CredentialBook> CredentialBook::TryCreateFromSlab(CredentialSlab &slab) {
+absl::Status CredentialSlab::AddV0Credential(V0MatchableCredential v0_cred) {
+ assert_panic(!this->moved_);
+ auto result = np_ffi::internal::np_ffi_CredentialSlab_add_v0_credential(
+ this->credential_slab_, v0_cred.internal_);
+ switch (result) {
+ case AddCredentialToSlabResult::Success: {
+ return absl::OkStatus();
+ }
+ case AddCredentialToSlabResult::InvalidHandle: {
+ return absl::InvalidArgumentError(
+ "invalid credential slab handle provided");
+ }
+ }
+}
+
+absl::Status CredentialSlab::AddV1Credential(V1MatchableCredential v1_cred) {
+ assert_panic(!this->moved_);
+ auto result = np_ffi::internal::np_ffi_CredentialSlab_add_v1_credential(
+ this->credential_slab_, v1_cred.internal_);
+ switch (result) {
+ case AddCredentialToSlabResult::Success: {
+ return absl::OkStatus();
+ }
+ case AddCredentialToSlabResult::InvalidHandle: {
+ return absl::InvalidArgumentError(
+ "invalid credential slab handle provided");
+ }
+ }
+}
+
+absl::StatusOr<CredentialBook>
+CredentialBook::TryCreateFromSlab(CredentialSlab& slab) {
assert_panic(!slab.moved_);
- auto result = np_ffi::internal::np_ffi_create_credential_book_from_slab(slab.credential_slab_);
+ auto result = np_ffi::internal::np_ffi_create_credential_book_from_slab(
+ slab.credential_slab_);
auto kind = np_ffi::internal::np_ffi_CreateCredentialBookResult_kind(result);
switch (kind) {
- case CreateCredentialBookResultKind::Success: {
- auto book = np_ffi::internal::np_ffi_CreateCredentialBookResult_into_SUCCESS(result);
- slab.moved_ = true;
- return CredentialBook(book);
- }
- case CreateCredentialBookResultKind::NoSpaceLeft: {
- return absl::ResourceExhaustedError(
- "No space left to create credential book");
- }
- case CreateCredentialBookResultKind::InvalidSlabHandle: {
- return absl::NotFoundError(
- "The slab referenced by the given handle was not found.");
- }
+ case CreateCredentialBookResultKind::Success: {
+ auto book =
+ np_ffi::internal::np_ffi_CreateCredentialBookResult_into_SUCCESS(
+ result);
+ slab.moved_ = true;
+ return CredentialBook(book);
+ }
+ case CreateCredentialBookResultKind::NoSpaceLeft: {
+ return absl::ResourceExhaustedError(
+ "No space left to create credential book");
+ }
+ case CreateCredentialBookResultKind::InvalidSlabHandle: {
+ return absl::NotFoundError(
+ "The slab referenced by the given handle was not found.");
+ }
}
}
@@ -169,13 +203,13 @@ CredentialBook::~CredentialBook() {
}
}
-CredentialBook::CredentialBook(CredentialBook &&other) noexcept
+CredentialBook::CredentialBook(CredentialBook&& other) noexcept
: credential_book_(other.credential_book_), moved_(other.moved_) {
other.credential_book_ = {};
other.moved_ = true;
}
-CredentialBook &CredentialBook::operator=(CredentialBook &&other) noexcept {
+CredentialBook& CredentialBook::operator=(CredentialBook&& other) noexcept {
if (this != &other) {
if (!this->moved_) {
auto result = np_ffi::internal::np_ffi_deallocate_credential_book(
@@ -193,8 +227,8 @@ CredentialBook &CredentialBook::operator=(CredentialBook &&other) noexcept {
}
DeserializeAdvertisementResult
-Deserializer::DeserializeAdvertisement(RawAdvertisementPayload &payload,
- const CredentialBook &credential_book) {
+Deserializer::DeserializeAdvertisement(RawAdvertisementPayload& payload,
+ const CredentialBook& credential_book) {
assert_panic(!credential_book.moved_);
auto result = np_ffi::internal::np_ffi_deserialize_advertisement(
{payload.buffer_.internal_}, credential_book.credential_book_);
@@ -232,14 +266,14 @@ DeserializeAdvertisementResult::~DeserializeAdvertisementResult() {
}
DeserializeAdvertisementResult::DeserializeAdvertisementResult(
- DeserializeAdvertisementResult &&other) noexcept
+ DeserializeAdvertisementResult&& other) noexcept
: result_(other.result_), moved_(other.moved_) {
other.result_ = {};
other.moved_ = true;
}
-DeserializeAdvertisementResult &DeserializeAdvertisementResult::operator=(
- DeserializeAdvertisementResult &&other) noexcept {
+DeserializeAdvertisementResult& DeserializeAdvertisementResult::operator=(
+ DeserializeAdvertisementResult&& other) noexcept {
if (this != &other) {
if (!this->moved_) {
auto result =
@@ -258,14 +292,14 @@ DeserializeAdvertisementResult &DeserializeAdvertisementResult::operator=(
// V0 Stuff
DeserializedV0Advertisement::DeserializedV0Advertisement(
- DeserializedV0Advertisement &&other) noexcept
+ DeserializedV0Advertisement&& other) noexcept
: v0_advertisement_(other.v0_advertisement_), moved_(other.moved_) {
other.v0_advertisement_ = {};
other.moved_ = true;
}
-DeserializedV0Advertisement &DeserializedV0Advertisement::operator=(
- DeserializedV0Advertisement &&other) noexcept {
+DeserializedV0Advertisement& DeserializedV0Advertisement::operator=(
+ DeserializedV0Advertisement&& other) noexcept {
if (this != &other) {
if (!this->moved_) {
auto result =
@@ -309,16 +343,16 @@ LegibleDeserializedV0Advertisement DeserializedV0Advertisement::IntoLegible() {
}
LegibleDeserializedV0Advertisement::LegibleDeserializedV0Advertisement(
- LegibleDeserializedV0Advertisement &&other) noexcept
+ LegibleDeserializedV0Advertisement&& other) noexcept
: legible_v0_advertisement_(other.legible_v0_advertisement_),
moved_(other.moved_) {
other.moved_ = true;
other.legible_v0_advertisement_ = {};
}
-LegibleDeserializedV0Advertisement &
+LegibleDeserializedV0Advertisement&
LegibleDeserializedV0Advertisement::operator=(
- LegibleDeserializedV0Advertisement &&other) noexcept {
+ LegibleDeserializedV0Advertisement&& other) noexcept {
if (this != &other) {
if (!this->moved_) {
auto result =
@@ -343,19 +377,20 @@ LegibleDeserializedV0Advertisement::~LegibleDeserializedV0Advertisement() {
}
}
-DeserializedV0IdentityKind LegibleDeserializedV0Advertisement::GetIdentityKind() {
+DeserializedV0IdentityKind
+LegibleDeserializedV0Advertisement::GetIdentityKind() {
assert_panic(!this->moved_);
- auto result =
- np_ffi::internal::np_ffi_LegibleDeserializedV0Advertisement_get_identity_kind(
- legible_v0_advertisement_);
+ auto result = np_ffi::internal::
+ np_ffi_LegibleDeserializedV0Advertisement_get_identity_kind(
+ legible_v0_advertisement_);
return result;
}
uint8_t LegibleDeserializedV0Advertisement::GetNumberOfDataElements() {
assert_panic(!this->moved_);
return np_ffi::internal::
- np_ffi_LegibleDeserializedV0Advertisement_get_num_des(
- legible_v0_advertisement_);
+ np_ffi_LegibleDeserializedV0Advertisement_get_num_des(
+ legible_v0_advertisement_);
}
V0Payload LegibleDeserializedV0Advertisement::IntoPayload() {
@@ -366,13 +401,13 @@ V0Payload LegibleDeserializedV0Advertisement::IntoPayload() {
return V0Payload(result);
}
-V0Payload::V0Payload(V0Payload &&other) noexcept
+V0Payload::V0Payload(V0Payload&& other) noexcept
: v0_payload_(other.v0_payload_), moved_(other.moved_) {
other.v0_payload_ = {};
other.moved_ = true;
}
-V0Payload &V0Payload::operator=(V0Payload &&other) noexcept {
+V0Payload& V0Payload::operator=(V0Payload&& other) noexcept {
if (this != &other) {
if (!this->moved_) {
auto result =
@@ -401,16 +436,75 @@ absl::StatusOr<V0DataElement> V0Payload::TryGetDataElement(uint8_t index) {
auto result = np_ffi::internal::np_ffi_V0Payload_get_de(v0_payload_, index);
auto kind = np_ffi::internal::np_ffi_GetV0DEResult_kind(result);
switch (kind) {
- case GetV0DEResultKind::Success: {
- auto de = np_ffi_GetV0DEResult_into_SUCCESS(result);
- return V0DataElement(de);
+ case GetV0DEResultKind::Success: {
+ auto de = np_ffi_GetV0DEResult_into_SUCCESS(result);
+ return V0DataElement(de);
+ }
+ case GetV0DEResultKind::Error: {
+ return absl::OutOfRangeError("Invalid Data Element index");
+ }
}
- case GetV0DEResultKind::Error: {
- return absl::OutOfRangeError("Invalid Data Element index");
+}
+
+static absl::StatusOr<std::vector<uint8_t>>
+MetadataResultToVec(np_ffi::internal::DecryptMetadataResult decrypt_result) {
+ auto kind =
+ np_ffi::internal::np_ffi_DecryptMetadataResult_kind(decrypt_result);
+ switch (kind) {
+ case np_ffi::internal::DecryptMetadataResultKind::Success: {
+ auto metadata =
+ np_ffi::internal::np_ffi_DecryptMetadataResult_into_SUCCESS(
+ decrypt_result);
+ auto parts_result =
+ np_ffi::internal::np_ffi_DecryptedMetadata_get_metadata_buffer_parts(
+ metadata);
+ // The handle is guaranteed to be valid by the C++ wrapper so this should
+ // never fail
+ assert_panic(np_ffi::internal::np_ffi_GetMetadataBufferPartsResult_kind(
+ parts_result) ==
+ np_ffi::internal::GetMetadataBufferPartsResultKind::Success);
+ auto parts =
+ np_ffi::internal::np_ffi_GetMetadataBufferPartsResult_into_SUCCESS(
+ parts_result);
+ std::vector<uint8_t> result(parts.ptr, parts.ptr + parts.len);
+
+ // Now that the contents have been copied into the vec, the underlying
+ // handle can be de-allocated
+ auto deallocate_result =
+ np_ffi::internal::np_ffi_deallocate_DecryptedMetadata(metadata);
+ assert_panic(deallocate_result ==
+ np_ffi::internal::DeallocateResult::Success);
+ return result;
+ }
+ case np_ffi::internal::DecryptMetadataResultKind::Error: {
+ return absl::InvalidArgumentError("Invalid V0 payload handle");
+ }
}
+}
+
+absl::StatusOr<DeserializedV0IdentityDetails> V0Payload::GetIdentityDetails() {
+ assert_panic(!this->moved_);
+ auto result = np_ffi::internal::np_ffi_V0Payload_get_identity_details(
+ this->v0_payload_);
+ auto kind = np_ffi::internal::np_ffi_GetV0IdentityDetailsResult_kind(result);
+ switch (kind) {
+ case np_ffi::internal::GetV0IdentityDetailsResultKind::Error: {
+ return absl::InvalidArgumentError("Invalid handle");
+ }
+ case np_ffi::internal::GetV0IdentityDetailsResultKind::Success: {
+ return np_ffi::internal::np_ffi_GetV0IdentityDetailsResult_into_SUCCESS(
+ result);
+ }
}
}
+absl::StatusOr<std::vector<uint8_t>> V0Payload::DecryptMetadata() {
+ assert_panic(!this->moved_);
+ auto decrypt_result =
+ np_ffi::internal::np_ffi_V0Payload_decrypt_metadata(this->v0_payload_);
+ return MetadataResultToVec(decrypt_result);
+}
+
V0DataElementKind V0DataElement::GetKind() {
return np_ffi::internal::np_ffi_V0DataElement_kind(v0_data_element_);
}
@@ -440,7 +534,7 @@ uint8_t V0Actions::GetContextSyncSequenceNumber() {
// This is called after all references to the shared_ptr have gone out of scope
auto DeallocateV1Adv(
- np_ffi::internal::DeserializedV1Advertisement *v1_advertisement) {
+ np_ffi::internal::DeserializedV1Advertisement* v1_advertisement) {
auto result =
np_ffi::internal::np_ffi_deallocate_deserialized_V1_advertisement(
*v1_advertisement);
@@ -457,11 +551,11 @@ DeserializedV1Advertisement::DeserializedV1Advertisement(
}
DeserializedV1Advertisement::DeserializedV1Advertisement(
- DeserializedV1Advertisement &&other) noexcept
+ DeserializedV1Advertisement&& other) noexcept
: v1_advertisement_(std::move(other.v1_advertisement_)) {}
-DeserializedV1Advertisement &DeserializedV1Advertisement::operator=(
- DeserializedV1Advertisement &&other) noexcept {
+DeserializedV1Advertisement& DeserializedV1Advertisement::operator=(
+ DeserializedV1Advertisement&& other) noexcept {
if (this != &other) {
this->v1_advertisement_ = std::move(other.v1_advertisement_);
}
@@ -472,15 +566,15 @@ DeserializedV1Advertisement &DeserializedV1Advertisement::operator=(
uint8_t DeserializedV1Advertisement::GetNumLegibleSections() {
assert_panic(this->v1_advertisement_ != nullptr);
return np_ffi::internal::
- np_ffi_DeserializedV1Advertisement_get_num_legible_sections(
- *v1_advertisement_);
+ np_ffi_DeserializedV1Advertisement_get_num_legible_sections(
+ *v1_advertisement_);
}
uint8_t DeserializedV1Advertisement::GetNumUndecryptableSections() {
assert_panic(this->v1_advertisement_ != nullptr);
return np_ffi::internal::
- np_ffi_DeserializedV1Advertisement_get_num_undecryptable_sections(
- *v1_advertisement_);
+ np_ffi_DeserializedV1Advertisement_get_num_undecryptable_sections(
+ *v1_advertisement_);
}
absl::StatusOr<DeserializedV1Section>
@@ -491,14 +585,14 @@ DeserializedV1Advertisement::TryGetSection(uint8_t section_index) {
*v1_advertisement_, section_index);
auto kind = np_ffi::internal::np_ffi_GetV1SectionResult_kind(result);
switch (kind) {
- case np_ffi::internal::GetV1SectionResultKind::Error: {
- return absl::OutOfRangeError("Invalid section index");
- }
- case np_ffi::internal::GetV1SectionResultKind::Success: {
- auto section =
- np_ffi::internal::np_ffi_GetV1SectionResult_into_SUCCESS(result);
- return DeserializedV1Section(section, v1_advertisement_);
- }
+ case np_ffi::internal::GetV1SectionResultKind::Error: {
+ return absl::OutOfRangeError("Invalid section index");
+ }
+ case np_ffi::internal::GetV1SectionResultKind::Success: {
+ auto section =
+ np_ffi::internal::np_ffi_GetV1SectionResult_into_SUCCESS(result);
+ return DeserializedV1Section(section, v1_advertisement_);
+ }
}
}
@@ -517,23 +611,112 @@ DeserializedV1Section::TryGetDataElement(uint8_t index) {
np_ffi::internal::np_ffi_DeserializedV1Section_get_de(section_, index);
auto kind = np_ffi::internal::np_ffi_GetV1DEResult_kind(result);
switch (kind) {
- case np_ffi::internal::GetV1DEResultKind::Error: {
- return absl::OutOfRangeError("Invalid data element index for this section");
+ case np_ffi::internal::GetV1DEResultKind::Error: {
+ return absl::OutOfRangeError("Invalid data element index for this section");
+ }
+ case np_ffi::internal::GetV1DEResultKind::Success: {
+ return V1DataElement(
+ np_ffi::internal::np_ffi_GetV1DEResult_into_SUCCESS(result));
+ }
}
- case np_ffi::internal::GetV1DEResultKind::Success: {
- return V1DataElement(
- np_ffi::internal::np_ffi_GetV1DEResult_into_SUCCESS(result));
+}
+
+absl::StatusOr<std::vector<uint8_t>> DeserializedV1Section::DecryptMetadata() {
+ assert_panic(this->owning_v1_advertisement_ != nullptr);
+ auto decrypt_result =
+ np_ffi::internal::np_ffi_DeserializedV1Section_decrypt_metadata(
+ this->section_);
+ return MetadataResultToVec(decrypt_result);
+}
+
+absl::StatusOr<DeserializedV1IdentityDetails>
+DeserializedV1Section::GetIdentityDetails() {
+ assert_panic(this->owning_v1_advertisement_ != nullptr);
+ auto result =
+ np_ffi::internal::np_ffi_DeserializedV1Section_get_identity_details(
+ this->section_);
+ auto kind = np_ffi::internal::np_ffi_GetV1IdentityDetailsResult_kind(result);
+ switch (kind) {
+ case np_ffi::internal::GetV1IdentityDetailsResultKind::Error: {
+ return absl::InvalidArgumentError("Invalid handle");
+ }
+ case np_ffi::internal::GetV1IdentityDetailsResultKind::Success: {
+ return np_ffi::internal::np_ffi_GetV1IdentityDetailsResult_into_SUCCESS(
+ result);
+ }
}
+}
+
+absl::StatusOr<std::array<uint8_t, 16>> DeserializedV1Section::DeriveSaltForOffset(
+ uint8_t offset) {
+ auto result =
+ np_ffi::internal::np_ffi_DeserializedV1Section_derive_16_byte_salt_for_offset(
+ this->section_,
+ offset);
+ auto kind = np_ffi::internal::np_ffi_GetV1DE16ByteSaltResult_kind(result);
+ switch (kind) {
+ case np_ffi::internal::GetV1DE16ByteSaltResultKind::Error: {
+ return absl::InvalidArgumentError("Failed to derive salt for offset");
+ }
+ case np_ffi::internal::GetV1DE16ByteSaltResultKind::Success: {
+ auto buffer = np_ffi::internal::np_ffi_GetV1DE16ByteSaltResult_into_SUCCESS(result);
+ return std::to_array(buffer._0);
+ }
}
}
uint32_t V1DataElement::GetDataElementTypeCode() const {
return np_ffi::internal::np_ffi_V1DEType_to_uint32_t(
- v1_data_element_.generic._0.de_type);
+ np_ffi::internal::np_ffi_V1DataElement_to_generic(this->v1_data_element_)
+ .de_type);
}
ByteBuffer<127> V1DataElement::GetPayload() const {
- return ByteBuffer(v1_data_element_.generic._0.payload);
+ return ByteBuffer(
+ np_ffi::internal::np_ffi_V1DataElement_to_generic(this->v1_data_element_)
+ .payload);
}
+uint8_t V1DataElement::GetOffset() const {
+ return np_ffi::internal::np_ffi_V1DataElement_to_generic(
+ this->v1_data_element_)
+ .offset;
+}
+
+MatchedCredentialData::MatchedCredentialData(
+ uint32_t cred_id, std::span<uint8_t> metadata_bytes) {
+ this->data_ = {cred_id, metadata_bytes.data(), metadata_bytes.size()};
+}
+
+template<typename T, size_t N>
+static void CopyToRawArray(T (& dest)[N], const std::array<T, N>& src) {
+ memcpy(dest, src.data(), sizeof(T) * N);
+}
+
+V0MatchableCredential::V0MatchableCredential(
+ std::array<uint8_t, 32> key_seed,
+ std::array<uint8_t, 32> legacy_metadata_key_hmac,
+ MatchedCredentialData matched_credential_data) {
+ np_ffi::internal::V0DiscoveryCredential discovery_cred{};
+ CopyToRawArray(discovery_cred.key_seed, key_seed);
+ CopyToRawArray(discovery_cred.legacy_metadata_key_hmac,
+ legacy_metadata_key_hmac);
+ this->internal_ = {discovery_cred, matched_credential_data.data_};
+}
+
+V1MatchableCredential::V1MatchableCredential(
+ std::array<uint8_t, 32> key_seed,
+ std::array<uint8_t, 32> expected_unsigned_metadata_key_hmac,
+ std::array<uint8_t, 32> expected_signed_metadata_key_hmac,
+ std::array<uint8_t, 32> pub_key,
+ MatchedCredentialData matched_credential_data) {
+ np_ffi::internal::V1DiscoveryCredential discovery_cred{};
+ CopyToRawArray(discovery_cred.key_seed, key_seed);
+ CopyToRawArray(discovery_cred.expected_unsigned_metadata_key_hmac,
+ expected_unsigned_metadata_key_hmac);
+ CopyToRawArray(discovery_cred.expected_signed_metadata_key_hmac,
+ expected_signed_metadata_key_hmac);
+ CopyToRawArray(discovery_cred.pub_key, pub_key);
+ this->internal_ = {discovery_cred, matched_credential_data.data_};
+}
} // namespace nearby_protocol