[AMD Official Use Only - General] Reviewed-by: Abner Chang <abner.ch...@amd.com>
> -----Original Message----- > From: Nickle Wang <nick...@nvidia.com> > Sent: Wednesday, May 10, 2023 4:24 PM > To: devel@edk2.groups.io > Cc: Chang, Abner <abner.ch...@amd.com>; Igor Kulchytskyy > <ig...@ami.com> > Subject: [edk2-redfish-client][PATCH 2/4] RedfishClientPkg: Update Redfish > feature core driver > > Caution: This message originated from an External Source. Use proper > caution when opening attachments, clicking links, or responding. > > > Update Redfish feature core driver to support Redfish resource with multiple > parents. A resource may be presented in different resource and the link in > different resource point to the same location. Also add interchange data > interface in feature core driver so feature core driver can talk to feature > drivers directly. > > Signed-off-by: Nickle Wang <nick...@nvidia.com> > Cc: Abner Chang <abner.ch...@amd.com> > Cc: Igor Kulchytskyy <ig...@ami.com> > --- > .../RedfishFeatureCoreDxe.inf | 5 +- > .../Include/Protocol/EdkIIRedfishFeature.h | 20 +- > .../RedfishFeatureCoreDxe.h | 14 +- > .../RedfishFeatureCoreDxe.c | 309 +++++++++++++++--- > 4 files changed, 290 insertions(+), 58 deletions(-) > > diff --git > a/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.inf > b/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.inf > index 5a2cd7fe..ddcf9910 100644 > --- a/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.inf > +++ b/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.inf > @@ -3,7 +3,7 @@ > # EdkIIRedfishFeatureCoreProtocol to EDK2 Redfish Feature # drivers for > the registration. > # > -# (C) Copyright 2021 Hewlett Packard Enterprise Development LP<BR> > +# (C) Copyright 2021-2022 Hewlett Packard Enterprise Development > +LP<BR> > # SPDX-License-Identifier: BSD-2-Clause-Patent # ## @@ -27,6 +27,7 @@ > [Packages] > MdePkg/MdePkg.dec > MdeModulePkg/MdeModulePkg.dec > + RedfishPkg/RedfishPkg.dec > RedfishClientPkg/RedfishClientPkg.dec > > [LibraryClasses] > @@ -35,6 +36,8 @@ > DebugLib > MemoryAllocationLib > PrintLib > + RedfishEventLib > + RedfishFeatureUtilityLib > UefiBootServicesTableLib > UefiDriverEntryPoint > UefiLib > diff --git a/RedfishClientPkg/Include/Protocol/EdkIIRedfishFeature.h > b/RedfishClientPkg/Include/Protocol/EdkIIRedfishFeature.h > index 04b65a06..b8c09d09 100644 > --- a/RedfishClientPkg/Include/Protocol/EdkIIRedfishFeature.h > +++ b/RedfishClientPkg/Include/Protocol/EdkIIRedfishFeature.h > @@ -1,7 +1,7 @@ > /** @file > This file defines the EDKII_REDFISH_FEATURE_PROTOCOL interface. > > - (C) Copyright 2021 Hewlett Packard Enterprise Development LP<BR> > + (C) Copyright 2021-2022 Hewlett Packard Enterprise Development LP<BR> > > SPDX-License-Identifier: BSD-2-Clause-Patent > > @@ -10,6 +10,8 @@ > #ifndef EDKII_REDFISH_FEATURE_H_ > #define EDKII_REDFISH_FEATURE_H_ > > +#include <Protocol/EdkIIRedfishInterchangeData.h> > + > typedef struct _EDKII_REDFISH_FEATURE_PROTOCOL > EDKII_REDFISH_FEATURE_PROTOCOL; > > #define EDKII_REDFISH_FEATURE_PROTOCOL_GUID \ @@ -23,25 +25,13 > @@ typedef enum { > CallbackActionMax > } FEATURE_CALLBACK_ACTION; > > -typedef enum { > - InformationTypeNone = 0, ///< Invalid information. > - InformationTypeCollectionMemberUri, ///< URI to the new created > collection member. > - InformationTypeMax > -} FEATURE_RETURNED_INFORMATION_TYPE; > - > -typedef struct { > - FEATURE_RETURNED_INFORMATION_TYPE Type; > -} FEATURE_RETURNED_INFORMATION; > - > /** > The callback function provided by Redfish Feature driver. > > @param[in] This Pointer to > EDKII_REDFISH_FEATURE_PROTOCOL > instance. > @param[in] FeatureAction The action Redfish feature driver should > take. > @param[in] Context The context of Redfish feature driver. > - @param[in,out] InformationReturned The pointer to retrive the pointer to > - FEATURE_RETURNED_INFOMATION. The memory > block > of this > - information should be freed by caller. > + @param[in,out] ExchangeInformation The pointer to > RESOURCE_INFORMATION_EXCHANGE. > > @retval EFI_SUCCESS Redfish feature driver callback is > executed > successfully. > @retval Others Some errors happened. > @@ -53,7 +43,7 @@ EFI_STATUS > IN EDKII_REDFISH_FEATURE_PROTOCOL *This, > IN FEATURE_CALLBACK_ACTION FeatureAction, > IN VOID *Context, > - IN OUT FEATURE_RETURNED_INFORMATION **InformationReturned > + IN OUT RESOURCE_INFORMATION_EXCHANGE *ExchangeInformation > ); > > /** > diff --git > a/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.h > b/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.h > index 71432a1a..ff3c787a 100644 > --- a/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.h > +++ b/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.h > @@ -1,7 +1,7 @@ > /** @file > Definitions of RedfishFeatureCoreDxe > > - (C) Copyright 2021 Hewlett Packard Enterprise Development LP<BR> > + (C) Copyright 2021-2022 Hewlett Packard Enterprise Development LP<BR> > > SPDX-License-Identifier: BSD-2-Clause-Patent > > @@ -17,13 +17,17 @@ > #include <Library/BaseMemoryLib.h> > #include <Library/DebugLib.h> > #include <Library/MemoryAllocationLib.h> -#include <Library/PrintLib.h> > #include <Library/UefiBootServicesTableLib.h> > +#include <Library/RedfishEventLib.h> > +#include <Library/RedfishFeatureUtilityLib.h> > > #define MaxNodeNameLength 64 > +#define MaxParentUriLength 512 > #define NodeSeperator L'/' > -#define NodeIsCollectionLeftBracket '{' > -#define NodeIsCollectionRightBracket '}' > +#define UriSeperator L';' > +#define NodeIsCollectionLeftBracket L'{' > +#define NodeIsCollectionRightBracket L'}' > +#define NodeIsCollectionSymbol L"/{}" > > typedef struct _REDFISH_FEATURE_INTERNAL_DATA > REDFISH_FEATURE_INTERNAL_DATA; struct > _REDFISH_FEATURE_INTERNAL_DATA { @@ -32,7 +36,7 @@ struct > _REDFISH_FEATURE_INTERNAL_DATA { > EFI_STRING NodeName; ///< Name of the > node in > hierarchy of resource URI. > REDFISH_FEATURE_CALLBACK Callback; ///< Callback > function of > Redfish feature driver. > VOID *Context; ///< Context of > feature driver. > - FEATURE_RETURNED_INFORMATION *ReturnedInformation; ///< > Information returned from Redfish feature driver. > + RESOURCE_INFORMATION_EXCHANGE *InformationExchange; ///< > Information returned from Redfish feature driver. > UINT32 Flags; > }; > > diff --git > a/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.c > b/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.c > index 3776d52b..0e513b16 100644 > --- a/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.c > +++ b/RedfishClientPkg/RedfishFeatureCoreDxe/RedfishFeatureCoreDxe.c > @@ -2,7 +2,7 @@ > RedfishFeatureCoreDxe produces EdkIIRedfishFeatureCoreProtocol > for EDK2 Redfish Feature driver registration. > > - (C) Copyright 2021 Hewlett Packard Enterprise Development LP<BR> > + (C) Copyright 2021-2022 Hewlett Packard Enterprise Development LP<BR> > > SPDX-License-Identifier: BSD-2-Clause-Patent > > @@ -14,38 +14,194 @@ EFI_EVENT > mEdkIIRedfishFeatureDriverStartupEvent; > REDFISH_FEATURE_STARTUP_CONTEXT mFeatureDriverStartupContext; > REDFISH_FEATURE_INTERNAL_DATA *ResourceUriNodeList; > > +RESOURCE_INFORMATION_EXCHANGE *mInformationExchange; > + > +/** > + Setup the information to deliver to child feature/collection driver. > + @param[in] ThisList REDFISH_FEATURE_INTERNAL_DATA > instance. > + @param[in] ParentConfgLanguageUri Parent configure language URI. > +**/ > +EFI_STATUS > +SetupExchangeInformationInfo ( > + IN REDFISH_FEATURE_INTERNAL_DATA *ThisList, > + IN EFI_STRING ParentConfgLanguageUri > + ) > +{ > + ThisList->InformationExchange->SendInformation.ParentUri = > +(EFI_STRING)AllocateZeroPool (MaxParentUriLength * sizeof (CHAR16)); > + if (ThisList->InformationExchange->SendInformation.ParentUri == NULL) { > + return EFI_OUT_OF_RESOURCES; > + } > + > + ThisList->InformationExchange->SendInformation.PropertyName = > + (EFI_STRING)AllocateZeroPool (MaxNodeNameLength * sizeof (CHAR16)); > if (ThisList->InformationExchange->SendInformation.PropertyName == NULL) > { > + return EFI_OUT_OF_RESOURCES; > + } > + > + ThisList->InformationExchange->SendInformation.FullUri = > + (EFI_STRING)AllocateZeroPool (MaxParentUriLength * sizeof (CHAR16)); if > (ThisList->InformationExchange->SendInformation.FullUri == NULL) { > + return EFI_OUT_OF_RESOURCES; > + } > + > + // > + // Setup property name > + // > + StrCpyS (ThisList->InformationExchange->SendInformation.PropertyName, > + MaxNodeNameLength, ThisList->NodeName); > + > + // > + // Setup parent config language URI > + // > + StrCpyS (ThisList->InformationExchange->SendInformation.ParentUri, > + MaxParentUriLength, ParentConfgLanguageUri); > + > + // > + // Full config language URI > + // > + StrCpyS ( > + ThisList->InformationExchange->SendInformation.FullUri, > + MaxParentUriLength, > + ThisList->InformationExchange->SendInformation.ParentUri > + ); > + if (StrLen (ThisList->InformationExchange->SendInformation.FullUri) != 0) { > + StrCatS (ThisList->InformationExchange->SendInformation.FullUri, > + MaxParentUriLength, L"/"); } > + > + StrCatS (ThisList->InformationExchange->SendInformation.FullUri, > +MaxParentUriLength, > +ThisList->InformationExchange->SendInformation.PropertyName); > + return EFI_SUCCESS; > +} > + > +/** > + Destroy the exchange information. > + @param[in] ThisList REDFISH_FEATURE_INTERNAL_DATA instance. > +**/ > +EFI_STATUS > +DestroryExchangeInformation ( > + IN REDFISH_FEATURE_INTERNAL_DATA *ThisList > + ) > +{ > + if (ThisList->InformationExchange != NULL) { > + if (ThisList->InformationExchange->SendInformation.Type == > InformationTypeCollectionMemberUri) { > + if (ThisList->InformationExchange->SendInformation.ParentUri != NULL) > { > + FreePool (ThisList->InformationExchange->SendInformation.ParentUri); > + ThisList->InformationExchange->SendInformation.ParentUri = NULL; > + } > + > + if (ThisList->InformationExchange->SendInformation.PropertyName != > NULL) { > + FreePool (ThisList->InformationExchange- > >SendInformation.PropertyName); > + ThisList->InformationExchange->SendInformation.PropertyName = > NULL; > + } > + > + if (ThisList->InformationExchange->SendInformation.FullUri != NULL) { > + FreePool (ThisList->InformationExchange->SendInformation.FullUri); > + ThisList->InformationExchange->SendInformation.FullUri = NULL; > + } > + } > + > + if (ThisList->InformationExchange->ReturnedInformation.Type == > InformationTypeCollectionMemberConfigLanguage) { > + DestroyConfiglanguageList (&ThisList->InformationExchange- > >ReturnedInformation.ConfigureLanguageList); > + } > + > + ThisList->InformationExchange->SendInformation.Type = > InformationTypeNone; > + ThisList->InformationExchange->ReturnedInformation.Type = > + InformationTypeNone; } > + > + return EFI_SUCCESS; > +} > + > /** > Startup child feature drivers and it's sibing feature drivers. > > - @param[in] ThisFeatureDriverList This feature driver list. > - @param[in] StartupContext Start up information > + @param[in] ThisFeatureDriverList This feature driver list. > + @param[in] CurrentConfigLanguageUri The current parent configure > language URI. > + @param[in] StartupContext Start up information > > **/ > VOID > StartUpFeatureDriver ( > IN REDFISH_FEATURE_INTERNAL_DATA *ThisFeatureDriverList, > + IN EFI_STRING CurrentConfigLanguageUri, > IN REDFISH_FEATURE_STARTUP_CONTEXT *StartupContext > ) > { > - EFI_STATUS Status; > - REDFISH_FEATURE_INTERNAL_DATA *ThisList; > + EFI_STATUS Status; > + UINTN Index; > + REDFISH_FEATURE_INTERNAL_DATA *ThisList; > + REDFISH_FEATURE_ARRAY_TYPE_CONFIG_LANG_LIST ConfigLangList; > + EFI_STRING NextParentUri; > + > + NextParentUri = (EFI_STRING)AllocateZeroPool (MaxParentUriLength * > + sizeof (CHAR16)); if (NextParentUri == NULL) { > + DEBUG ((DEBUG_ERROR, "%a: Fail to allocate memory for parent > configure language.\n", __FUNCTION__)); > + return; > + } > + > + if (CurrentConfigLanguageUri != NULL) { > + StrCpyS (NextParentUri, MaxParentUriLength, > + CurrentConfigLanguageUri); } > > ThisList = ThisFeatureDriverList; > while (TRUE) { > if (ThisList->Callback != NULL) { > - Status = ThisList->Callback ( > - StartupContext->This, > - StartupContext->Action, > - ThisList->Context, > - &ThisList->ReturnedInformation > - ); > + ThisList->InformationExchange = mInformationExchange; > + Status = SetupExchangeInformationInfo (ThisList, > NextParentUri); > + if (!EFI_ERROR (Status)) { > + Status = ThisList->Callback ( > + StartupContext->This, > + StartupContext->Action, > + ThisList->Context, > + ThisList->InformationExchange > + ); > + } > + > if (EFI_ERROR (Status)) { > - DEBUG ((DEBUG_ERROR, "%a: Callback to EDK2 Redfish feature driver > fail.", __func__)); > + DEBUG ((DEBUG_ERROR, "%a: Callback to EDK2 Redfish feature > + driver fail: %s.\n", __FUNCTION__, > + ThisList->InformationExchange->SendInformation.FullUri)); > } > } > > - if (ThisList->ChildList != NULL) { > - StartUpFeatureDriver (ThisList->ChildList, StartupContext); > + if (!EFI_ERROR (Status) && (ThisList->Callback != NULL) && (ThisList- > >ChildList != NULL)) { > + // > + // Go through child list only when the parent node is managed by > feature driver. > + // > + if (ThisList->Flags & > REDFISH_FEATURE_INTERNAL_DATA_IS_COLLECTION) { > + // > + // The collection driver's callback is invoked. > InformationTypeCollectionMemberConfigLanguage > + // should be returned in RESOURCE_INFORMATION_RETURNED. > + // > + if (ThisList->InformationExchange->ReturnedInformation.Type == > InformationTypeCollectionMemberConfigLanguage) { > + // > + // Copy RESOURCE_INFORMATION_RETURNED then destroy the > exchange information. > + // > + CopyConfiglanguageList (&ThisList->InformationExchange- > >ReturnedInformation.ConfigureLanguageList, &ConfigLangList); > + DestroryExchangeInformation (ThisList); > + // > + // Modify the collection instance according to the returned > InformationTypeCollectionMemberConfigLanguage. > + // > + for (Index = 0; Index < ConfigLangList.Count; Index++) { > + StrCatS (NextParentUri, MaxParentUriLength, ThisList->NodeName); > + StrCatS (NextParentUri, MaxParentUriLength, > NodeIsCollectionSymbol); > + SetResourceConfigLangMemberInstance (&NextParentUri, > MaxParentUriLength, (REDFISH_FEATURE_ARRAY_TYPE_CONFIG_LANG > *)&ConfigLangList.List[Index]); > + StartUpFeatureDriver (ThisList->ChildList, NextParentUri, > StartupContext); > + } > + > + DestroyConfiglanguageList (&ConfigLangList); > + } else { > + DEBUG ((DEBUG_ERROR, "%a: No > InformationTypeCollectionMemberConfigLanguage of %s returned.\n", > __FUNCTION__, ThisList->InformationExchange->SendInformation.FullUri)); > + DEBUG ((DEBUG_ERROR, "%a: Redfish service maybe not connected > or the network has problems.\n", __FUNCTION__)); > + return; > + } > + } else { > + StrCatS (NextParentUri, MaxParentUriLength, ThisList->NodeName); > + StartUpFeatureDriver (ThisList->ChildList, NextParentUri, > StartupContext); > + } > + > + // > + // Restore the parent configure language URI for this level. > + // > + if (CurrentConfigLanguageUri != NULL) { > + StrCpyS (NextParentUri, MaxParentUriLength, > CurrentConfigLanguageUri); > + } else { > + NextParentUri[0] = 0; > + } > + } else { > + DestroryExchangeInformation (ThisList); > } > > // > @@ -60,6 +216,10 @@ StartUpFeatureDriver ( > // > ThisList = ThisList->SiblingList; > } > + > + if (NextParentUri != NULL) { > + FreePool (NextParentUri); > + } > } > > /** > @@ -89,10 +249,29 @@ RedfishFeatureDriverStartup ( > return; > } > > + // > + // Initial dispatcher variables. > + // > + mInformationExchange = (RESOURCE_INFORMATION_EXCHANGE > + *)AllocateZeroPool (sizeof (RESOURCE_INFORMATION_EXCHANGE)); if > (mInformationExchange == NULL) { > + DEBUG ((DEBUG_ERROR, "%a: Fail to allocate memory for exchange > information.\n", __FUNCTION__)); > + return; > + } > + > + // > + // Signal event before doing provisioning // > + SignalReadyToProvisioningEvent (); > + > // > // Invoke the callback by the hierarchy level > // > - StartUpFeatureDriver (ResourceUriNodeList, StartupContext); > + StartUpFeatureDriver (ResourceUriNodeList, NULL, StartupContext); > + > + // > + // Signal event after provisioning finished // > + SignalAfterProvisioningEvent (); > } > > /** > @@ -101,6 +280,8 @@ RedfishFeatureDriverStartup ( > @param[in,out] PtrToNewInternalData Pointer to receive new instance of > REDFISH_FEATURE_INTERNAL_DATA. > @param[in] NodeName Name of URI node. > + @param[in] NodeIsCollection TRUE means the node to add is the > collection node. > + Otherwise it is a resource node. > > @retval EFI_SUCCESS New entry is inserted successfully. > @retval EFI_INVALID_PARAMETER Improper given parameters. > @@ -110,7 +291,8 @@ RedfishFeatureDriverStartup ( > EFI_STATUS > NewInternalInstance ( > IN OUT REDFISH_FEATURE_INTERNAL_DATA **PtrToNewInternalData, > - IN EFI_STRING NodeName > + IN EFI_STRING NodeName, > + IN BOOLEAN NodeIsCollection > ) > { > REDFISH_FEATURE_INTERNAL_DATA *NewInternalData; > @@ -131,9 +313,7 @@ NewInternalInstance ( > StrnCpyS (NewInternalData->NodeName, StrSize (NodeName), (CONST > CHAR16 *)NodeName, StrLen (NodeName)); > NewInternalData->SiblingList = NULL; > NewInternalData->ChildList = NULL; > - if ((NodeName[0] == (UINT16)NodeIsCollectionLeftBracket) && > - (NodeName[StrLen (NodeName) - 1] == > (UINT16)NodeIsCollectionRightBracket)) > - { > + if (NodeIsCollection) { > NewInternalData->Flags |= > REDFISH_FEATURE_INTERNAL_DATA_IS_COLLECTION; > } > > @@ -145,11 +325,16 @@ NewInternalInstance ( > Insert the URI node into internal data structure > > @param[in] HeadEntryToInsert The head entry to start the searching. > + @param[in] PrevisouEntry Previsou entry. > @param[in] NodeName Name of URI node. > + @param[in] NodeIsCollection TRUE means the node to add is the > collection node. > + Otherwise it is a resource node. > @param[in, out] NextNodeEntry Pointer to receive the pointer of next > head > entry for inserting the follow up > nodes. > The returned LIST_ENTRY is the > address of > ChildList link list. > + @param[out] MatchNodeEntry The matched node entry. > + > @retval EFI_SUCCESS New entry is inserted successfully. > @retval EFI_INVALID_PARAMETER Improper given parameters. > @retval EFI_OUT_OF_RESOURCES Lack of memory for the internal data > structure. > @@ -158,8 +343,11 @@ NewInternalInstance ( > EFI_STATUS > InsertRedfishFeatureUriNode ( > IN REDFISH_FEATURE_INTERNAL_DATA *HeadEntryToInsert, > + IN REDFISH_FEATURE_INTERNAL_DATA **PrevisouEntry, > IN EFI_STRING NodeName, > - IN OUT REDFISH_FEATURE_INTERNAL_DATA **NextNodeEntry > + IN BOOLEAN NodeIsCollection, > + IN OUT REDFISH_FEATURE_INTERNAL_DATA **NextNodeEntry, > + OUT REDFISH_FEATURE_INTERNAL_DATA **MatchNodeEntry > ) > { > EFI_STATUS Status; > @@ -167,6 +355,7 @@ InsertRedfishFeatureUriNode ( > REDFISH_FEATURE_INTERNAL_DATA *ThisInternalData; > REDFISH_FEATURE_INTERNAL_DATA *SiblingList; > > + *MatchNodeEntry = NULL; > if (NodeName == NULL) { > DEBUG ((DEBUG_ERROR, "%a: Node name is NULL.\n", __func__)); > return EFI_INVALID_PARAMETER; > @@ -177,19 +366,20 @@ InsertRedfishFeatureUriNode ( > return EFI_INVALID_PARAMETER; > } > > - if ((HeadEntryToInsert == NULL) || (HeadEntryToInsert->ChildList == NULL)) > { > - Status = NewInternalInstance (&NewInternalData, NodeName); > + if (HeadEntryToInsert == NULL) { > + Status = NewInternalInstance (&NewInternalData, NodeName, > NodeIsCollection); > if (EFI_ERROR (Status)) { > return Status; > } > > - if (HeadEntryToInsert == NULL) { > + if ((HeadEntryToInsert == NULL) && (ResourceUriNodeList == NULL)) { > ResourceUriNodeList = NewInternalData; > } else { > - HeadEntryToInsert->ChildList = NewInternalData; > + (*PrevisouEntry)->ChildList = NewInternalData; > } > > - *NextNodeEntry = NewInternalData; > + *PrevisouEntry = NewInternalData; > + *NextNodeEntry = NewInternalData->ChildList; > return EFI_SUCCESS; > } > > @@ -200,7 +390,9 @@ InsertRedfishFeatureUriNode ( > SiblingList = ThisInternalData->SiblingList; > while (TRUE) { > if (StrCmp ((CONST CHAR16 *)ThisInternalData->NodeName, (CONST > CHAR16 *)NodeName) == 0) { > - *NextNodeEntry = ThisInternalData->ChildList; > + *MatchNodeEntry = ThisInternalData; > + *NextNodeEntry = ThisInternalData->ChildList; > + *PrevisouEntry = ThisInternalData; > return EFI_SUCCESS; > } > > @@ -208,17 +400,19 @@ InsertRedfishFeatureUriNode ( > // If sibing exist? > // > if (SiblingList == NULL) { > - Status = NewInternalInstance (&NewInternalData, NodeName); > + Status = NewInternalInstance (&NewInternalData, NodeName, > NodeIsCollection); > if (EFI_ERROR (Status)) { > return Status; > } > > ThisInternalData->SiblingList = NewInternalData; > + *PrevisouEntry = NewInternalData; > *NextNodeEntry = NewInternalData->ChildList; > return EFI_SUCCESS; > } > > - SiblingList = SiblingList->SiblingList; > + ThisInternalData = SiblingList; > + SiblingList = ThisInternalData->SiblingList; > } > > return EFI_SUCCESS; > @@ -265,7 +459,12 @@ RedfishFeatureRegister ( > UINTN Index; > UINTN AnchorIndex; > UINTN UriLength; > + BOOLEAN NewUri; > REDFISH_FEATURE_INTERNAL_DATA *ThisUriNode; > + REDFISH_FEATURE_INTERNAL_DATA *PreUriNode; > + REDFISH_FEATURE_INTERNAL_DATA *NewUriNode; > + REDFISH_FEATURE_INTERNAL_DATA *MatchNodeEntry; > + BOOLEAN ItsCollection; > > if ((FeatureManagedUri == NULL) || (Callback == NULL)) { > DEBUG ((DEBUG_ERROR, "%a: The given parameter is invalid\n", > __func__)); > @@ -279,7 +478,9 @@ RedfishFeatureRegister ( > Index = 0; > AnchorIndex = 0; > ThisUriNode = ResourceUriNodeList; > - do { > + PreUriNode = ResourceUriNodeList; > + NewUri = FALSE; > + while ((Index < UriLength)) { > if ((Index - AnchorIndex + 1) >= MaxNodeNameLength) { > // Increase one for the NULL terminator > DEBUG ((DEBUG_ERROR, "%a: the length of node name is >= > MaxNodeNameLength\n", __func__)); > @@ -287,22 +488,61 @@ RedfishFeatureRegister ( > } > > NodeName[Index - AnchorIndex] = *(FeatureManagedUri + Index); > - if ((NodeName[Index - AnchorIndex] == NodeSeperator) || > (NodeName[Index - AnchorIndex] == (CHAR16)0)) { > + if ((NodeName[Index - AnchorIndex] == NodeSeperator) || > (NodeName[Index - AnchorIndex] == UriSeperator) || (NodeName[Index - > AnchorIndex] == (CHAR16)0)) { > + if (NodeName[Index - AnchorIndex] == UriSeperator) { > + NewUri = TRUE; > + } > + > NodeName[Index - AnchorIndex] = 0; > AnchorIndex = Index + 1; > // > // Insert node > // > if (StrLen (NodeName) != 0) { > - Status = InsertRedfishFeatureUriNode (ThisUriNode, NodeName, > &ThisUriNode); > + ItsCollection = FALSE; > + if (((Index + StrLen (NodeIsCollectionSymbol)) < UriLength) && > + (*(FeatureManagedUri + Index + 1) == NodeIsCollectionLeftBracket) > && > + (*(FeatureManagedUri + Index + 2) == > NodeIsCollectionRightBracket)) > + { > + Index += (StrLen (NodeIsCollectionSymbol)); > + AnchorIndex += (StrLen (NodeIsCollectionSymbol)); > + ItsCollection = TRUE; > + if (*(FeatureManagedUri + Index) == UriSeperator) { > + NewUri = TRUE; > + } > + } > + > + Status = InsertRedfishFeatureUriNode (ThisUriNode, &PreUriNode, > NodeName, ItsCollection, &NewUriNode, &MatchNodeEntry); > if (EFI_ERROR (Status)) { > return Status; > } > + > + ThisUriNode = NewUriNode; > + } > + > + if (NewUri || ((Index + 1) >= UriLength)) { > + // > + // Setup the callabck and restart the searching for the > + // next URI. > + // > + if (MatchNodeEntry != NULL) { > + MatchNodeEntry->Callback = Callback; > + MatchNodeEntry->Context = Context; > + MatchNodeEntry = NULL; > + } else { > + PreUriNode->Callback = Callback; > + PreUriNode->Context = Context; > + } > + > + NewUri = FALSE; > + ThisUriNode = ResourceUriNodeList; > + Index++; > + continue; > } > } > > Index++; > - } while ((Index < UriLength)); > + } > > if (ThisUriNode == NULL) { > // > @@ -312,11 +552,6 @@ RedfishFeatureRegister ( > return EFI_INVALID_PARAMETER; > } > > - // > - // Add feature driver info to internal data instance. > - // > - ThisUriNode->Callback = Callback; > - ThisUriNode->Context = Context; > return EFI_SUCCESS; > } > > -- > 2.17.1 -=-=-=-=-=-=-=-=-=-=-=- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#104514): https://edk2.groups.io/g/devel/message/104514 Mute This Topic: https://groups.io/mt/98801716/21656 Group Owner: devel+ow...@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [arch...@mail-archive.com] -=-=-=-=-=-=-=-=-=-=-=-