Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
43 changes: 33 additions & 10 deletions include/internal/libspdm_common_lib.h
Original file line number Diff line number Diff line change
Expand Up @@ -1158,24 +1158,47 @@ bool libspdm_calculate_l1l2_hash(libspdm_context_t *spdm_context,
#endif /* LIBSPDM_RECORD_TRANSCRIPT_DATA_SUPPORT */

/**
* Get element from multi element opaque data by element id.
* Get element from multi element opaque data by element id and element index
*
* @param[in] spdm_context A pointer to the SPDM context.
* @param[in] data_in_size Size of multi element opaque data.
* @param[in] data_in A pointer to the multi element opaque data.
* @param[in] element_id Element id.
* @param[in] element_index Element index, start from 0.
* It is used to get the nth element with the same element id.
* @param[out] total_matched_element_cnt Pointer to store total matched element count with the same element id.
* @param[out] get_element_ptr Pointer to store found element.
* @param[out] get_element_len Pointer to length of found element.
*
* @retval true Get element successfully
* @retval false Get element failed
**/
bool libspdm_get_element_from_opaque_data_with_element_id (libspdm_context_t *spdm_context,
size_t data_in_size, const void *data_in,
uint8_t element_id, uint8_t element_index,
uint8_t *total_matched_element_cnt,
const void **get_element_ptr, size_t *get_element_len);

/**
* Get secured message opaque data element from multi element opaque data by sm data id
*
* This function should be called in
* libspdm_process_opaque_data_supported_version_data/libspdm_process_opaque_data_version_selection_data.
*
* @param[in] data_in_size Size of multi element opaque data.
* @param[in] data_in A pointer to the multi element opaque data.
* @param[in] element_id Element id.
* @param[in] sm_data_id ID for the Secured Message data type.
* @param[out] get_element_ptr Pointer to store found element.
* @param[in] spdm_context A pointer to the SPDM context.
* @param[in] data_in_size Size of multi element opaque data.
* @param[in] data_in A pointer to the multi element opaque data.
* @param[in] sm_data_id ID for the Secured Message data type.
* @param[out] get_element_ptr Pointer to store found element.
* @param[out] get_element_len Pointer to length of found element.
*
* @retval true Get element successfully
* @retval false Get element failed
**/
bool libspdm_get_element_from_opaque_data(libspdm_context_t *spdm_context,
size_t data_in_size, const void *data_in,
uint8_t element_id, uint8_t sm_data_id,
const void **get_element_ptr, size_t *get_element_len);
bool libspdm_get_sm_data_element_from_opaque_data (libspdm_context_t *spdm_context,
size_t data_in_size, const void *data_in,
uint8_t sm_data_id,
const void **get_element_ptr, size_t *get_element_len);

/**
* Process opaque data version selection.
Expand Down
110 changes: 81 additions & 29 deletions library/spdm_common_lib/libspdm_com_opaque_data.c
Original file line number Diff line number Diff line change
Expand Up @@ -72,21 +72,21 @@ size_t libspdm_get_untrusted_opaque_data_supported_version_data_size(
return (size + 3) & ~3;
}

bool libspdm_get_element_from_opaque_data(libspdm_context_t *spdm_context,
size_t data_in_size, const void *data_in,
uint8_t element_id, uint8_t sm_data_id,
const void **get_element_ptr, size_t *get_element_len)
bool libspdm_get_element_from_opaque_data_with_element_id (libspdm_context_t *spdm_context,
size_t data_in_size, const void *data_in,
uint8_t element_id, uint8_t element_index,
uint8_t *total_matched_element_cnt,
const void **get_element_ptr, size_t *get_element_len)
{
const secured_message_general_opaque_data_table_header_t *general_opaque_data_table_header;
const spdm_general_opaque_data_table_header_t *spdm_general_opaque_data_table_header;
const opaque_element_table_header_t *opaque_element_table_header;
uint16_t opaque_element_data_len;
const secured_message_opaque_element_table_header_t *secured_message_element_table_header;
const secured_message_opaque_element_header_t *secured_message_element_header;

bool result;
uint8_t element_num;
uint8_t element_index;
uint8_t index;
uint8_t matched_element_cnt;
size_t data_element_size;
size_t current_element_len;
size_t total_element_len;
Expand Down Expand Up @@ -133,7 +133,9 @@ bool libspdm_get_element_from_opaque_data(libspdm_context_t *spdm_context,
total_element_len = 0;
result = false;

for (element_index = 0; element_index < element_num; element_index++) {
/* find the Nth element with specific element_id, N = element_index. */
matched_element_cnt = 0;
for (index = 0; index < element_num; index++) {
/*ensure the opaque_element_table_header is valid*/
if (total_element_len + sizeof(opaque_element_table_header_t) >
data_element_size) {
Expand Down Expand Up @@ -166,25 +168,13 @@ bool libspdm_get_element_from_opaque_data(libspdm_context_t *spdm_context,
}

if (opaque_element_table_header->id == element_id) {
secured_message_element_table_header = (const void *)opaque_element_table_header;
if (secured_message_element_table_header->vendor_len == 0) {
secured_message_element_header =
(const void *)(secured_message_element_table_header + 1);
if ((const uint8_t *)secured_message_element_header +
sizeof(secured_message_opaque_element_header_t) >
(const uint8_t *)data_in + data_in_size) {
return false;
}

if ((secured_message_element_header->sm_data_id == sm_data_id) &&
(secured_message_element_header->sm_data_version ==
SECURED_MESSAGE_OPAQUE_ELEMENT_SMDATA_DATA_VERSION)) {
/*get element by element id*/
*get_element_ptr = opaque_element_table_header;
*get_element_len = current_element_len;
result = true;
}
/*get element by element id*/
if (matched_element_cnt == element_index) {
*get_element_ptr = opaque_element_table_header;
*get_element_len = current_element_len;
result = true;
}
matched_element_cnt += 1;
}

/*move to next element*/
Expand All @@ -198,9 +188,72 @@ bool libspdm_get_element_from_opaque_data(libspdm_context_t *spdm_context,
return false;
}

*total_matched_element_cnt = matched_element_cnt;
return result;
}

bool libspdm_get_sm_data_element_from_opaque_data (libspdm_context_t *spdm_context,
size_t data_in_size, const void *data_in,
uint8_t sm_data_id,
const void **get_element_ptr, size_t *get_element_len)
{
const opaque_element_table_header_t *opaque_element_table_header;
size_t opaque_element_len;
const secured_message_opaque_element_table_header_t *secured_message_element_table_header;
const secured_message_opaque_element_header_t *secured_message_element_header;
bool result;
uint8_t element_index;
uint8_t element_num;
uint8_t total_matched_element_cnt;

/*check parameter in*/
if ((data_in_size == 0) || (data_in == NULL)) {
return false;
}

/*get the total matched element count*/
result = libspdm_get_element_from_opaque_data_with_element_id(
spdm_context, data_in_size, data_in,
SPDM_REGISTRY_ID_DMTF, 0, &total_matched_element_cnt,
(const void **) &opaque_element_table_header, &opaque_element_len);
if (!result) {
return false;
}

element_num = total_matched_element_cnt;
for (element_index = 0; element_index < element_num; element_index++) {
/*get element by element id*/
result = libspdm_get_element_from_opaque_data_with_element_id(
spdm_context, data_in_size, data_in,
SPDM_REGISTRY_ID_DMTF, element_index, &total_matched_element_cnt,
(const void **) &opaque_element_table_header, &opaque_element_len);
if (!result) {
return false;
}

secured_message_element_table_header = (const void *)opaque_element_table_header;
if (secured_message_element_table_header->vendor_len == 0) {
secured_message_element_header =
(const void *)(secured_message_element_table_header + 1);
if ((const uint8_t *)secured_message_element_header +
sizeof(secured_message_opaque_element_header_t) >
(const uint8_t *)data_in + data_in_size) {
return false;
}

if ((secured_message_element_header->sm_data_id == sm_data_id) &&
(secured_message_element_header->sm_data_version ==
SECURED_MESSAGE_OPAQUE_ELEMENT_SMDATA_DATA_VERSION)) {
*get_element_ptr = opaque_element_table_header;
*get_element_len = opaque_element_len;
return true;
}
}
}

return false;
}

bool libspdm_process_general_opaque_data_check(libspdm_context_t *spdm_context,
size_t data_in_size,
const void *data_in)
Expand Down Expand Up @@ -321,9 +374,8 @@ libspdm_return_t libspdm_process_opaque_data_version_selection_data(
return LIBSPDM_STATUS_SUCCESS;
}

result = libspdm_get_element_from_opaque_data(
spdm_context, data_in_size,
data_in, SPDM_REGISTRY_ID_DMTF,
result = libspdm_get_sm_data_element_from_opaque_data(
spdm_context, data_in_size, data_in,
SECURED_MESSAGE_OPAQUE_ELEMENT_SMDATA_ID_VERSION_SELECTION,
&get_element_ptr, &get_element_len);
if ((!result) || (get_element_ptr == NULL)) {
Expand Down
7 changes: 3 additions & 4 deletions library/spdm_responder_lib/libspdm_rsp_common.c
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
/**
* Copyright Notice:
* Copyright 2021-2025 DMTF. All rights reserved.
* Copyright 2021-2026 DMTF. All rights reserved.
* License: BSD 3-Clause License. For full text see link: https://github.com/DMTF/libspdm/blob/main/LICENSE.md
**/

Expand Down Expand Up @@ -118,10 +118,9 @@ libspdm_return_t libspdm_process_opaque_data_supported_version_data(
return LIBSPDM_STATUS_INVALID_MSG_FIELD;
}

result = libspdm_get_element_from_opaque_data(
result = libspdm_get_sm_data_element_from_opaque_data(
spdm_context, data_in_size,
data_in, SPDM_REGISTRY_ID_DMTF,
SECURED_MESSAGE_OPAQUE_ELEMENT_SMDATA_ID_SUPPORTED_VERSION,
data_in, SECURED_MESSAGE_OPAQUE_ELEMENT_SMDATA_ID_SUPPORTED_VERSION,
&get_element_ptr, &get_element_len);
if ((!result) || (get_element_ptr == NULL)) {
LIBSPDM_DEBUG((LIBSPDM_DEBUG_INFO,"get element error!\n"));
Expand Down
24 changes: 11 additions & 13 deletions unit_test/test_spdm_common/context_data.c
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
/**
* Copyright Notice:
* Copyright 2021-2025 DMTF. All rights reserved.
* Copyright 2021-2026 DMTF. All rights reserved.
* License: BSD 3-Clause License. For full text see link: https://github.com/DMTF/libspdm/blob/main/LICENSE.md
**/

Expand Down Expand Up @@ -1695,19 +1695,17 @@ static void libspdm_test_process_opaque_data_case22(void **state)

opaque_data_ptr = (uint8_t *)&opaque_data;
opaque_data_size = sizeof(opaque_data);
status = libspdm_get_element_from_opaque_data(spdm_context,
opaque_data_size, opaque_data_ptr,
SPDM_REGISTRY_ID_DMTF,
SECURED_MESSAGE_OPAQUE_ELEMENT_SMDATA_ID_VERSION_SELECTION,
&get_element_ptr, &get_element_len
);
status = libspdm_get_sm_data_element_from_opaque_data(spdm_context,
opaque_data_size, opaque_data_ptr,
SECURED_MESSAGE_OPAQUE_ELEMENT_SMDATA_ID_VERSION_SELECTION,
&get_element_ptr, &get_element_len
);
assert_int_equal (status, true);
status = libspdm_get_element_from_opaque_data(spdm_context,
opaque_data_size, opaque_data_ptr,
SPDM_REGISTRY_ID_DMTF,
SECURED_MESSAGE_OPAQUE_ELEMENT_SMDATA_ID_SUPPORTED_VERSION,
&get_element_ptr, &get_element_len
);
status = libspdm_get_sm_data_element_from_opaque_data(spdm_context,
opaque_data_size, opaque_data_ptr,
SECURED_MESSAGE_OPAQUE_ELEMENT_SMDATA_ID_SUPPORTED_VERSION,
&get_element_ptr, &get_element_len
);
assert_int_equal (status, true);
}

Expand Down