diff --git a/RedfishPkg/Include/Library/RedfishDebugLib.h b/RedfishPkg/Include/Library/RedfishDebugLib.h new file mode 100644 index 0000000000..21f01353ed --- /dev/null +++ b/RedfishPkg/Include/Library/RedfishDebugLib.h @@ -0,0 +1,90 @@ +/** @file + This file defines the Redfish debug library interface. + + Copyright (c) 2023, NVIDIA CORPORATION & AFFILIATES. All rights reserved. + + SPDX-License-Identifier: BSD-2-Clause-Patent + +**/ + +#ifndef REDFISH_DEBUG_LIB_H_ +#define REDFISH_DEBUG_LIB_H_ + +#include +#include +#include + +#define DEBUG_REDFISH_NETWORK DEBUG_INFO ///< Debug error level for Redfish networking function + +/** + + This function dump the Json string in given error level. + + @param[in] ErrorLevel DEBUG macro error level + @param[in] JsonValue Json value to dump. + + @retval EFI_SUCCESS Json string is printed. + @retval Others Errors occur. + +**/ +EFI_STATUS +DumpJsonValue ( + IN UINTN ErrorLevel, + IN EDKII_JSON_VALUE JsonValue + ); + +/** + + This function dump the status code, header and body in given + Redfish payload. + + @param[in] ErrorLevel DEBUG macro error level + @param[in] Payload Redfish payload to dump + + @retval EFI_SUCCESS Redfish payload is printed. + @retval Others Errors occur. + +**/ +EFI_STATUS +DumpRedfishPayload ( + IN UINTN ErrorLevel, + IN REDFISH_PAYLOAD Payload + ); + +/** + + This function dump the status code, header and body in given + Redfish response. + + @param[in] Message Message string + @param[in] ErrorLevel DEBUG macro error level + @param[in] Response Redfish response to dump + + @retval EFI_SUCCESS Redfish response is printed. + @retval Others Errors occur. + +**/ +EFI_STATUS +DumpRedfishResponse ( + IN CONST CHAR8 *Message, + IN UINTN ErrorLevel, + IN REDFISH_RESPONSE *Response + ); + +/** + + This function dump the HTTP status code. + + @param[in] ErrorLevel DEBUG macro error level + @param[in] HttpStatusCode HTTP status code + + @retval EFI_SUCCESS HTTP status code is printed + +**/ +EFI_STATUS +DumpHttpStatusCode ( + IN UINTN ErrorLevel, + IN EFI_HTTP_STATUS_CODE HttpStatusCode + ); + +#endif diff --git a/RedfishPkg/Library/RedfishDebugLib/RedfishDebugLib.c b/RedfishPkg/Library/RedfishDebugLib/RedfishDebugLib.c new file mode 100644 index 0000000000..6f1d9de25e --- /dev/null +++ b/RedfishPkg/Library/RedfishDebugLib/RedfishDebugLib.c @@ -0,0 +1,229 @@ +/** @file + Redfish debug library to debug Redfish application. + + Copyright (c) 2023, NVIDIA CORPORATION & AFFILIATES. All rights reserved. + + SPDX-License-Identifier: BSD-2-Clause-Patent + +**/ + +#include + +#include +#include +#include +#include +#include + +#ifndef IS_EMPTY_STRING +#define IS_EMPTY_STRING(a) ((a) == NULL || (a)[0] == '\0') +#endif + +#define REDFISH_JSON_STRING_LENGTH 200 +#define REDFISH_JSON_OUTPUT_FORMAT (EDKII_JSON_COMPACT | EDKII_JSON_INDENT(2)) + +/** + + This function dump the Json string in given error level. + + @param[in] ErrorLevel DEBUG macro error level + @param[in] JsonValue Json value to dump. + + @retval EFI_SUCCESS Json string is printed. + @retval Others Errors occur. + +**/ +EFI_STATUS +DumpJsonValue ( + IN UINTN ErrorLevel, + IN EDKII_JSON_VALUE JsonValue + ) +{ + CHAR8 *String; + CHAR8 *Runner; + CHAR8 Buffer[REDFISH_JSON_STRING_LENGTH + 1]; + UINTN StrLen; + UINTN Count; + UINTN Index; + + if (JsonValue == NULL) { + return EFI_INVALID_PARAMETER; + } + + String = JsonDumpString (JsonValue, REDFISH_JSON_OUTPUT_FORMAT); + if (String == NULL) { + return EFI_UNSUPPORTED; + } + + StrLen = AsciiStrLen (String); + if (StrLen == 0) { + return EFI_UNSUPPORTED; + } + + Count = StrLen / REDFISH_JSON_STRING_LENGTH; + Runner = String; + for (Index = 0; Index < Count; Index++) { + AsciiStrnCpyS (Buffer, (REDFISH_JSON_STRING_LENGTH + 1), Runner, REDFISH_JSON_STRING_LENGTH); + Buffer[REDFISH_JSON_STRING_LENGTH] = '\0'; + DEBUG ((ErrorLevel, "%a", Buffer)); + Runner += REDFISH_JSON_STRING_LENGTH; + } + + Count = StrLen % REDFISH_JSON_STRING_LENGTH; + if (Count > 0) { + DEBUG ((ErrorLevel, "%a", Runner)); + } + + DEBUG ((ErrorLevel, "\n")); + + FreePool (String); + return EFI_SUCCESS; +} + +/** + + This function dump the status code, header and body in given + Redfish payload. + + @param[in] ErrorLevel DEBUG macro error level + @param[in] Payload Redfish payload to dump + + @retval EFI_SUCCESS Redfish payload is printed. + @retval Others Errors occur. + +**/ +EFI_STATUS +DumpRedfishPayload ( + IN UINTN ErrorLevel, + IN REDFISH_PAYLOAD Payload + ) +{ + EDKII_JSON_VALUE JsonValue; + + if (Payload == NULL) { + return EFI_INVALID_PARAMETER; + } + + JsonValue = RedfishJsonInPayload (Payload); + if (JsonValue != NULL) { + DEBUG ((ErrorLevel, "Payload:\n")); + DumpJsonValue (ErrorLevel, JsonValue); + } + + return EFI_SUCCESS; +} + +/** + + This function dump the HTTP status code. + + @param[in] ErrorLevel DEBUG macro error level + @param[in] HttpStatusCode HTTP status code + + @retval EFI_SUCCESS HTTP status code is printed + +**/ +EFI_STATUS +DumpHttpStatusCode ( + IN UINTN ErrorLevel, + IN EFI_HTTP_STATUS_CODE HttpStatusCode + ) +{ + switch (HttpStatusCode) { + case HTTP_STATUS_100_CONTINUE: + DEBUG ((ErrorLevel, "Status code: 100 CONTINUE\n")); + break; + case HTTP_STATUS_200_OK: + DEBUG ((ErrorLevel, "Status code: 200 OK\n")); + break; + case HTTP_STATUS_201_CREATED: + DEBUG ((ErrorLevel, "Status code: 201 CREATED\n")); + break; + case HTTP_STATUS_202_ACCEPTED: + DEBUG ((ErrorLevel, "Status code: 202 ACCEPTED\n")); + break; + case HTTP_STATUS_304_NOT_MODIFIED: + DEBUG ((ErrorLevel, "Status code: 304 NOT MODIFIED\n")); + break; + case HTTP_STATUS_400_BAD_REQUEST: + DEBUG ((ErrorLevel, "Status code: 400 BAD REQUEST\n")); + break; + case HTTP_STATUS_401_UNAUTHORIZED: + DEBUG ((ErrorLevel, "Status code: 401 UNAUTHORIZED\n")); + break; + case HTTP_STATUS_403_FORBIDDEN: + DEBUG ((ErrorLevel, "Status code: 403 FORBIDDEN\n")); + break; + case HTTP_STATUS_404_NOT_FOUND: + DEBUG ((ErrorLevel, "Status code: 404 NOT FOUND\n")); + break; + case HTTP_STATUS_405_METHOD_NOT_ALLOWED: + DEBUG ((ErrorLevel, "Status code: 405 METHOD NOT ALLOWED\n")); + break; + case HTTP_STATUS_500_INTERNAL_SERVER_ERROR: + DEBUG ((ErrorLevel, "Status code: 500 INTERNAL SERVER ERROR\n")); + break; + default: + DEBUG ((ErrorLevel, "Status code: 0x%x\n", HttpStatusCode)); + break; + } + + return EFI_SUCCESS; +} + +/** + + This function dump the status code, header and body in given + Redfish response. + + @param[in] Message Message string + @param[in] ErrorLevel DEBUG macro error level + @param[in] Response Redfish response to dump + + @retval EFI_SUCCESS Redfish response is printed. + @retval Others Errors occur. + +**/ +EFI_STATUS +DumpRedfishResponse ( + IN CONST CHAR8 *Message, + IN UINTN ErrorLevel, + IN REDFISH_RESPONSE *Response + ) +{ + UINTN Index; + + if (Response == NULL) { + return EFI_INVALID_PARAMETER; + } + + if (!IS_EMPTY_STRING (Message)) { + DEBUG ((ErrorLevel, "%a\n", Message)); + } + + // + // status code + // + if (Response->StatusCode != NULL) { + DumpHttpStatusCode (ErrorLevel, *(Response->StatusCode)); + } + + // + // header + // + if (Response->HeaderCount > 0) { + DEBUG ((ErrorLevel, "Header: %d\n", Response->HeaderCount)); + for (Index = 0; Index < Response->HeaderCount; Index++) { + DEBUG ((ErrorLevel, " %a: %a\n", Response->Headers[Index].FieldName, Response->Headers[Index].FieldValue)); + } + } + + // + // Body + // + if (Response->Payload != NULL) { + DumpRedfishPayload (ErrorLevel, Response->Payload); + } + + return EFI_SUCCESS; +} diff --git a/RedfishPkg/Library/RedfishDebugLib/RedfishDebugLib.inf b/RedfishPkg/Library/RedfishDebugLib/RedfishDebugLib.inf new file mode 100644 index 0000000000..048d27c6dc --- /dev/null +++ b/RedfishPkg/Library/RedfishDebugLib/RedfishDebugLib.inf @@ -0,0 +1,39 @@ +## @file +# INF file for Redfish debug library. +# +# Copyright (c) 2023, NVIDIA CORPORATION & AFFILIATES. All rights reserved. +# +# SPDX-License-Identifier: BSD-2-Clause-Patent +# +## + +[Defines] + INF_VERSION = 0x00010006 + BASE_NAME = RedfishDebugLib + FILE_GUID = 7F64C79F-ABD0-4446-86B5-2C1AE36168AD + MODULE_TYPE = DXE_DRIVER + VERSION_STRING = 1.0 + LIBRARY_CLASS = RedfishDebugLib| DXE_DRIVER UEFI_DRIVER + +# +# VALID_ARCHITECTURES = IA32 X64 EBC +# + +[Sources] + RedfishDebugLib.c + +[Packages] + MdePkg/MdePkg.dec + MdeModulePkg/MdeModulePkg.dec + RedfishPkg/RedfishPkg.dec + +[LibraryClasses] + BaseLib + DebugLib + JsonLib + MemoryAllocationLib + RedfishLib + UefiLib + +[Depex] + TRUE diff --git a/RedfishPkg/RedfishLibs.dsc.inc b/RedfishPkg/RedfishLibs.dsc.inc index 56950b711f..84f52d4b27 100644 --- a/RedfishPkg/RedfishLibs.dsc.inc +++ b/RedfishPkg/RedfishLibs.dsc.inc @@ -6,6 +6,7 @@ # of EDKII network library classes. # # (C) Copyright 2021 Hewlett Packard Enterprise Development LP
+# Copyright (c) 2023, NVIDIA CORPORATION & AFFILIATES. All rights reserved. # # SPDX-License-Identifier: BSD-2-Clause-Patent # @@ -17,5 +18,6 @@ RedfishCrtLib|RedfishPkg/PrivateLibrary/RedfishCrtLib/RedfishCrtLib.inf JsonLib|RedfishPkg/Library/JsonLib/JsonLib.inf RedfishLib|RedfishPkg/PrivateLibrary/RedfishLib/RedfishLib.inf + RedfishDebugLib|RedfishPkg/Library/RedfishDebugLib/RedfishDebugLib.inf !endif diff --git a/RedfishPkg/RedfishPkg.dec b/RedfishPkg/RedfishPkg.dec index 130e7ec260..53e52c2b00 100644 --- a/RedfishPkg/RedfishPkg.dec +++ b/RedfishPkg/RedfishPkg.dec @@ -4,6 +4,7 @@ # Copyright (c) 2019, Intel Corporation. All rights reserved.
# (C) Copyright 2021 Hewlett Packard Enterprise Development LP
# Copyright (c) 2023, American Megatrends International LLC. +# Copyright (c) 2023, NVIDIA CORPORATION & AFFILIATES. All rights reserved. # # SPDX-License-Identifier: BSD-2-Clause-Patent ## @@ -55,6 +56,10 @@ # RedfishContentCodingLib|Include/Library/RedfishContentCodingLib.h + ## @libraryclass Redfish Debug Library + # Library provides Redfish debug functions. + RedfishDebugLib|Include/Library/RedfishDebugLib.h + [LibraryClasses.Common.Private] ## @libraryclass Provides the private C runtime library functions. # CRT library is currently used by edk2 JsonLib (open source diff --git a/RedfishPkg/RedfishPkg.dsc b/RedfishPkg/RedfishPkg.dsc index 16139146ff..cf25b63cc2 100644 --- a/RedfishPkg/RedfishPkg.dsc +++ b/RedfishPkg/RedfishPkg.dsc @@ -58,5 +58,6 @@ RedfishPkg/PrivateLibrary/RedfishCrtLib/RedfishCrtLib.inf RedfishPkg/Library/JsonLib/JsonLib.inf RedfishPkg/PrivateLibrary/RedfishLib/RedfishLib.inf + RedfishPkg/Library/RedfishDebugLib/RedfishDebugLib.inf !include RedfishPkg/Redfish.dsc.inc diff --git a/RedfishPkg/RedfishRestExDxe/RedfishRestExDxe.inf b/RedfishPkg/RedfishRestExDxe/RedfishRestExDxe.inf index 2f7a2188e8..64e6343bfb 100644 --- a/RedfishPkg/RedfishRestExDxe/RedfishRestExDxe.inf +++ b/RedfishPkg/RedfishRestExDxe/RedfishRestExDxe.inf @@ -4,6 +4,7 @@ # Copyright (c) 2019, Intel Corporation. All rights reserved.
# (C) Copyright 2020 Hewlett Packard Enterprise Development LP
# Copyright (c) 2023, American Megatrends International LLC. +# Copyright (c) 2023, NVIDIA CORPORATION & AFFILIATES. All rights reserved. # # SPDX-License-Identifier: BSD-2-Clause-Patent # @@ -44,6 +45,7 @@ PrintLib MemoryAllocationLib NetLib + RedfishDebugLib UefiLib UefiBootServicesTableLib UefiDriverEntryPoint diff --git a/RedfishPkg/RedfishRestExDxe/RedfishRestExInternal.h b/RedfishPkg/RedfishRestExDxe/RedfishRestExInternal.h index a687c4ddb1..bca679e2cc 100644 --- a/RedfishPkg/RedfishRestExDxe/RedfishRestExInternal.h +++ b/RedfishPkg/RedfishRestExDxe/RedfishRestExInternal.h @@ -3,6 +3,7 @@ Copyright (c) 2019, Intel Corporation. All rights reserved.
(C) Copyright 2019-2020 Hewlett Packard Enterprise Development LP
+ Copyright (c) 2023, NVIDIA CORPORATION & AFFILIATES. All rights reserved. SPDX-License-Identifier: BSD-2-Clause-Patent @@ -21,6 +22,7 @@ #include #include #include +#include #include #include #include diff --git a/RedfishPkg/RedfishRestExDxe/RedfishRestExProtocol.c b/RedfishPkg/RedfishRestExDxe/RedfishRestExProtocol.c index 1c3deab09a..3722e1f795 100644 --- a/RedfishPkg/RedfishRestExDxe/RedfishRestExProtocol.c +++ b/RedfishPkg/RedfishRestExDxe/RedfishRestExProtocol.c @@ -4,6 +4,7 @@ Copyright (c) 2019, Intel Corporation. All rights reserved.
(C) Copyright 2020 Hewlett Packard Enterprise Development LP
Copyright (c) 2023, American Megatrends International LLC. + Copyright (c) 2023, NVIDIA CORPORATION & AFFILIATES. All rights reserved. SPDX-License-Identifier: BSD-2-Clause-Patent @@ -90,12 +91,12 @@ RedfishRestExSendReceive ( MediaPresent = TRUE; NetLibDetectMedia (Instance->Service->ControllerHandle, &MediaPresent); if (!MediaPresent) { - DEBUG ((DEBUG_INFO, "RedfishRestExSendReceive(): No MediaPresent.\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "RedfishRestExSendReceive(): No MediaPresent.\n")); return EFI_NO_MEDIA; } - DEBUG ((DEBUG_INFO, "\nRedfishRestExSendReceive():\n")); - DEBUG ((DEBUG_INFO, "*** Perform HTTP Request Method - %d, URL: %s\n", RequestMessage->Data.Request->Method, RequestMessage->Data.Request->Url)); + DEBUG ((DEBUG_REDFISH_NETWORK, "\nRedfishRestExSendReceive():\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "*** Perform HTTP Request Method - %d, URL: %s\n", RequestMessage->Data.Request->Method, RequestMessage->Data.Request->Url)); if (FixedPcdGetBool (PcdRedfishRestExChunkRequestMode)) { // @@ -215,7 +216,7 @@ ReSendRequest:; goto ON_EXIT; } - DEBUG ((DEBUG_INFO, "Receiving HTTP response and headers...\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "Receiving HTTP response and headers...\n")); Status = RedfishCheckHttpReceiveStatus ( Instance, HttpIoRecvResponse ( @@ -239,12 +240,12 @@ ReSendRequest:; RequestMessage->HeaderCount--; // Minus one header count for "Expect". } - DEBUG ((DEBUG_INFO, "HTTP Response StatusCode - %d:", ResponseData->Response.StatusCode)); + DEBUG ((DEBUG_REDFISH_NETWORK, "HTTP Response StatusCode - %d:", ResponseData->Response.StatusCode)); if (ResponseData->Response.StatusCode == HTTP_STATUS_200_OK) { - DEBUG ((DEBUG_INFO, "HTTP_STATUS_200_OK\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "HTTP_STATUS_200_OK\n")); if (FixedPcdGetBool (PcdRedfishRestExChunkRequestMode) && (SendChunkProcess == HttpIoSendChunkHeaderZeroContent)) { - DEBUG ((DEBUG_INFO, "This is chunk transfer, start to send all chunks - %d.", ResponseData->Response.StatusCode)); + DEBUG ((DEBUG_REDFISH_NETWORK, "This is chunk transfer, start to send all chunks - %d.", ResponseData->Response.StatusCode)); SendChunkProcess++; goto ReSendRequest; } @@ -261,7 +262,7 @@ ReSendRequest:; } else if (ResponseData->Response.StatusCode == HTTP_STATUS_202_ACCEPTED) { DEBUG ((DEBUG_INFO, "HTTP_STATUS_202_ACCEPTED\n")); } else if (ResponseData->Response.StatusCode == HTTP_STATUS_413_REQUEST_ENTITY_TOO_LARGE) { - DEBUG ((DEBUG_INFO, "HTTP_STATUS_413_REQUEST_ENTITY_TOO_LARGE\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "HTTP_STATUS_413_REQUEST_ENTITY_TOO_LARGE\n")); Status = EFI_BAD_BUFFER_SIZE; goto ON_EXIT; @@ -271,25 +272,25 @@ ReSendRequest:; Status = EFI_ACCESS_DENIED; goto ON_EXIT; } else if (ResponseData->Response.StatusCode == HTTP_STATUS_400_BAD_REQUEST) { - DEBUG ((DEBUG_INFO, "HTTP_STATUS_400_BAD_REQUEST\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "HTTP_STATUS_400_BAD_REQUEST\n")); if (FixedPcdGetBool (PcdRedfishRestExChunkRequestMode) && (SendChunkProcess == HttpIoSendChunkHeaderZeroContent)) { - DEBUG ((DEBUG_INFO, "Bad request may caused by zero length chunk. Try to send all chunks...\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "Bad request may caused by zero length chunk. Try to send all chunks...\n")); SendChunkProcess++; goto ReSendRequest; } } else if (ResponseData->Response.StatusCode == HTTP_STATUS_100_CONTINUE) { - DEBUG ((DEBUG_INFO, "HTTP_STATUS_100_CONTINUE\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "HTTP_STATUS_100_CONTINUE\n")); if (FixedPcdGetBool (PcdRedfishRestExChunkRequestMode) && (SendChunkProcess == HttpIoSendChunkHeaderZeroContent)) { // // We get HTTP_STATUS_100_CONTINUE to send the body using chunk transfer. // - DEBUG ((DEBUG_INFO, "HTTP_STATUS_100_CONTINUE for chunk transfer...\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "HTTP_STATUS_100_CONTINUE for chunk transfer...\n")); SendChunkProcess++; goto ReSendRequest; } if (FixedPcdGetBool (PcdRedfishRestExChunkRequestMode) && (SendNonChunkProcess == HttpIoSendNonChunkHeaderZeroContent)) { - DEBUG ((DEBUG_INFO, "HTTP_STATUS_100_CONTINUE for non chunk transfer...\n")); + DEBUG ((DEBUG_REDFISH_NETWORK, "HTTP_STATUS_100_CONTINUE for non chunk transfer...\n")); SendNonChunkProcess++; goto ReSendRequest; } @@ -313,6 +314,7 @@ ReSendRequest:; } } else { DEBUG ((DEBUG_ERROR, "This HTTP Status is not handled!\n")); + DumpHttpStatusCode (DEBUG_REDFISH_NETWORK, ResponseData->Response.StatusCode); Status = EFI_UNSUPPORTED; goto ON_EXIT; } @@ -426,10 +428,10 @@ ReSendRequest:; TotalReceivedSize += ResponseData->BodyLength; } - DEBUG ((DEBUG_INFO, "Total of length of Response :%d\n", TotalReceivedSize)); + DEBUG ((DEBUG_REDFISH_NETWORK, "Total of length of Response :%d\n", TotalReceivedSize)); } - DEBUG ((DEBUG_INFO, "RedfishRestExSendReceive()- EFI_STATUS: %r\n", Status)); + DEBUG ((DEBUG_REDFISH_NETWORK, "RedfishRestExSendReceive()- EFI_STATUS: %r\n", Status)); ON_EXIT: