1 /* SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later */ 2 #ifndef BASE_H 3 #define BASE_H 4 5 #ifdef __cplusplus 6 extern "C" { 7 #endif 8 9 #include <libpldm/compiler.h> 10 #include <libpldm/pldm_types.h> 11 #include <libpldm/utils.h> 12 13 #include <asm/byteorder.h> 14 #include <stdalign.h> 15 #include <stdbool.h> 16 #include <stddef.h> 17 #include <stdint.h> 18 19 typedef uint8_t pldm_tid_t; 20 21 /** @brief PLDM Types 22 */ 23 enum pldm_supported_types { 24 PLDM_BASE = 0x00, 25 PLDM_SMBIOS = 0x01, 26 PLDM_PLATFORM = 0x02, 27 PLDM_BIOS = 0x03, 28 PLDM_FRU = 0x04, 29 PLDM_FWUP = 0x05, 30 PLDM_RDE = 0x06, 31 PLDM_FILE = 0x07, 32 PLDM_OEM = 0x3f, 33 }; 34 35 /** @brief PLDM Commands 36 */ 37 enum pldm_supported_commands { 38 PLDM_SET_TID = 0x1, 39 PLDM_GET_TID = 0x2, 40 PLDM_GET_PLDM_VERSION = 0x3, 41 PLDM_GET_PLDM_TYPES = 0x4, 42 PLDM_GET_PLDM_COMMANDS = 0x5, 43 PLDM_SELECT_PLDM_VERSION = 0x6, 44 PLDM_NEGOTIATE_TRANSFER_PARAMETERS = 0x7, 45 PLDM_MULTIPART_SEND = 0x8, 46 PLDM_MULTIPART_RECEIVE = 0x9, 47 PLDM_GET_MULTIPART_TRANSFER_SUPPORT = 0xa, 48 }; 49 50 /** @brief PLDM base codes 51 */ 52 enum pldm_completion_codes { 53 PLDM_SUCCESS = 0x00, 54 PLDM_ERROR = 0x01, 55 PLDM_ERROR_INVALID_DATA = 0x02, 56 PLDM_ERROR_INVALID_LENGTH = 0x03, 57 PLDM_ERROR_NOT_READY = 0x04, 58 PLDM_ERROR_UNSUPPORTED_PLDM_CMD = 0x05, 59 PLDM_ERROR_INVALID_PLDM_TYPE = 0x20, 60 PLDM_INVALID_TRANSFER_OPERATION_FLAG = 0x21 61 }; 62 63 enum transfer_op_flag { 64 PLDM_GET_NEXTPART = 0, 65 PLDM_GET_FIRSTPART = 1, 66 PLDM_ACKNOWLEDGEMENT_ONLY = 2, 67 }; 68 69 enum transfer_multipart_op_flag { 70 PLDM_XFER_FIRST_PART = 0, 71 PLDM_XFER_NEXT_PART = 1, 72 PLDM_XFER_ABORT = 2, 73 PLDM_XFER_COMPLETE = 3, 74 PLDM_XFER_CURRENT_PART = 4, 75 }; 76 77 enum pldm_base_multipart_receive_transfer_flag { 78 PLDM_BASE_MULTIPART_RECEIVE_TRANSFER_FLAG_START = 0x01, 79 PLDM_BASE_MULTIPART_RECEIVE_TRANSFER_FLAG_MIDDLE = 0x02, 80 PLDM_BASE_MULTIPART_RECEIVE_TRANSFER_FLAG_END = 0x04, 81 PLDM_BASE_MULTIPART_RECEIVE_TRANSFER_FLAG_START_AND_END = 0x05, 82 PLDM_BASE_MULTIPART_RECEIVE_TRANSFER_FLAG_ACK_COMPLETION = 0x08, 83 }; 84 85 enum transfer_resp_flag { 86 PLDM_START = 0x01, 87 PLDM_MIDDLE = 0x02, 88 PLDM_END = 0x04, 89 PLDM_START_AND_END = 0x05, 90 }; 91 92 /** @brief PLDM transport protocol type 93 */ 94 enum pldm_transport_protocol_type { 95 PLDM_TRANSPORT_PROTOCOL_TYPE_MCTP = 0x00, 96 PLDM_TRANSPORT_PROTOCOL_TYPE_OEM = 0xff, 97 }; 98 99 /** @enum MessageType 100 * 101 * The different message types supported by the PLDM specification. 102 */ 103 typedef enum { 104 PLDM_RESPONSE, //!< PLDM response 105 PLDM_REQUEST, //!< PLDM request 106 PLDM_RESERVED, //!< Reserved 107 PLDM_ASYNC_REQUEST_NOTIFY, //!< Unacknowledged PLDM request messages 108 } MessageType; 109 110 #define PLDM_INSTANCE_MAX 31 111 #define PLDM_MAX_TYPES 64 112 #define PLDM_MAX_CMDS_PER_TYPE 256 113 #define PLDM_MAX_TIDS 256 114 #define PLDM_TID_UNASSIGNED 0x00 115 #define PLDM_TID_RESERVED 0xff 116 117 /* Message payload lengths */ 118 #define PLDM_GET_COMMANDS_REQ_BYTES 5 119 #define PLDM_GET_VERSION_REQ_BYTES 6 120 121 /* Response lengths are inclusive of completion code */ 122 #define PLDM_GET_TYPES_REQ_BYTES 0 123 #define PLDM_GET_TYPES_RESP_BYTES 9 124 #define PLDM_GET_TID_REQ_BYTES 0 125 #define PLDM_GET_TID_RESP_BYTES 2 126 #define PLDM_SET_TID_REQ_BYTES 1 127 #define PLDM_SET_TID_RESP_BYTES 1 128 #define PLDM_GET_COMMANDS_RESP_BYTES 33 129 /* Response data has only one version and does not contain the checksum */ 130 #define PLDM_GET_VERSION_RESP_BYTES 10 131 #define PLDM_MULTIPART_RECEIVE_REQ_BYTES 18 132 #define PLDM_BASE_MULTIPART_RECEIVE_RESP_MIN_BYTES 10 133 134 #define PLDM_VERSION_0 0 135 #define PLDM_CURRENT_VERSION PLDM_VERSION_0 136 137 #define PLDM_TIMESTAMP104_SIZE 13 138 139 /** @brief Minimum length of response for a optional PLDM command 140 * 141 * For a optional PLDM command, the command handler might not be 142 * implemented in a device's firmware, a response contains only CC 143 * might come in, such as ERROR_UNSUPPORTED_PLDM_CMD. 144 * 145 * The description can be found in DSP0240: 146 * > For an unsupported PLDM command, the ERROR_UNSUPPORTED_PLDM_CMD 147 * > completion code shall be returned unless the responder is in a 148 * > transient state (not ready), in which it cannot process the PLDM 149 * > command. If the responder is in a transient state, it may return 150 * > the ERROR_NOT_READY completion code. 151 */ 152 #define PLDM_OPTIONAL_COMMAND_RESP_MIN_LEN 1 153 154 /** @struct pldm_msg_hdr 155 * 156 * Structure representing PLDM message header fields 157 */ 158 struct pldm_msg_hdr { 159 #if defined(__LITTLE_ENDIAN_BITFIELD) 160 uint8_t instance_id : 5; //!< Instance ID 161 uint8_t reserved : 1; //!< Reserved 162 uint8_t datagram : 1; //!< Datagram bit 163 uint8_t request : 1; //!< Request bit 164 #elif defined(__BIG_ENDIAN_BITFIELD) 165 uint8_t request : 1; //!< Request bit 166 uint8_t datagram : 1; //!< Datagram bit 167 uint8_t reserved : 1; //!< Reserved 168 uint8_t instance_id : 5; //!< Instance ID 169 #endif 170 171 #if defined(__LITTLE_ENDIAN_BITFIELD) 172 uint8_t type : 6; //!< PLDM type 173 uint8_t header_ver : 2; //!< Header version 174 #elif defined(__BIG_ENDIAN_BITFIELD) 175 uint8_t header_ver : 2; //!< Header version 176 uint8_t type : 6; //!< PLDM type 177 #endif 178 uint8_t command; //!< PLDM command code 179 } __attribute__((packed)); 180 181 // Macros for byte-swapping variables in-place 182 #define HTOLE32(X) ((X) = htole32(X)) 183 #define HTOLE16(X) ((X) = htole16(X)) 184 #define LE32TOH(X) ((X) = le32toh(X)) 185 #define LE16TOH(X) ((X) = le16toh(X)) 186 187 /** @struct pldm_msg 188 * 189 * Structure representing PLDM message 190 */ 191 struct pldm_msg { 192 struct pldm_msg_hdr hdr; //!< PLDM message header 193 uint8_t payload[1]; //!< &payload[0] is the beginning of the payload 194 } __attribute__((packed)); 195 196 /** @brief Determine the underlying object size for a @struct pldm_msg 197 * 198 * @pre @p size must be a constant expression 199 * 200 * @note Providing an expression for @p size that is not an integer constant 201 * expression will force a compilation failure. 202 * 203 * @param size The desired size of the @struct pldm_msg payload 204 */ 205 #define PLDM_MSG_SIZE(size) \ 206 (sizeof(char[(__builtin_constant_p(size)) ? 1 : -1])) * \ 207 (sizeof(struct pldm_msg) - \ 208 sizeof(((struct pldm_msg *)NULL)->payload) + (size)) 209 210 /** @brief Stack-allocate a buffer to hold a @struct pldm_msg 211 * 212 * Allocate an appropriately aligned array named @p name of type unsigned char 213 * with the necessary length to hold a payload of the requested size. 214 * 215 * @param name - The variable name used to define the buffer 216 * @param size - The desired payload length for the intended @struct pldm_msg 217 */ 218 #define PLDM_MSG_BUFFER(name, size) \ 219 alignas(struct pldm_msg) unsigned char(name)[PLDM_MSG_SIZE(size)] 220 221 /** @brief Create a pointer to a stack-allocated @struct pldm_msg 222 * 223 * Define a pointer named @p name of type @struct pldm_msg to an object on the 224 * stack of appropriate alignment and length to hold a @struct pldm_msg with a 225 * payload of @p size. 226 * 227 * @param name - The variable name for pointer 228 * @param size - The desired payload length for the underlying @struct pldm_msg 229 * buffer 230 */ 231 #ifdef __cplusplus 232 #define PLDM_MSG_DEFINE_P(name, size) \ 233 PLDM_MSG_BUFFER(name##_buf, size); \ 234 auto *(name) = new (name##_buf) pldm_msg 235 #endif 236 237 /** 238 * @brief Compare the headers from two PLDM messages to determine if the latter 239 * is a message representing a response to the former, where the former must be 240 * a request. 241 * 242 * @param[in] req - A pointer to a PLDM header object, which must represent a 243 * request 244 * @param[in] resp - A pointer to a PLDM header object, which may represent a 245 * response to the provided request. 246 * 247 * @return true if the header pointed to by resp represents a message that is a 248 * response to the header pointed to by req, otherwise false. 249 */ 250 bool pldm_msg_hdr_correlate_response(const struct pldm_msg_hdr *req, 251 const struct pldm_msg_hdr *resp); 252 253 /** @struct pldm_header_info 254 * 255 * The information needed to prepare PLDM header and this is passed to the 256 * pack_pldm_header and unpack_pldm_header API. 257 */ 258 struct pldm_header_info { 259 MessageType msg_type; //!< PLDM message type 260 uint8_t instance; //!< PLDM instance id 261 uint8_t pldm_type; //!< PLDM type 262 uint8_t command; //!< PLDM command code 263 uint8_t completion_code; //!< PLDM completion code, applies for response 264 }; 265 266 /** @struct pldm_get_types_resp 267 * 268 * Structure representing PLDM get types response. 269 */ 270 struct pldm_get_types_resp { 271 uint8_t completion_code; //!< completion code 272 bitfield8_t types[8]; //!< each bit represents whether a given PLDM Type 273 //!< is supported 274 } __attribute__((packed)); 275 276 /** @struct pldm_get_commands_req 277 * 278 * Structure representing PLDM get commands request. 279 */ 280 struct pldm_get_commands_req { 281 uint8_t type; //!< PLDM Type for which command support information is 282 //!< being requested 283 ver32_t version; //!< version for the specified PLDM Type 284 } __attribute__((packed)); 285 286 /** @struct pldm_get_commands_resp 287 * 288 * Structure representing PLDM get commands response. 289 */ 290 struct pldm_get_commands_resp { 291 uint8_t completion_code; //!< completion code 292 bitfield8_t commands[32]; //!< each bit represents whether a given PLDM 293 //!< command is supported 294 } __attribute__((packed)); 295 296 /** @struct pldm_get_version_req 297 * 298 * Structure representing PLDM get version request. 299 */ 300 struct pldm_get_version_req { 301 uint32_t transfer_handle; //!< handle to identify PLDM version data transfer 302 uint8_t transfer_opflag; //!< PLDM GetVersion operation flag 303 uint8_t type; //!< PLDM Type for which version information is being requested 304 } __attribute__((packed)); 305 306 /** @struct pldm_get_version_resp 307 * 308 * Structure representing PLDM get version response. 309 */ 310 311 struct pldm_get_version_resp { 312 uint8_t completion_code; //!< completion code 313 uint32_t next_transfer_handle; //!< next portion of PLDM version data 314 //!< transfer 315 uint8_t transfer_flag; //!< PLDM GetVersion transfer flag 316 uint8_t version_data[1]; //!< PLDM GetVersion version field 317 } __attribute__((packed)); 318 319 /** @struct pldm_set_tid_req 320 * 321 * Structure representing PLDM set tid request. 322 */ 323 324 struct pldm_set_tid_req { 325 uint8_t tid; //!< PLDM SetTID TID field 326 } __attribute__((packed)); 327 328 /** @struct pldm_get_tid_resp 329 * 330 * Structure representing PLDM get tid response. 331 */ 332 333 struct pldm_get_tid_resp { 334 uint8_t completion_code; //!< completion code 335 uint8_t tid; //!< PLDM GetTID TID field 336 } __attribute__((packed)); 337 338 /** @struct pldm_multipart_receive_req 339 * 340 * Structure representing PLDM multipart receive request. 341 */ 342 struct pldm_multipart_receive_req { 343 uint8_t pldm_type; //!< PLDM Type for the MultipartReceive 344 //!< command. 345 uint8_t transfer_opflag; //!< PLDM MultipartReceive operation flag. 346 uint32_t transfer_ctx; //!< Protocol-specifc context for this 347 //!< transfer. 348 uint32_t transfer_handle; //!< handle to identify the part of data to be 349 //!< received. 350 uint32_t section_offset; //!< The start offset for the requested 351 //!< section. 352 uint32_t section_length; //!< The length (in bytes) of the section 353 //!< requested. 354 } __attribute__((packed)); 355 356 /** @struct pldm_multipart_receive_resp 357 * 358 * Structure representing PLDM multipart receive request. 359 */ 360 struct pldm_multipart_receive_resp { 361 uint8_t completion_code; //!< Completion code of the command. 362 uint8_t transfer_flag; //!< PLDM MultipartReceive transfer flag. 363 uint32_t next_transfer_handle; //!< The handle for the next part of 364 //!< data for this section transfer. 365 struct variable_field data; 366 }; 367 368 /** 369 * @brief Populate the PLDM message with the PLDM header.The caller of this API 370 * allocates buffer for the PLDM header when forming the PLDM message. 371 * The buffer is passed to this API to pack the PLDM header. 372 * 373 * @param[in] hdr - Pointer to the PLDM header information 374 * @param[out] msg - Pointer to PLDM message header 375 * 376 * @return 0 on success, otherwise PLDM error codes. 377 * @note Caller is responsible for alloc and dealloc of msg 378 * and hdr params 379 */ 380 uint8_t pack_pldm_header(const struct pldm_header_info *hdr, 381 struct pldm_msg_hdr *msg); 382 383 /** 384 * @brief Unpack the PLDM header from the PLDM message. 385 * 386 * @param[in] msg - Pointer to the PLDM message header 387 * @param[out] hdr - Pointer to the PLDM header information 388 * 389 * @return 0 on success, otherwise PLDM error codes. 390 * @note Caller is responsible for alloc and dealloc of msg 391 * and hdr params 392 */ 393 uint8_t unpack_pldm_header(const struct pldm_msg_hdr *msg, 394 struct pldm_header_info *hdr); 395 396 /* Requester */ 397 398 /* GetPLDMTypes */ 399 400 /** @brief Create a PLDM request message for GetPLDMTypes 401 * 402 * @param[in] instance_id - Message's instance id 403 * @param[in,out] msg - Message will be written to this 404 * @return pldm_completion_codes 405 * @note Caller is responsible for memory alloc and dealloc of param 406 * 'msg.payload' 407 */ 408 int encode_get_types_req(uint8_t instance_id, struct pldm_msg *msg); 409 410 /** @brief Decode a GetPLDMTypes response message 411 * 412 * Note: 413 * * If the return value is not PLDM_SUCCESS, it represents a 414 * transport layer error. 415 * * If the completion_code value is not PLDM_SUCCESS, it represents a 416 * protocol layer error and all the out-parameters are invalid. 417 * 418 * @param[in] msg - Response message 419 * @param[in] payload_length - Length of response message payload 420 * @param[out] completion_code - Pointer to response msg's PLDM completion code 421 * @param[out] types - pointer to array bitfield8_t[8] containing supported 422 * types (MAX_TYPES/8) = 8), as per DSP0240 423 * @return pldm_completion_codes 424 */ 425 int decode_get_types_resp(const struct pldm_msg *msg, size_t payload_length, 426 uint8_t *completion_code, bitfield8_t *types); 427 428 /* GetPLDMCommands */ 429 430 /** @brief Create a PLDM request message for GetPLDMCommands 431 * 432 * @param[in] instance_id - Message's instance id 433 * @param[in] type - PLDM Type 434 * @param[in] version - Version for PLDM Type 435 * @param[in,out] msg - Message will be written to this 436 * @return pldm_completion_codes 437 * @note Caller is responsible for memory alloc and dealloc of param 438 * 'msg.payload' 439 */ 440 int encode_get_commands_req(uint8_t instance_id, uint8_t type, ver32_t version, 441 struct pldm_msg *msg); 442 443 /** @brief Decode a GetPLDMCommands response message 444 * 445 * Note: 446 * * If the return value is not PLDM_SUCCESS, it represents a 447 * transport layer error. 448 * * If the completion_code value is not PLDM_SUCCESS, it represents a 449 * protocol layer error and all the out-parameters are invalid. 450 * 451 * @param[in] msg - Response message 452 * @param[in] payload_length - Length of response message payload 453 * @param[out] completion_code - Pointer to response msg's PLDM completion code 454 * @param[in] commands - pointer to array bitfield8_t[32] containing supported 455 * commands (PLDM_MAX_CMDS_PER_TYPE/8) = 32), as per DSP0240 456 * @return pldm_completion_codes 457 */ 458 int decode_get_commands_resp(const struct pldm_msg *msg, size_t payload_length, 459 uint8_t *completion_code, bitfield8_t *commands); 460 461 /* GetPLDMVersion */ 462 463 /** @brief Create a PLDM request for GetPLDMVersion 464 * 465 * @param[in] instance_id - Message's instance id 466 * @param[in] transfer_handle - Handle to identify PLDM version data transfer. 467 * This handle is ignored by the responder when the 468 * transferop_flag is set to getFirstPart. 469 * @param[in] transfer_opflag - flag to indicate whether it is start of 470 * transfer 471 * @param[in] type - PLDM Type for which version is requested 472 * @param[in,out] msg - Message will be written to this 473 * @return pldm_completion_codes 474 * @note Caller is responsible for memory alloc and dealloc of param 475 * 'msg.payload' 476 */ 477 int encode_get_version_req(uint8_t instance_id, uint32_t transfer_handle, 478 uint8_t transfer_opflag, uint8_t type, 479 struct pldm_msg *msg); 480 481 /** @brief Decode a GetPLDMVersion response message 482 * 483 * Note: 484 * * If the return value is not PLDM_SUCCESS, it represents a 485 * transport layer error. 486 * * If the completion_code value is not PLDM_SUCCESS, it represents a 487 * protocol layer error and all the out-parameters are invalid. 488 * 489 * @param[in] msg - Response message 490 * @param[in] payload_length - Length of response message payload 491 * @param[out] completion_code - Pointer to response msg's PLDM completion code 492 * @param[out] next_transfer_handle - the next handle for the next part of data 493 * @param[out] transfer_flag - flag to indicate the part of data 494 * @return pldm_completion_codes 495 */ 496 int decode_get_version_resp(const struct pldm_msg *msg, size_t payload_length, 497 uint8_t *completion_code, 498 uint32_t *next_transfer_handle, 499 uint8_t *transfer_flag, ver32_t *version); 500 501 /* GetTID */ 502 503 /** @brief Decode a GetTID response message 504 * 505 * Note: 506 * * If the return value is not PLDM_SUCCESS, it represents a 507 * transport layer error. 508 * * If the completion_code value is not PLDM_SUCCESS, it represents a 509 * protocol layer error and all the out-parameters are invalid. 510 * 511 * @param[in] msg - Response message 512 * @param[in] payload_length - Length of response message payload 513 * @param[out] completion_code - Pointer to response msg's PLDM completion code 514 * @param[out] tid - Pointer to the terminus id 515 * @return pldm_completion_codes 516 */ 517 int decode_get_tid_resp(const struct pldm_msg *msg, size_t payload_length, 518 uint8_t *completion_code, uint8_t *tid); 519 520 /* Responder */ 521 522 /* GetPLDMTypes */ 523 524 /** @brief Create a PLDM response message for GetPLDMTypes 525 * 526 * @param[in] instance_id - Message's instance id 527 * @param[in] completion_code - PLDM completion code 528 * @param[in] types - pointer to array bitfield8_t[8] containing supported 529 * types (MAX_TYPES/8) = 8), as per DSP0240 530 * @param[in,out] msg - Message will be written to this 531 * @return pldm_completion_codes 532 * @note Caller is responsible for memory alloc and dealloc of param 533 * 'msg.payload' 534 */ 535 int encode_get_types_resp(uint8_t instance_id, uint8_t completion_code, 536 const bitfield8_t *types, struct pldm_msg *msg); 537 538 /* GetPLDMCommands */ 539 540 /** @brief Decode GetPLDMCommands' request data 541 * 542 * @param[in] msg - Request message 543 * @param[in] payload_length - Length of request message payload 544 * @param[out] type - PLDM Type 545 * @param[out] version - Version for PLDM Type 546 * @return pldm_completion_codes 547 */ 548 int decode_get_commands_req(const struct pldm_msg *msg, size_t payload_length, 549 uint8_t *type, ver32_t *version); 550 551 /** @brief Create a PLDM response message for GetPLDMCommands 552 * 553 * @param[in] instance_id - Message's instance id 554 * @param[in] completion_code - PLDM completion code 555 * @param[in] commands - pointer to array bitfield8_t[32] containing supported 556 * commands (PLDM_MAX_CMDS_PER_TYPE/8) = 32), as per DSP0240 557 * @param[in,out] msg - Message will be written to this 558 * @return pldm_completion_codes 559 * @note Caller is responsible for memory alloc and dealloc of param 560 * 'msg.payload' 561 */ 562 int encode_get_commands_resp(uint8_t instance_id, uint8_t completion_code, 563 const bitfield8_t *commands, struct pldm_msg *msg); 564 565 /* GetPLDMVersion */ 566 567 /** @brief Create a PLDM response for GetPLDMVersion 568 * 569 * @param[in] instance_id - Message's instance id 570 * @param[in] completion_code - PLDM completion code 571 * @param[in] next_transfer_handle - Handle to identify next portion of 572 * data transfer 573 * @param[in] transfer_flag - Represents the part of transfer 574 * @param[in] version_data - the version data 575 * @param[in] version_size - size of version data 576 * @param[in,out] msg - Message will be written to this 577 * @return pldm_completion_codes 578 * @note Caller is responsible for memory alloc and dealloc of param 579 * 'msg.payload' 580 */ 581 int encode_get_version_resp(uint8_t instance_id, uint8_t completion_code, 582 uint32_t next_transfer_handle, 583 uint8_t transfer_flag, const ver32_t *version_data, 584 size_t version_size, struct pldm_msg *msg); 585 586 /** @brief Decode a GetPLDMVersion request message 587 * 588 * @param[in] msg - Request message 589 * @param[in] payload_length - length of request message payload 590 * @param[out] transfer_handle - the handle of data 591 * @param[out] transfer_opflag - Transfer Flag 592 * @param[out] type - PLDM type for which version is requested 593 * @return pldm_completion_codes 594 */ 595 int decode_get_version_req(const struct pldm_msg *msg, size_t payload_length, 596 uint32_t *transfer_handle, uint8_t *transfer_opflag, 597 uint8_t *type); 598 599 /* Requester */ 600 601 /* GetTID */ 602 603 /** @brief Create a PLDM request message for GetTID 604 * 605 * @param[in] instance_id - Message's instance id 606 * @param[in,out] msg - Message will be written to this 607 * @return pldm_completion_codes 608 * @note Caller is responsible for memory alloc and dealloc of param 609 * 'msg.payload' 610 */ 611 int encode_get_tid_req(uint8_t instance_id, struct pldm_msg *msg); 612 613 /** @brief Create a PLDM response message for GetTID 614 * 615 * @param[in] instance_id - Message's instance id 616 * @param[in] completion_code - PLDM completion code 617 * @param[in] tid - Terminus ID 618 * @param[in,out] msg - Message will be written to this 619 * @return pldm_completion_codes 620 * @note Caller is responsible for memory alloc and dealloc of param 621 * 'msg.payload' 622 */ 623 int encode_get_tid_resp(uint8_t instance_id, uint8_t completion_code, 624 uint8_t tid, struct pldm_msg *msg); 625 626 /** @brief Create a PLDM request message for SetTID 627 * 628 * @param[in] instance_id - Message's instance id 629 * @param[in] tid - Terminus ID 630 * @param[in,out] msg - Message will be written to this 631 * @return pldm_completion_codes 632 * @note Caller is responsible for memory alloc and dealloc of param 633 * 'msg.payload' 634 */ 635 int encode_set_tid_req(uint8_t instance_id, uint8_t tid, struct pldm_msg *msg); 636 637 /* Responder */ 638 639 /* MultipartRecieve */ 640 641 /** @brief Decode a PLDM MultipartReceive request message 642 * 643 * @param[in] msg - Request message 644 * @param[in] payload_length - length of request message payload 645 * @param[out] pldm_type - PLDM type for which version is requested 646 * @param[out] transfer_opflag - Transfer Flag 647 * @param[out] transfer_ctx - The context of the packet 648 * @param[out] transfer_handle - The handle of data 649 * @param[out] section_offset - The start of the requested section 650 * @param[out] section_length - The length of the requested section 651 * @return pldm_completion_codes 652 */ 653 int decode_multipart_receive_req(const struct pldm_msg *msg, 654 size_t payload_length, uint8_t *pldm_type, 655 uint8_t *transfer_opflag, 656 uint32_t *transfer_ctx, 657 uint32_t *transfer_handle, 658 uint32_t *section_offset, 659 uint32_t *section_length); 660 661 /** @brief Encode a PLDM MultipartReceive request message 662 * 663 * @param[in] instance_id - Message's instance id 664 * @param[in] req - The pointer to the request message to be encoded 665 * @param[in,out] msg - Message will be written to this 666 * @param[in] payload_length - length of request message payload 667 * @return 0 on success 668 * -EINVAL if the input parameters' memory are not allocated, 669 * or message type or instance in request header is invalid 670 * -ENOMSG if the PLDM type in the request header is invalid 671 * -EOVERFLOW if the input message length is invalid 672 */ 673 int encode_base_multipart_receive_req( 674 uint8_t instance_id, const struct pldm_multipart_receive_req *req, 675 struct pldm_msg *msg, size_t payload_length); 676 677 /** @brief Decode a PLDM MultipartReceive response message 678 * 679 * @param[in] msg - Response message 680 * @param[in] payload_length - length of request message payload 681 * @param[out] resp - pointer to the decoded response message, 682 * excluding the data integrity checksum 683 * @param[out] data_integrity_checksum - The checksum of data field 684 * of the decoded response message 685 * @return 0 on success 686 * -EINVAL if the input parameters' memory are not allocated 687 * -EOVERFLOW if the input message buffer is too short for the output 688 * response struct 689 * -EBADMSG if the input message buffer is too large for the output 690 * response struct 691 * @note Caller is responsible for memory alloc and dealloc of param 692 * 'msg.payload' 693 */ 694 int decode_base_multipart_receive_resp(const struct pldm_msg *msg, 695 size_t payload_length, 696 struct pldm_multipart_receive_resp *resp, 697 uint32_t *data_integrity_checksum); 698 699 /** @brief Create a PLDM response message containing only cc 700 * 701 * @param[in] instance_id - Message's instance id 702 * @param[in] type - PLDM Type 703 * @param[in] command - PLDM Command 704 * @param[in] cc - PLDM Completion Code 705 * @param[out] msg - Message will be written to this 706 * @return pldm_completion_codes 707 */ 708 int encode_cc_only_resp(uint8_t instance_id, uint8_t type, uint8_t command, 709 uint8_t cc, struct pldm_msg *msg); 710 711 /** @brief Create a PLDM message only with the header 712 * 713 * @param[in] msg_type - PLDM message type 714 * @param[in] instance_id - Message's instance id 715 * @param[in] pldm_type - PLDM Type 716 * @param[in] command - PLDM Command 717 * @param[out] msg - Message will be written to this 718 * 719 * @return pldm_completion_codes 720 */ 721 int encode_pldm_header_only(uint8_t msg_type, uint8_t instance_id, 722 uint8_t pldm_type, uint8_t command, 723 struct pldm_msg *msg); 724 725 #ifdef __cplusplus 726 } 727 #endif 728 729 #endif /* BASE_H */ 730