Date   

[PATCH v1 05/13] DynamicTablesPkg: Helper function to compute package length

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Some AML object have a PkgLen which indicates the size of the
AML object. The package length can be encoded in 1 to 4 bytes.
The bytes used to encode the PkgLen is itself counted in the
PkgLen value. So, if an AML object's size increments/decrements,
the number of bytes used to encode the PkgLen value can itself
increment/decrement.

Therefore, a helper function AmlComputePkgLength() is introduced
to simply computation of the PkgLen.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Library/Common/AmlLib/AmlEncoding/Aml.c | 87 ++++++++++++++++++-
.../Library/Common/AmlLib/AmlEncoding/Aml.h | 47 +++++++++-
2 files changed, 132 insertions(+), 2 deletions(-)

diff --git a/DynamicTablesPkg/Library/Common/AmlLib/AmlEncoding/Aml.c b/DynamicTablesPkg/Library/Common/AmlLib/AmlEncoding/Aml.c
index eadafca97ea5..d829b1869846 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/AmlEncoding/Aml.c
+++ b/DynamicTablesPkg/Library/Common/AmlLib/AmlEncoding/Aml.c
@@ -2,7 +2,7 @@
AML grammar definitions.

Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved. <BR>
- Copyright (c) 2019 - 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2019 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent
**/
@@ -803,3 +803,88 @@ AmlComputePkgLengthWidth (
// Length < 2^6
return 1;
}
+
+/** Given a length, compute the value of a PkgLen.
+
+ In AML, some object have a PkgLen, telling the size of the AML object.
+ It can be encoded in 1 to 4 bytes. The bytes used to encode the PkgLen is
+ itself counted in the PkgLen value.
+ This means that if an AML object sees its size increment/decrement,
+ the number of bytes used to encode the PkgLen value can itself
+ increment/decrement.
+
+ For instance, the AML encoding of a DeviceOp is:
+ DefDevice := DeviceOp PkgLength NameString TermList
+ If:
+ - sizeof (NameString) = 4 (the name is "DEV0" for instance);
+ - sizeof (TermList) = (2^6-6)
+ then the PkgLen is encoded on 1 byte. Indeed, its value is:
+ sizeof (PkgLen) + sizeof (NameString) + sizeof (TermList) =
+ sizeof (PkgLen) + 4 + (2^6-6)
+ So:
+ PkgLen = sizeof (PkgLen) + (2^6-2)
+
+ The input arguments Length and PkgLen represent, for the DefDevice:
+ DefDevice := DeviceOp PkgLength NameString TermList
+ |------Length-----|
+ |--------*PgkLength---------|
+
+ @param [in] Length The length to encode as a PkgLen.
+ Length cannot exceed 2^28 - 4 (4 bytes for the
+ PkgLen encoding).
+ The size of the PkgLen encoding bytes should not be
+ counted in this length value.
+ @param [out] PkgLen If success, contains the value of the PkgLen,
+ ready to encode in the PkgLen format.
+ This value takes into account the size of PkgLen
+ encoding.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+**/
+EFI_STATUS
+EFIAPI
+AmlComputePkgLength (
+ IN UINT32 Length,
+ OUT UINT32 * PkgLen
+ )
+{
+ UINT32 PkgLenWidth;
+ UINT32 ReComputedPkgLenWidth;
+
+ if (PkgLen == NULL) {
+ ASSERT (0);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ // Compute the PkgLenWidth.
+ PkgLenWidth = AmlComputePkgLengthWidth (Length);
+ if (PkgLenWidth == 0) {
+ ASSERT (0);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ // Add it to the Length.
+ Length += PkgLenWidth;
+
+ // Check that adding the PkgLenWidth didn't trigger a domino effect,
+ // increasing the encoding width of the PkgLen again.
+ // The PkgLen is encoded in at most 4 bytes. It is possible to increase
+ // the PkgLen width if its encoding is less than 3 bytes.
+ ReComputedPkgLenWidth = AmlComputePkgLengthWidth (Length);
+ if (ReComputedPkgLenWidth != PkgLenWidth) {
+ if ((ReComputedPkgLenWidth != 0) &&
+ (ReComputedPkgLenWidth < 4)) {
+ // No need to recompute the PkgLen since a new threshold cannot
+ // be reached by incrementing the value by one.
+ Length += 1;
+ } else {
+ ASSERT (0);
+ return EFI_INVALID_PARAMETER;
+ }
+ }
+
+ *PkgLen = Length;
+
+ return EFI_SUCCESS;
+}
diff --git a/DynamicTablesPkg/Library/Common/AmlLib/AmlEncoding/Aml.h b/DynamicTablesPkg/Library/Common/AmlLib/AmlEncoding/Aml.h
index 35c0680b6159..0641500fcd5f 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/AmlEncoding/Aml.h
+++ b/DynamicTablesPkg/Library/Common/AmlLib/AmlEncoding/Aml.h
@@ -2,7 +2,7 @@
AML grammar definitions.

Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved. <BR>
- Copyright (c) 2019 - 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2019 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent
**/
@@ -326,5 +326,50 @@ AmlComputePkgLengthWidth (
IN UINT32 Length
);

+/** Given a length, compute the value of a PkgLen.
+
+ In AML, some object have a PkgLen, telling the size of the AML object.
+ It can be encoded in 1 to 4 bytes. The bytes used to encode the PkgLen is
+ itself counted in the PkgLen value.
+ This means that if an AML object sees its size increment/decrement,
+ the number of bytes used to encode the PkgLen value can itself
+ increment/decrement.
+
+ For instance, the AML encoding of a DeviceOp is:
+ DefDevice := DeviceOp PkgLength NameString TermList
+ If:
+ - sizeof (NameString) = 4 (the name is "DEV0" for instance);
+ - sizeof (TermList) = (2^6-6)
+ then the PkgLen is encoded on 1 byte. Indeed, its value is:
+ sizeof (PkgLen) + sizeof (NameString) + sizeof (TermList) =
+ sizeof (PkgLen) + 4 + (2^6-6)
+ So:
+ PkgLen = sizeof (PkgLen) + (2^6-2)
+
+ The input arguments Length and PkgLen represent, for the DefDevice:
+ DefDevice := DeviceOp PkgLength NameString TermList
+ |------Length-----|
+ |--------*PgkLength---------|
+
+ @param [in] Length The length to encode as a PkgLen.
+ Length cannot exceed 2^28 - 4 (4 bytes for the
+ PkgLen encoding).
+ The size of the PkgLen encoding bytes should not be
+ counted in this length value.
+ @param [out] PkgLen If success, contains the value of the PkgLen,
+ ready to encode in the PkgLen format.
+ This value takes into account the size of PkgLen
+ encoding.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+**/
+EFI_STATUS
+EFIAPI
+AmlComputePkgLength (
+ IN UINT32 Length,
+ OUT UINT32 * PkgLen
+ );
+
#endif // AML_H_

--
2.17.1


[PATCH v1 04/13] DynamicTablesPkg: AML code generation for a Package

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Add AmlCodeGenPackage() to generate AML code for declaring
a Package() object. This function generates an empty package
node. New elements can then be added to the package's variable
argument list.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Common/AmlLib/CodeGen/AmlCodeGen.c | 82 ++++++++++++++++++-
1 file changed, 81 insertions(+), 1 deletion(-)

diff --git a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlCodeGen.c b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlCodeGen.c
index 5d310f201319..ea9b73b464a4 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlCodeGen.c
+++ b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlCodeGen.c
@@ -1,7 +1,7 @@
/** @file
AML Code Generation.

- Copyright (c) 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2020 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent
**/
@@ -235,6 +235,86 @@ AmlCodeGenInteger (
return Status;
}

+/** AML code generation for a Package object node.
+
+ The package generated is empty. New elements can be added via its
+ list of variable arguments.
+
+ @param [out] NewObjectNode If success, contains the created
+ Package object node.
+
+ @retval EFI_SUCCESS Success.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+ @retval EFI_OUT_OF_RESOURCES Failed to allocate memory.
+**/
+STATIC
+EFI_STATUS
+EFIAPI
+AmlCodeGenPackage (
+ OUT AML_OBJECT_NODE ** NewObjectNode
+ )
+{
+ EFI_STATUS Status;
+ AML_DATA_NODE * DataNode;
+ UINT8 NodeCount;
+
+ if (NewObjectNode == NULL) {
+ ASSERT (0);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ DataNode = NULL;
+ NodeCount = 0;
+
+ // Create an object node.
+ // PkgLen is 2:
+ // - one byte to store the PkgLength
+ // - one byte for the NumElements.
+ // Cf ACPI6.3, s20.2.5 "Term Objects Encoding"
+ // DefPackage := PackageOp PkgLength NumElements PackageElementList
+ // NumElements := ByteData
+ Status = AmlCreateObjectNode (
+ AmlGetByteEncodingByOpCode (AML_PACKAGE_OP, 0),
+ 2,
+ NewObjectNode
+ );
+ if (EFI_ERROR (Status)) {
+ ASSERT (0);
+ return Status;
+ }
+
+ // NumElements is a ByteData.
+ Status = AmlCreateDataNode (
+ EAmlNodeDataTypeUInt,
+ &NodeCount,
+ sizeof (NodeCount),
+ &DataNode
+ );
+ if (EFI_ERROR (Status)) {
+ ASSERT (0);
+ goto error_handler;
+ }
+
+ Status = AmlSetFixedArgument (
+ *NewObjectNode,
+ EAmlParseIndexTerm0,
+ (AML_NODE_HEADER*)DataNode
+ );
+ if (EFI_ERROR (Status)) {
+ ASSERT (0);
+ goto error_handler;
+ }
+
+ return Status;
+
+error_handler:
+ AmlDeleteTree ((AML_NODE_HEADER*)*NewObjectNode);
+ if (DataNode != NULL) {
+ AmlDeleteTree ((AML_NODE_HEADER*)DataNode);
+ }
+ return Status;
+}
+
/** AML code generation for a Name object node.

@param [in] NameString The new variable name.
--
2.17.1


[PATCH v1 03/13] DynamicTablesPkg: AML Code generation for Resource data EndTag

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Add a helper function AmlCodeGenEndTag() to generate AML Resource Data
EndTag. The EndTag resource data is automatically generated by the ASL
compiler at the end of a list of resource data elements. Therefore, an
equivalent function is not present in ASL.

However, AmlCodeGenEndTag() is useful when generating AML code for the
ResourceTemplate() macro.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../AmlLib/CodeGen/AmlResourceDataCodeGen.c | 104 ++++++++++++++++++
.../AmlLib/CodeGen/AmlResourceDataCodeGen.h | 34 ++++++
2 files changed, 138 insertions(+)

diff --git a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
index 07a96725a4ef..78910cc5d4b4 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
+++ b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
@@ -274,6 +274,110 @@ AmlCodeGenRdRegister (
return LinkRdNode (RdNode, NameOpNode, NewRdNode);
}

+/** Code generation for the EndTag resource data.
+
+ The EndTag resource data is automatically generated by the ASL compiler
+ at the end of a list of resource data elements. Thus, it doesn't have
+ a corresponding ASL function.
+
+ This function allocates memory to create a data node. It is the caller's
+ responsibility to either:
+ - attach this node to an AML tree;
+ - delete this node.
+
+ @param [in] CheckSum CheckSum to store in the EndTag.
+ Optional: can be let to 0. It is not
+ updated when new resource data elements
+ are added/removed/modified in the list.
+ @param [in] ParentNode If not NULL, add the generated node
+ to the end of the variable list of
+ argument of the ParentNode.
+ The ParentNode must not initially contain
+ an EndTag resource data element.
+ @param [out] NewRdNode If success, contains the generated node.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+ @retval EFI_OUT_OF_RESOURCES Could not allocate memory.
+**/
+EFI_STATUS
+EFIAPI
+AmlCodeGenEndTag (
+ IN UINT8 CheckSum, OPTIONAL
+ IN AML_OBJECT_NODE * ParentNode, OPTIONAL
+ OUT AML_DATA_NODE ** NewRdNode OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ AML_DATA_NODE * RdNode;
+ EFI_ACPI_END_TAG_DESCRIPTOR EndTag;
+ ACPI_SMALL_RESOURCE_HEADER SmallResHdr;
+
+ if ((ParentNode == NULL) && (NewRdNode == NULL)) {
+ ASSERT (0);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ RdNode = NULL;
+
+ // Header
+ SmallResHdr.Bits.Length = sizeof (EFI_ACPI_END_TAG_DESCRIPTOR) -
+ sizeof (ACPI_SMALL_RESOURCE_HEADER);
+ SmallResHdr.Bits.Name = ACPI_SMALL_END_TAG_DESCRIPTOR_NAME;
+ SmallResHdr.Bits.Type = ACPI_SMALL_ITEM_FLAG;
+
+ // Body
+ EndTag.Desc = SmallResHdr.Byte;
+ EndTag.Checksum = CheckSum;
+
+ Status = AmlCreateDataNode (
+ EAmlNodeDataTypeResourceData,
+ (UINT8*)&EndTag,
+ sizeof (EFI_ACPI_END_TAG_DESCRIPTOR),
+ &RdNode
+ );
+ if (EFI_ERROR (Status)) {
+ ASSERT (0);
+ return Status;
+ }
+
+ if (NewRdNode != NULL) {
+ *NewRdNode = RdNode;
+ }
+
+ if (ParentNode != NULL) {
+ // Check the BufferOp doesn't contain any resource data yet.
+ // This is a hard check: do not allow to add an EndTag if the BufferNode
+ // already has resource data elements attached. Indeed, the EndTag should
+ // have already been added.
+ if (AmlGetNextVariableArgument ((AML_NODE_HEADER*)ParentNode, NULL) !=
+ NULL) {
+ ASSERT (0);
+ Status = EFI_INVALID_PARAMETER;
+ goto error_handler;
+ }
+
+ // Manually add the EndTag RdNode. Indeed, the AmlAppendRdNode function
+ // is looking for an EndTag, which we are adding here.
+ Status = AmlVarListAddTail (
+ (AML_NODE_HEADER*)ParentNode,
+ (AML_NODE_HEADER*)RdNode
+ );
+ if (EFI_ERROR (Status)) {
+ ASSERT (0);
+ goto error_handler;
+ }
+ }
+
+ return Status;
+
+error_handler:
+ if (RdNode != NULL) {
+ AmlDeleteTree ((AML_NODE_HEADER*)RdNode);
+ }
+ return Status;
+}
+
// DEPRECATED APIS
#ifndef DISABLE_NEW_DEPRECATED_INTERFACES

diff --git a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h
index 3c9217d9ddab..0b464305da40 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h
+++ b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h
@@ -104,4 +104,38 @@ AmlCodeGenRdRegister (
OUT AML_DATA_NODE_HANDLE *NewRdNode OPTIONAL
);

+/** Code generation for the EndTag resource data.
+
+ The EndTag resource data is automatically generated by the ASL compiler
+ at the end of a list of resource data elements. Thus, it doesn't have
+ a corresponding ASL function.
+
+ This function allocates memory to create a data node. It is the caller's
+ responsibility to either:
+ - attach this node to an AML tree;
+ - delete this node.
+
+ @param [in] CheckSum CheckSum to store in the EndTag.
+ Optional: can be let to 0. It is not
+ updated when new resource data elements
+ are added/removed/modified in the list.
+ @param [in] ParentNode If not NULL, add the generated node
+ to the end of the variable list of
+ argument of the ParentNode.
+ The ParentNode must not initially contain
+ an EndTag resource data element.
+ @param [out] NewRdNode If success, contains the generated node.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+ @retval EFI_OUT_OF_RESOURCES Could not allocate memory.
+**/
+EFI_STATUS
+EFIAPI
+AmlCodeGenEndTag (
+ IN UINT8 CheckSum, OPTIONAL
+ IN AML_OBJECT_NODE * ParentNode, OPTIONAL
+ OUT AML_DATA_NODE ** NewRdNode OPTIONAL
+ );
+
#endif // AML_RESOURCE_DATA_CODE_GEN_H_
--
2.17.1


[PATCH v1 02/13] DynamicTablesPkg: AML Code generation for Register()

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Add AmlCodeGenRegister() to generate AML code for the
Generic Register Resource Descriptor. This function is
equivalent to the ASL macro Register().

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../AmlLib/CodeGen/AmlResourceDataCodeGen.c | 87 +++++++++++++++++++
.../AmlLib/CodeGen/AmlResourceDataCodeGen.h | 49 +++++++++++
2 files changed, 136 insertions(+)

diff --git a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
index 089597a6c906..07a96725a4ef 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
+++ b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
@@ -187,6 +187,93 @@ AmlCodeGenRdInterrupt (
return LinkRdNode (RdNode, NameOpNode, NewRdNode);
}

+/** Code generation for the "Register ()" ASL function.
+
+ The Resource Data effectively created is a Generic Register Descriptor.
+ Data. Cf ACPI 6.4:
+ - s6.4.3.7 "Generic Register Descriptor".
+ - s19.6.114 "Register".
+
+ The created resource data node can be:
+ - appended to the list of resource data elements of the NameOpNode.
+ In such case NameOpNode must be defined by a the "Name ()" ASL statement
+ and initially contain a "ResourceTemplate ()".
+ - returned through the NewRdNode parameter.
+
+ @param [in] AddressSpace Address space where the register exists.
+ Can be one of I/O space, System Memory, etc.
+ @param [in] BitWidth Number of bits in the register.
+ @param [in] BitOffset Offset in bits from the start of the register
+ indicated by the Address.
+ @param [in] Address Register address.
+ @param [in] AccessSize Size of data values used when accessing the
+ address space. Can be one of:
+ 0 - Undefined, legacy (EFI_ACPI_6_3_UNDEFINED)
+ 1 - Byte access (EFI_ACPI_6_3_BYTE)
+ 2 - Word access (EFI_ACPI_6_3_WORD)
+ 3 - DWord access (EFI_ACPI_6_3_DWORD)
+ 4 - QWord access (EFI_ACPI_6_3_QWORD)
+ @param [in] NameOpNode NameOp object node defining a named object.
+ If provided, append the new resource data node
+ to the list of resource data elements of this
+ node.
+ @param [out] NewRdNode If provided and success,
+ contain the created node.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+ @retval EFI_OUT_OF_RESOURCES Could not allocate memory.
+**/
+EFI_STATUS
+EFIAPI
+AmlCodeGenRdRegister (
+ IN UINT8 AddressSpace,
+ IN UINT8 BitWidth,
+ IN UINT8 BitOffset,
+ IN UINT64 Address,
+ IN UINT8 AccessSize,
+ IN AML_OBJECT_NODE_HANDLE NameOpNode, OPTIONAL
+ OUT AML_DATA_NODE_HANDLE *NewRdNode OPTIONAL
+ )
+{
+ EFI_STATUS Status;
+ AML_DATA_NODE * RdNode;
+ EFI_ACPI_GENERIC_REGISTER_DESCRIPTOR RdRegister;
+
+ if ((AccessSize > EFI_ACPI_6_3_QWORD) ||
+ ((NameOpNode == NULL) && (NewRdNode == NULL))) {
+ ASSERT (0);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ // Header
+ RdRegister.Header.Header.Bits.Name =
+ ACPI_LARGE_GENERIC_REGISTER_DESCRIPTOR_NAME;
+ RdRegister.Header.Header.Bits.Type = ACPI_LARGE_ITEM_FLAG;
+ RdRegister.Header.Length = sizeof (EFI_ACPI_GENERIC_REGISTER_DESCRIPTOR) -
+ sizeof (ACPI_LARGE_RESOURCE_HEADER);
+
+ // Body
+ RdRegister.AddressSpaceId = AddressSpace;
+ RdRegister.RegisterBitWidth = BitWidth;
+ RdRegister.RegisterBitOffset = BitOffset;
+ RdRegister.AddressSize = AccessSize;
+ RdRegister.RegisterAddress = Address;
+
+ Status = AmlCreateDataNode (
+ EAmlNodeDataTypeResourceData,
+ (UINT8*)&RdRegister,
+ sizeof (EFI_ACPI_GENERIC_REGISTER_DESCRIPTOR),
+ &RdNode
+ );
+ if (EFI_ERROR (Status)) {
+ ASSERT (0);
+ return Status;
+ }
+
+ return LinkRdNode (RdNode, NameOpNode, NewRdNode);
+}
+
// DEPRECATED APIS
#ifndef DISABLE_NEW_DEPRECATED_INTERFACES

diff --git a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h
index 764051e3d7c9..3c9217d9ddab 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h
+++ b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h
@@ -55,4 +55,53 @@ AmlCodeGenRdInterrupt (
OUT AML_DATA_NODE_HANDLE *NewRdNode OPTIONAL
);

+/** Code generation for the "Register ()" ASL function.
+
+ The Resource Data effectively created is a Generic Register Descriptor.
+ Data. Cf ACPI 6.4:
+ - s6.4.3.7 "Generic Register Descriptor".
+ - s19.6.114 "Register".
+
+ The created resource data node can be:
+ - appended to the list of resource data elements of the NameOpNode.
+ In such case NameOpNode must be defined by a the "Name ()" ASL statement
+ and initially contain a "ResourceTemplate ()".
+ - returned through the NewRdNode parameter.
+
+ @param [in] AddressSpace Address space where the register exists.
+ Can be one of I/O space, System Memory, etc.
+ @param [in] BitWidth Number of bits in the register.
+ @param [in] BitOffset Offset in bits from the start of the register
+ indicated by the Address.
+ @param [in] Address Register address.
+ @param [in] AccessSize Size of data values used when accessing the
+ address space. Can be one of:
+ 0 - Undefined, legacy (EFI_ACPI_6_3_UNDEFINED)
+ 1 - Byte access (EFI_ACPI_6_3_BYTE)
+ 2 - Word access (EFI_ACPI_6_3_WORD)
+ 3 - DWord access (EFI_ACPI_6_3_DWORD)
+ 4 - QWord access (EFI_ACPI_6_3_QWORD)
+ @param [in] NameOpNode NameOp object node defining a named object.
+ If provided, append the new resource data node
+ to the list of resource data elements of this
+ node.
+ @param [out] NewRdNode If provided and success,
+ contain the created node.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+ @retval EFI_OUT_OF_RESOURCES Could not allocate memory.
+**/
+EFI_STATUS
+EFIAPI
+AmlCodeGenRdRegister (
+ IN UINT8 AddressSpace,
+ IN UINT8 BitWidth,
+ IN UINT8 BitOffset,
+ IN UINT64 Address,
+ IN UINT8 AccessSize,
+ IN AML_OBJECT_NODE_HANDLE NameOpNode, OPTIONAL
+ OUT AML_DATA_NODE_HANDLE *NewRdNode OPTIONAL
+ );
+
#endif // AML_RESOURCE_DATA_CODE_GEN_H_
--
2.17.1


[PATCH v1 01/13] DynamicTablesPkg: Make AmlNodeGetIntegerValue public

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Remove the STATIC qualifier for the AmlUtility function
AmlNodeGetIntegerValue() and add the definition to the
header file so that it can be used by other AmlLib
sub-modules.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Library/Common/AmlLib/Utils/AmlUtility.c | 3 +--
.../Library/Common/AmlLib/Utils/AmlUtility.h | 18 +++++++++++++++++-
2 files changed, 18 insertions(+), 3 deletions(-)

diff --git a/DynamicTablesPkg/Library/Common/AmlLib/Utils/AmlUtility.c b/DynamicTablesPkg/Library/Common/AmlLib/Utils/AmlUtility.c
index 7ebd08f945c0..3c8927acda6a 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/Utils/AmlUtility.c
+++ b/DynamicTablesPkg/Library/Common/AmlLib/Utils/AmlUtility.c
@@ -1,7 +1,7 @@
/** @file
AML Utility.

- Copyright (c) 2019 - 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2019 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent
**/
@@ -192,7 +192,6 @@ AmlComputeSize (
@retval EFI_SUCCESS The function completed successfully.
@retval EFI_INVALID_PARAMETER Invalid parameter.
**/
-STATIC
EFI_STATUS
EFIAPI
AmlNodeGetIntegerValue (
diff --git a/DynamicTablesPkg/Library/Common/AmlLib/Utils/AmlUtility.h b/DynamicTablesPkg/Library/Common/AmlLib/Utils/AmlUtility.h
index c57d780140d4..5013bfb81d2d 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/Utils/AmlUtility.h
+++ b/DynamicTablesPkg/Library/Common/AmlLib/Utils/AmlUtility.h
@@ -1,7 +1,7 @@
/** @file
AML Utility.

- Copyright (c) 2019 - 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2019 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent
**/
@@ -39,6 +39,22 @@ AmlComputeSize (
IN OUT UINT32 * Size
);

+/** Get the value contained in an integer node.
+
+ @param [in] Node Pointer to an integer node.
+ Must be an object node.
+ @param [out] Value Value contained in the integer node.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+**/
+EFI_STATUS
+EFIAPI
+AmlNodeGetIntegerValue (
+ IN AML_OBJECT_NODE * Node,
+ OUT UINT64 * Value
+ );
+
/** Set the value contained in an integer node.

The OpCode is updated accordingly to the new value
--
2.17.1


[PATCH v1 00/13] Create a SSDT CPU topology generator

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

As part of the DynamicTablesPkg, add a generator creating a
SSDT table representing a CPU topology. Low Power Idle (LPI)
states can also be generated along the CPUs.
This patch-set also adds new functions to generate AML bytecode.

The changes can be seen at: https://github.com/PierreARM/edk2/tree/1449_Create_ssdt_cpu_topology_generator_v1
The results of the CI can be seen at: https://github.com/tianocore/edk2/pull/1746
This patch-set is dependent over the following patch set:
[PATCH v1 00/10] Various DynamicTablesPkg modifications
https://edk2.groups.io/g/devel/message/76929

Pierre Gondois (13):
DynamicTablesPkg: Make AmlNodeGetIntegerValue public
DynamicTablesPkg: AML Code generation for Register()
DynamicTablesPkg: AML Code generation for Resource data EndTag
DynamicTablesPkg: AML code generation for a Package
DynamicTablesPkg: Helper function to compute package length
DynamicTablesPkg: AML code generation for a ResourceTemplate
DynamicTablesPkg: AML code generation for a Method
DynamicTablesPkg: AML code generation to Return a NameString
DynamicTablesPkg: AML code generation for a Method returning a NS
DynamicTablesPkg: AML code generation for a _LPI object
DynamicTablesPkg: AML code generation to add an _LPI state
DynamicTablesPkg: Add CM_ARM_LPI_INFO object
DynamicTablesPkg: SSDT CPU topology and LPI state generator

DynamicTablesPkg/DynamicTables.dsc.inc | 6 +
DynamicTablesPkg/Include/AcpiTableGenerator.h | 7 +-
.../Include/ArmNameSpaceObjects.h | 68 +
.../Include/Library/AmlLib/AmlLib.h | 168 +++
.../SsdtCpuTopologyGenerator.c | 1230 ++++++++++++++++
.../SsdtCpuTopologyGenerator.h | 134 ++
.../SsdtCpuTopologyLibArm.inf | 40 +
.../Library/Common/AmlLib/AmlEncoding/Aml.c | 87 +-
.../Library/Common/AmlLib/AmlEncoding/Aml.h | 47 +-
.../Common/AmlLib/CodeGen/AmlCodeGen.c | 1296 ++++++++++++++++-
.../AmlLib/CodeGen/AmlResourceDataCodeGen.c | 191 +++
.../AmlLib/CodeGen/AmlResourceDataCodeGen.h | 83 ++
.../Library/Common/AmlLib/Utils/AmlUtility.c | 3 +-
.../Library/Common/AmlLib/Utils/AmlUtility.h | 18 +-
.../ConfigurationManagerObjectParser.c | 35 +
15 files changed, 3406 insertions(+), 7 deletions(-)
create mode 100644 DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCpuTopologyLibArm/SsdtCpuTopologyGenerator.c
create mode 100644 DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCpuTopologyLibArm/SsdtCpuTopologyGenerator.h
create mode 100644 DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCpuTopologyLibArm/SsdtCpuTopologyLibArm.inf

--
2.17.1


Re: Help with debugging

Laszlo Ersek
 

On 06/11/21 19:06, Ethin Probst wrote:
Hey all,

So Leif and I have discussed this at length but I thought I'd reach
out to all of you for more help.

I'm having a lot of trouble debugging my UEFI app. Here's how I do things:

- I load the app using uefi-run
(https://github.com/Richard-W/uefi-run) like this (from the main EDK
II directory): uefi-run -b Build/OvmfX64/DEBUG_GCC5/FV/OVMF.fd
Build/OvmfX64/DEBUG_GCC5/X64/Shell.efi -- -M q35 -m 24G -usb -device
qemu-xhci -device usb-audio,audiodev=audio -audiodev alsa,id=audio -s
-debugcon file:../debug.log -global isa-debugcon.iobase=0x402
-nographic
Or:
uefi-run -b Build/OvmfX64/DEBUG_GCC5/FV/OVMF.fd
Build/OvmfX64/DEBUG_GCC5/X64/Shell.efi -- -M q35 -m 24G -usb -device
qemu-xhci -device usb-audio,audiodev=audio -audiodev alsa,id=audio -s
-debugcon stdio -global isa-debugcon.iobase=0x402
Side comment:

OVMF supports virtio-fs, and using virtio-fs could speed up your
develop/build/test cycle.

Assuming your UEFI application does not crash or hang (i.e., assuming it
exits cleanly and you can continue using the same UEFI shell session),
virtio-fs could be a small productivity boost for you, as you wouldn't
have to re-launch QEMU every time.

The idea is to build your application through some platform DSC file as
follows -- note that it need not be an OVMF DSC file, but it may be one,
if you prefer that:

build -a X64 -b NOOPT -p MyAppPkg/MyApp.dsc -t GCC5 \
-m MyAppPkg/MyApp/MyApp.inf

You don't need an FDF file for this, just grab the resultant "MyApp.efi"
binary from the Build directory.

Then copy "MyApp.efi" (on the host side) under the virtio-fs root
directory somewhere. When the copy operation completes (on the host
side), just switch your focus to the guest UEFI shell window, and you
can immediately execute the just-built application.

I find using virtio-fs by far the easiest with libvirt, but you can use
it from the bare QEMU command line, too.

https://libvirt.org/kbase/virtiofs.html
https://virtio-fs.gitlab.io/howto-qemu.html

This assumes that your development environment is Linux-based, as the
virtio-fs daemon (which runs in tandem with QEMU on the host) is Linux-only.

Thanks,
Laszlo


[PATCH v1 10/10] DynamicTablesPkg: Rework AmlResourceDataCodegen.c/h

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Rework all the functions to to have a generic prototype:
- First take take the resource data specific arguments.
E.g.: for a Register(): the AddressSpace, BitWidth, ...
- The penultimate parameter is a NameOpNode. The resource data
created is appended to the ResourceTemplate() contained in the
NameOpNode.
- The last parameter is a pointer holding the created resource data.

A least one of the two last parameter must be provided. One of them can
be omitted. This generic interface allows to either:
- Add the resource data to a NameOpNode. This is a common case for the
Ssdt tables generator.
- Get the created resource data and let the caller place it in an AML
tree.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Include/Library/AmlLib/AmlLib.h | 60 +++--
.../SsdtCmn600Generator.c | 8 +-
.../AmlLib/CodeGen/AmlResourceDataCodeGen.c | 235 +++++++-----------
.../AmlLib/CodeGen/AmlResourceDataCodeGen.h | 67 +++--
4 files changed, 150 insertions(+), 220 deletions(-)

diff --git a/DynamicTablesPkg/Include/Library/AmlLib/AmlLib.h b/DynamicTablesPkg/Include/Library/AmlLib/AmlLib.h
index c40808343fce..6824cf3a6c82 100644
--- a/DynamicTablesPkg/Include/Library/AmlLib/AmlLib.h
+++ b/DynamicTablesPkg/Include/Library/AmlLib/AmlLib.h
@@ -418,41 +418,36 @@ AmlUpdateRdQWord (
IN UINT64 BaseAddressLength
);

-/** Add an Interrupt Resource Data node.
-
- This function creates a Resource Data element corresponding to the
- "Interrupt ()" ASL function, stores it in an AML Data Node.
-
- It then adds it after the input NameOpNode in the list of resource data
- element.
+/** Code generation for the "Interrupt ()" ASL function.

The Resource Data effectively created is an Extended Interrupt Resource
- Data. See ACPI 6.3 specification, s6.4.3.6 "Extended Interrupt Descriptor"
- for more information about Extended Interrupt Resource Data.
+ Data. Cf ACPI 6.4:
+ - s6.4.3.6 "Extended Interrupt Descriptor"
+ - s19.6.64 "Interrupt (Interrupt Resource Descriptor Macro)"

- The Extended Interrupt contains one single interrupt.
-
- This function allocates memory to create a data node. It is the caller's
- responsibility to either:
- - attach this node to an AML tree;
- - delete this node.
+ The created resource data node can be:
+ - appended to the list of resource data elements of the NameOpNode.
+ In such case NameOpNode must be defined by a the "Name ()" ASL statement
+ and initially contain a "ResourceTemplate ()".
+ - returned through the NewRdNode parameter.

@ingroup CodeGenApis

+ @param [in] ResourceConsumer The device consumes the specified interrupt
+ or produces it for use by a child device.
+ @param [in] EdgeTriggered The interrupt is edge triggered or
+ level triggered.
+ @param [in] ActiveLow The interrupt is active-high or active-low.
+ @param [in] Shared The interrupt can be shared with other
+ devices or not (Exclusive).
+ @param [in] IrqList Interrupt list. Must be non-NULL.
+ @param [in] IrqCount Interrupt count. Must be non-zero.
@param [in] NameOpNode NameOp object node defining a named object.
- Must have an OpCode=AML_NAME_OP, SubOpCode=0.
- NameOp object nodes are defined in ASL
- using the "Name ()" function.
- @param [in] ResourceConsumer The device consumes the specified interrupt
- or produces it for use by a child device.
- @param [in] EdgeTriggered The interrupt is edge triggered or
- level triggered.
- @param [in] ActiveLow The interrupt is active-high or active-low.
- @param [in] Shared The interrupt can be shared with other
- devices or not (Exclusive).
- @param [in] IrqList Interrupt list. Must be non-NULL.
- @param [in] IrqCount Interrupt count. Must be non-zero.
-
+ If provided, append the new resource data node
+ to the list of resource data elements of this
+ node.
+ @param [out] NewRdNode If provided and success,
+ contain the created node.

@retval EFI_SUCCESS The function completed successfully.
@retval EFI_INVALID_PARAMETER Invalid parameter.
@@ -460,14 +455,15 @@ AmlUpdateRdQWord (
**/
EFI_STATUS
EFIAPI
-AmlCodeGenAddRdInterrupt (
- IN AML_OBJECT_NODE_HANDLE NameOpNode,
+AmlCodeGenRdInterrupt (
IN BOOLEAN ResourceConsumer,
IN BOOLEAN EdgeTriggered,
IN BOOLEAN ActiveLow,
IN BOOLEAN Shared,
- IN UINT32 * IrqList,
- IN UINT8 IrqCount
+ IN UINT32 *IrqList,
+ IN UINT8 IrqCount,
+ IN AML_OBJECT_NODE_HANDLE NameOpNode, OPTIONAL
+ OUT AML_DATA_NODE_HANDLE *NewRdNode OPTIONAL
);

/** AML code generation for DefinitionBlock.
diff --git a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c
index fb93a5d2e70c..19b7b128a08d 100644
--- a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c
+++ b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c
@@ -338,8 +338,8 @@ FixupCmn600Info (
// Resource Data nodes.
for (Index = 0; Index < Cmn600Info->DtcCount; Index++) {
DtcInt = &Cmn600Info->DtcInterrupt[Index];
- Status = AmlCodeGenAddRdInterrupt (
- NameOpCrsNode,
+
+ Status = AmlCodeGenRdInterrupt (
((DtcInt->Flags &
EFI_ACPI_EXTENDED_INTERRUPT_FLAG_PRODUCER_CONSUMER_MASK) != 0),
((DtcInt->Flags &
@@ -349,7 +349,9 @@ FixupCmn600Info (
((DtcInt->Flags &
EFI_ACPI_EXTENDED_INTERRUPT_FLAG_SHARABLE_MASK) != 0),
(UINT32*)&DtcInt->Interrupt,
- 1
+ 1,
+ NameOpCrsNode,
+ NULL
);
if (EFI_ERROR (Status)) {
goto error_handler;
diff --git a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
index c7348aa5daf7..089597a6c906 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
+++ b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
@@ -24,11 +24,15 @@
If NewRdNode is not NULL, update its value to RdNode.

@param [in] RdNode Newly created Resource Data node.
- @param [in] ParentNode If not NULL, add the generated node
- to the end of the variable list of
- argument of the ParentNode, but
- before the "End Tag" Resource Data.
- Must be a BufferOpNode.
+ RdNode is deleted if an error occurs.
+ @param [in] ParentNode If not NULL, ParentNode must:
+ - be a NameOp node, i.e. have the AML_NAME_OP
+ opcode (cf "Name ()" ASL statement)
+ - contain a list of resource data elements
+ (cf "ResourceTemplate ()" ASL statement)
+ RdNode is then added at the end of the variable
+ list of resource data elements, but before the
+ "End Tag" Resource Data.
@param [out] NewRdNode If not NULL, update the its value to RdNode.

@retval EFI_SUCCESS The function completed successfully.
@@ -43,57 +47,81 @@ LinkRdNode (
OUT AML_DATA_NODE ** NewRdNode
)
{
- EFI_STATUS Status;
- EFI_STATUS Status1;
+ EFI_STATUS Status;
+ EFI_STATUS Status1;
+ AML_OBJECT_NODE *BufferOpNode;

if (NewRdNode != NULL) {
*NewRdNode = RdNode;
}

- // Add RdNode as the last element, but before the EndTag.
if (ParentNode != NULL) {
- Status = AmlAppendRdNode (ParentNode, RdNode);
+ // Check this is a NameOp node.
+ if ((!AmlNodeHasOpCode (ParentNode, AML_NAME_OP, 0))) {
+ ASSERT (0);
+ Status = EFI_INVALID_PARAMETER;
+ goto error_handler;
+ }
+
+ // Get the value which is represented as a BufferOp object node
+ // which is the 2nd fixed argument (i.e. index 1).
+ BufferOpNode = (AML_OBJECT_NODE_HANDLE)AmlGetFixedArgument (
+ ParentNode,
+ EAmlParseIndexTerm1
+ );
+ if ((BufferOpNode == NULL) ||
+ (AmlGetNodeType ((AML_NODE_HANDLE)BufferOpNode) != EAmlNodeObject) ||
+ (!AmlNodeHasOpCode (BufferOpNode, AML_BUFFER_OP, 0))) {
+ ASSERT (0);
+ Status = EFI_INVALID_PARAMETER;
+ goto error_handler;
+ }
+
+ // Add RdNode as the last element, but before the EndTag.
+ Status = AmlAppendRdNode (BufferOpNode, RdNode);
if (EFI_ERROR (Status)) {
ASSERT (0);
- Status1 = AmlDeleteTree ((AML_NODE_HEADER*)RdNode);
- ASSERT_EFI_ERROR (Status1);
- // Return original error.
- return Status;
+ goto error_handler;
}
}

- return EFI_SUCCESS;
+ return Status;
+
+error_handler:
+ Status1 = AmlDeleteTree ((AML_NODE_HEADER*)RdNode);
+ ASSERT_EFI_ERROR (Status1);
+ // Return original error.
+ return Status;
}

/** Code generation for the "Interrupt ()" ASL function.

- This function creates a Resource Data element corresponding to the
- "Interrupt ()" ASL function and stores it in an AML Data Node.
-
The Resource Data effectively created is an Extended Interrupt Resource
- Data. See ACPI 6.3 specification, s6.4.3.6 "Extended Interrupt Descriptor"
- for more information about Extended Interrupt Resource Data.
+ Data. Cf ACPI 6.4:
+ - s6.4.3.6 "Extended Interrupt Descriptor"
+ - s19.6.64 "Interrupt (Interrupt Resource Descriptor Macro)"

- This function allocates memory to create a data node. It is the caller's
- responsibility to either:
- - attach this node to an AML tree;
- - delete this node.
+ The created resource data node can be:
+ - appended to the list of resource data elements of the NameOpNode.
+ In such case NameOpNode must be defined by a the "Name ()" ASL statement
+ and initially contain a "ResourceTemplate ()".
+ - returned through the NewRdNode parameter.

- @param [in] ResourceConsumer The device consumes the specified interrupt
- or produces it for use by a child device.
- @param [in] EdgeTriggered The interrupt is edge triggered or
- level triggered.
- @param [in] ActiveLow The interrupt is active-high or active-low.
- @param [in] Shared The interrupt can be shared with other
- devices or not (Exclusive).
- @param [in] IrqList Interrupt list. Must be non-NULL.
- @param [in] IrqCount Interrupt count. Must be non-zero.
- @param [in] ParentNode If not NULL, add the generated node
- to the end of the variable list of
- argument of the ParentNode, but
- before the "End Tag" Resource Data.
- Must be a BufferOpNode.
- @param [out] NewRdNode If success, contains the generated node.
+ @param [in] ResourceConsumer The device consumes the specified interrupt
+ or produces it for use by a child device.
+ @param [in] EdgeTriggered The interrupt is edge triggered or
+ level triggered.
+ @param [in] ActiveLow The interrupt is active-high or active-low.
+ @param [in] Shared The interrupt can be shared with other
+ devices or not (Exclusive).
+ @param [in] IrqList Interrupt list. Must be non-NULL.
+ @param [in] IrqCount Interrupt count. Must be non-zero.
+ @param [in] NameOpNode NameOp object node defining a named object.
+ If provided, append the new resource data node
+ to the list of resource data elements of this
+ node.
+ @param [out] NewRdNode If provided and success,
+ contain the created node.

@retval EFI_SUCCESS The function completed successfully.
@retval EFI_INVALID_PARAMETER Invalid parameter.
@@ -101,15 +129,15 @@ LinkRdNode (
**/
EFI_STATUS
EFIAPI
-AmlCodeGenInterrupt (
- IN BOOLEAN ResourceConsumer,
- IN BOOLEAN EdgeTriggered,
- IN BOOLEAN ActiveLow,
- IN BOOLEAN Shared,
- IN UINT32 * IrqList,
- IN UINT8 IrqCount,
- IN AML_OBJECT_NODE * ParentNode, OPTIONAL
- OUT AML_DATA_NODE ** NewRdNode OPTIONAL
+AmlCodeGenRdInterrupt (
+ IN BOOLEAN ResourceConsumer,
+ IN BOOLEAN EdgeTriggered,
+ IN BOOLEAN ActiveLow,
+ IN BOOLEAN Shared,
+ IN UINT32 *IrqList,
+ IN UINT8 IrqCount,
+ IN AML_OBJECT_NODE_HANDLE NameOpNode, OPTIONAL
+ OUT AML_DATA_NODE_HANDLE *NewRdNode OPTIONAL
)
{
EFI_STATUS Status;
@@ -120,16 +148,19 @@ AmlCodeGenInterrupt (

if ((IrqList == NULL) ||
(IrqCount == 0) ||
- ((ParentNode == NULL) && (NewRdNode == NULL))) {
+ ((NameOpNode == NULL) && (NewRdNode == NULL))) {
ASSERT (0);
return EFI_INVALID_PARAMETER;
}

+ // Header
RdInterrupt.Header.Header.Bits.Name =
ACPI_LARGE_EXTENDED_IRQ_DESCRIPTOR_NAME;
RdInterrupt.Header.Header.Bits.Type = ACPI_LARGE_ITEM_FLAG;
RdInterrupt.Header.Length = sizeof (EFI_ACPI_EXTENDED_INTERRUPT_DESCRIPTOR) -
sizeof (ACPI_LARGE_RESOURCE_HEADER);
+
+ // Body
RdInterrupt.InterruptVectorFlags = (ResourceConsumer ? BIT0 : 0) |
(EdgeTriggered ? BIT1 : 0) |
(ActiveLow ? BIT2 : 0) |
@@ -153,105 +184,7 @@ AmlCodeGenInterrupt (
return Status;
}

- return LinkRdNode (RdNode, ParentNode, NewRdNode);
-}
-
-/** Add an Interrupt Resource Data node.
-
- This function creates a Resource Data element corresponding to the
- "Interrupt ()" ASL function, stores it in an AML Data Node.
-
- It then adds it after the input NameOpNode in the list of resource data
- element.
-
- The Resource Data effectively created is an Extended Interrupt Resource
- Data. See ACPI 6.3 specification, s6.4.3.6 "Extended Interrupt Descriptor"
- for more information about Extended Interrupt Resource Data.
-
- The Extended Interrupt contains one single interrupt.
-
- This function allocates memory to create a data node. It is the caller's
- responsibility to either:
- - attach this node to an AML tree;
- - delete this node.
-
- Note:
- The named node must be defined using the ASL "Name ()" statement.
- E.g. Name (_CRS, ResourceTemplate () { ... })
- Methods cannot be modified with this function.
-
- @param [in] NameOpNode NameOp object node defining a named object.
- Must have an OpCode=AML_NAME_OP, SubOpCode=0.
- NameOp object nodes are defined in ASL
- using the "Name ()" function.
- @param [in] ResourceConsumer The device consumes the specified interrupt
- or produces it for use by a child device.
- @param [in] EdgeTriggered The interrupt is edge triggered or
- level triggered.
- @param [in] ActiveLow The interrupt is active-high or active-low.
- @param [in] Shared The interrupt can be shared with other
- devices or not (Exclusive).
- @param [in] IrqList Interrupt list. Must be non-NULL.
- @param [in] IrqCount Interrupt count. Must be non-zero.
-
-
- @retval EFI_SUCCESS The function completed successfully.
- @retval EFI_INVALID_PARAMETER Invalid parameter.
- @retval EFI_OUT_OF_RESOURCES Could not allocate memory.
-**/
-EFI_STATUS
-EFIAPI
-AmlCodeGenAddRdInterrupt (
- IN AML_OBJECT_NODE_HANDLE NameOpNode,
- IN BOOLEAN ResourceConsumer,
- IN BOOLEAN EdgeTriggered,
- IN BOOLEAN ActiveLow,
- IN BOOLEAN Shared,
- IN UINT32 * IrqList,
- IN UINT8 IrqCount
- )
-{
- EFI_STATUS Status;
-
- AML_OBJECT_NODE_HANDLE BufferOpNode;
-
- if ((IrqList == NULL) ||
- (IrqCount == 0) ||
- (!AmlNodeHasOpCode (NameOpNode, AML_NAME_OP, 0))) {
- ASSERT (0);
- return EFI_INVALID_PARAMETER;
- }
-
- // Get the value which is represented as a BufferOp object node
- // which is the 2nd fixed argument (i.e. index 1).
- BufferOpNode = (AML_OBJECT_NODE_HANDLE)AmlGetFixedArgument (
- NameOpNode,
- EAmlParseIndexTerm1
- );
- if ((BufferOpNode == NULL) ||
- (AmlGetNodeType ((AML_NODE_HANDLE)BufferOpNode) != EAmlNodeObject) ||
- (!AmlNodeHasOpCode (BufferOpNode, AML_BUFFER_OP, 0))) {
- ASSERT (0);
- return EFI_INVALID_PARAMETER;
- }
-
- // Generate the Extended Interrupt Resource Data node,
- // and attach it as the last variable argument of the BufferOpNode.
- Status = AmlCodeGenInterrupt (
- ResourceConsumer,
- EdgeTriggered,
- ActiveLow,
- Shared,
- IrqList,
- IrqCount,
- BufferOpNode,
- NULL
- );
- if (EFI_ERROR (Status)) {
- ASSERT (0);
- }
-
- return Status;
+ return LinkRdNode (RdNode, NameOpNode, NewRdNode);
}

// DEPRECATED APIS
@@ -316,15 +249,15 @@ AmlCodeGenCrsAddRdInterrupt (
IN UINT8 IrqCount
)
{
- return AmlCodeGenAddRdInterrupt (
- NameOpCrsNode,
- NameOpNode,
+ return AmlCodeGenRdInterrupt (
ResourceConsumer,
EdgeTriggered,
ActiveLow,
Shared,
IrqList,
- IrqCount
+ IrqCount,
+ NameOpCrsNode,
+ NULL
);
}

diff --git a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h
index 08364db4431f..764051e3d7c9 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h
+++ b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.h
@@ -1,7 +1,7 @@
/** @file
AML Resource Data Code Generation.

- Copyright (c) 2019 - 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2019 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent
**/
@@ -11,33 +11,32 @@

/** Code generation for the "Interrupt ()" ASL function.

- This function creates a Resource Data element corresponding to the
- "Interrupt ()" ASL function and stores it in an AML Data Node.
-
The Resource Data effectively created is an Extended Interrupt Resource
- Data. See ACPI 6.3 specification, s6.4.3.6 "Extended Interrupt Descriptor"
- for more information about Extended Interrupt Resource Data.
+ Data. Cf ACPI 6.4:
+ - s6.4.3.6 "Extended Interrupt Descriptor"
+ - s19.6.64 "Interrupt (Interrupt Resource Descriptor Macro)"

- This function allocates memory to create a data node. It is the caller's
- responsibility to either:
- - attach this node to an AML tree;
- - delete this node.
+ The created resource data node can be:
+ - appended to the list of resource data elements of the NameOpNode.
+ In such case NameOpNode must be defined by a the "Name ()" ASL statement
+ and initially contain a "ResourceTemplate ()".
+ - returned through the NewRdNode parameter.

- @param [in] ResourceConsumer The device consumes the specified interrupt
- or produces it for use by a child device.
- @param [in] EdgeTriggered The interrupt is edge triggered or
- level triggered.
- @param [in] ActiveLow The interrupt is active-high or active-low.
- @param [in] Shared The interrupt can be shared with other
- devices or not (Exclusive).
- @param [in] IrqList Interrupt list. Must be non-NULL.
- @param [in] IrqCount Interrupt count. Must be non-zero.
- @param [in] ParentNode If not NULL, add the generated node
- to the end of the variable list of
- argument of the ParentNode, but
- before the "End Tag" Resource Data.
- Must be a BufferOpNode.
- @param [out] NewRdNode If success, contains the generated node.
+ @param [in] ResourceConsumer The device consumes the specified interrupt
+ or produces it for use by a child device.
+ @param [in] EdgeTriggered The interrupt is edge triggered or
+ level triggered.
+ @param [in] ActiveLow The interrupt is active-high or active-low.
+ @param [in] Shared The interrupt can be shared with other
+ devices or not (Exclusive).
+ @param [in] IrqList Interrupt list. Must be non-NULL.
+ @param [in] IrqCount Interrupt count. Must be non-zero.
+ @param [in] NameOpNode NameOp object node defining a named object.
+ If provided, append the new resource data node
+ to the list of resource data elements of this
+ node.
+ @param [out] NewRdNode If provided and success,
+ contain the created node.

@retval EFI_SUCCESS The function completed successfully.
@retval EFI_INVALID_PARAMETER Invalid parameter.
@@ -45,15 +44,15 @@
**/
EFI_STATUS
EFIAPI
-AmlCodeGenInterrupt (
- IN BOOLEAN ResourceConsumer,
- IN BOOLEAN EdgeTriggered,
- IN BOOLEAN ActiveLow,
- IN BOOLEAN Shared,
- IN UINT32 * IrqList,
- IN UINT8 IrqCount,
- IN AML_OBJECT_NODE * ParentNode, OPTIONAL
- OUT AML_DATA_NODE ** NewRdNode OPTIONAL
+AmlCodeGenRdInterrupt (
+ IN BOOLEAN ResourceConsumer,
+ IN BOOLEAN EdgeTriggered,
+ IN BOOLEAN ActiveLow,
+ IN BOOLEAN Shared,
+ IN UINT32 *IrqList,
+ IN UINT8 IrqCount,
+ IN AML_OBJECT_NODE_HANDLE NameOpNode, OPTIONAL
+ OUT AML_DATA_NODE_HANDLE *NewRdNode OPTIONAL
);

#endif // AML_RESOURCE_DATA_CODE_GEN_H_
--
2.17.1


[PATCH v1 09/10] DynamicTablesPkg: Deprecate Crs specific methods in AmlLib

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Some functions in the AmlLib have 'Crs' in their name and can only
be applied to '_CRS' AML objects. To re-use them on AML objects that
have different names:
- Rename them and remove the '_CRS' name check.
- Create aliases having of the 'Crs' function prototypes. These
aliases are available when DISABLE_NEW_DEPRECATED_INTERFACES
is not defined. They will be deprecated in a near future.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Include/Library/AmlLib/AmlLib.h | 189 +++++++++++++++---
.../SsdtCmn600Generator.c | 6 +-
.../Library/Common/AmlLib/Api/AmlApi.c | 147 +++++++++++---
.../AmlLib/CodeGen/AmlResourceDataCodeGen.c | 105 ++++++++--
.../SsdtSerialPortFixupLib.c | 4 +-
5 files changed, 371 insertions(+), 80 deletions(-)

diff --git a/DynamicTablesPkg/Include/Library/AmlLib/AmlLib.h b/DynamicTablesPkg/Include/Library/AmlLib/AmlLib.h
index 1dcb93861436..c40808343fce 100644
--- a/DynamicTablesPkg/Include/Library/AmlLib/AmlLib.h
+++ b/DynamicTablesPkg/Include/Library/AmlLib/AmlLib.h
@@ -1,7 +1,7 @@
/** @file
AML Lib.

- Copyright (c) 2019 - 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2019 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent
**/
@@ -301,7 +301,7 @@ AmlNameOpUpdateString (
IN CONST CHAR8 * NewName
);

-/** Get the first Resource Data element contained in a "_CRS" object.
+/** Get the first Resource Data element contained in a named object.

In the following ASL code, the function will return the Resource Data
node corresponding to the "QWordMemory ()" ASL macro.
@@ -312,27 +312,26 @@ AmlNameOpUpdateString (
)

Note:
- - The "_CRS" object must be declared using ASL "Name (Declare Named Object)".
- - "_CRS" declared using ASL "Method (Declare Control Method)" is not
- supported.
+ "_CRS" names defined as methods are not handled by this function.
+ They must be defined as names, using the "Name ()" statement.

@ingroup UserApis

- @param [in] NameOpCrsNode NameOp object node defining a "_CRS" object.
- Must have an OpCode=AML_NAME_OP, SubOpCode=0.
- NameOp object nodes are defined in ASL
- using the "Name ()" function.
- @param [out] OutRdNode Pointer to the first Resource Data element of
- the "_CRS" object. A Resource Data element
- is stored in a data node.
+ @param [in] NameOpNode NameOp object node defining a named object.
+ Must have an OpCode=AML_NAME_OP, SubOpCode=0.
+ NameOp object nodes are defined in ASL
+ using the "Name ()" function.
+ @param [out] OutRdNode Pointer to the first Resource Data element of
+ the named object. A Resource Data element
+ is stored in a data node.

@retval EFI_SUCCESS The function completed successfully.
@retval EFI_INVALID_PARAMETER Invalid parameter.
**/
EFI_STATUS
EFIAPI
-AmlNameOpCrsGetFirstRdNode (
- IN AML_OBJECT_NODE_HANDLE NameOpCrsNode,
+AmlNameOpGetFirstRdNode (
+ IN AML_OBJECT_NODE_HANDLE NameOpNode,
OUT AML_DATA_NODE_HANDLE * OutRdNode
);

@@ -347,13 +346,14 @@ AmlNameOpCrsGetFirstRdNode (
}
)

- The CurrRdNode Resource Data node must be defined in an object named "_CRS"
- and defined by a "Name ()" ASL function.
+ Note:
+ "_CRS" names defined as methods are not handled by this function.
+ They must be defined as names, using the "Name ()" statement.

@ingroup UserApis

@param [in] CurrRdNode Pointer to the current Resource Data element of
- the "_CRS" variable.
+ the named object.
@param [out] OutRdNode Pointer to the Resource Data element following
the CurrRdNode.
Contain a NULL pointer if CurrRdNode is the
@@ -366,7 +366,7 @@ AmlNameOpCrsGetFirstRdNode (
**/
EFI_STATUS
EFIAPI
-AmlNameOpCrsGetNextRdNode (
+AmlNameOpGetNextRdNode (
IN AML_DATA_NODE_HANDLE CurrRdNode,
OUT AML_DATA_NODE_HANDLE * OutRdNode
);
@@ -423,7 +423,7 @@ AmlUpdateRdQWord (
This function creates a Resource Data element corresponding to the
"Interrupt ()" ASL function, stores it in an AML Data Node.

- It then adds it after the input CurrRdNode in the list of resource data
+ It then adds it after the input NameOpNode in the list of resource data
element.

The Resource Data effectively created is an Extended Interrupt Resource
@@ -437,14 +437,9 @@ AmlUpdateRdQWord (
- attach this node to an AML tree;
- delete this node.

- Note: The _CRS node must be defined using the ASL Name () function.
- e.g. Name (_CRS, ResourceTemplate () {
- ...
- }
+ @ingroup CodeGenApis

- @ingroup UserApis
-
- @param [in] NameOpCrsNode NameOp object node defining a "_CRS" object.
+ @param [in] NameOpNode NameOp object node defining a named object.
Must have an OpCode=AML_NAME_OP, SubOpCode=0.
NameOp object nodes are defined in ASL
using the "Name ()" function.
@@ -465,8 +460,8 @@ AmlUpdateRdQWord (
**/
EFI_STATUS
EFIAPI
-AmlCodeGenCrsAddRdInterrupt (
- IN AML_OBJECT_NODE_HANDLE NameOpCrsNode,
+AmlCodeGenAddRdInterrupt (
+ IN AML_OBJECT_NODE_HANDLE NameOpNode,
IN BOOLEAN ResourceConsumer,
IN BOOLEAN EdgeTriggered,
IN BOOLEAN ActiveLow,
@@ -628,4 +623,142 @@ AmlCodeGenScope (
OUT AML_OBJECT_NODE_HANDLE * NewObjectNode OPTIONAL
);

+// DEPRECATED APIS
+#ifndef DISABLE_NEW_DEPRECATED_INTERFACES
+
+/** DEPRECATED API
+
+ Get the first Resource Data element contained in a "_CRS" object.
+
+ In the following ASL code, the function will return the Resource Data
+ node corresponding to the "QWordMemory ()" ASL macro.
+ Name (_CRS, ResourceTemplate() {
+ QWordMemory (...) {...},
+ Interrupt (...) {...}
+ }
+ )
+
+ Note:
+ - The "_CRS" object must be declared using ASL "Name (Declare Named Object)".
+ - "_CRS" declared using ASL "Method (Declare Control Method)" is not
+ supported.
+
+ @ingroup UserApis
+
+ @param [in] NameOpCrsNode NameOp object node defining a "_CRS" object.
+ Must have an OpCode=AML_NAME_OP, SubOpCode=0.
+ NameOp object nodes are defined in ASL
+ using the "Name ()" function.
+ @param [out] OutRdNode Pointer to the first Resource Data element of
+ the "_CRS" object. A Resource Data element
+ is stored in a data node.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+**/
+EFI_STATUS
+EFIAPI
+AmlNameOpCrsGetFirstRdNode (
+ IN AML_OBJECT_NODE_HANDLE NameOpCrsNode,
+ OUT AML_DATA_NODE_HANDLE * OutRdNode
+ );
+
+/** DEPRECATED API
+
+ Get the Resource Data element following the CurrRdNode Resource Data.
+
+ In the following ASL code, if CurrRdNode corresponds to the first
+ "QWordMemory ()" ASL macro, the function will return the Resource Data
+ node corresponding to the "Interrupt ()" ASL macro.
+ Name (_CRS, ResourceTemplate() {
+ QwordMemory (...) {...},
+ Interrupt (...) {...}
+ }
+ )
+
+ The CurrRdNode Resource Data node must be defined in an object named "_CRS"
+ and defined by a "Name ()" ASL function.
+
+ @ingroup UserApis
+
+ @param [in] CurrRdNode Pointer to the current Resource Data element of
+ the "_CRS" variable.
+ @param [out] OutRdNode Pointer to the Resource Data element following
+ the CurrRdNode.
+ Contain a NULL pointer if CurrRdNode is the
+ last Resource Data element in the list.
+ The "End Tag" is not considered as a resource
+ data element and is not returned.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+**/
+EFI_STATUS
+EFIAPI
+AmlNameOpCrsGetNextRdNode (
+ IN AML_DATA_NODE_HANDLE CurrRdNode,
+ OUT AML_DATA_NODE_HANDLE * OutRdNode
+ );
+
+/** DEPRECATED API
+
+ Add an Interrupt Resource Data node.
+
+ This function creates a Resource Data element corresponding to the
+ "Interrupt ()" ASL function, stores it in an AML Data Node.
+
+ It then adds it after the input CurrRdNode in the list of resource data
+ element.
+
+ The Resource Data effectively created is an Extended Interrupt Resource
+ Data. See ACPI 6.3 specification, s6.4.3.6 "Extended Interrupt Descriptor"
+ for more information about Extended Interrupt Resource Data.
+
+ The Extended Interrupt contains one single interrupt.
+
+ This function allocates memory to create a data node. It is the caller's
+ responsibility to either:
+ - attach this node to an AML tree;
+ - delete this node.
+
+ Note: The _CRS node must be defined using the ASL Name () function.
+ e.g. Name (_CRS, ResourceTemplate () {
+ ...
+ }
+
+ @ingroup CodeGenApis
+
+ @param [in] NameOpCrsNode NameOp object node defining a "_CRS" object.
+ Must have an OpCode=AML_NAME_OP, SubOpCode=0.
+ NameOp object nodes are defined in ASL
+ using the "Name ()" function.
+ @param [in] ResourceConsumer The device consumes the specified interrupt
+ or produces it for use by a child device.
+ @param [in] EdgeTriggered The interrupt is edge triggered or
+ level triggered.
+ @param [in] ActiveLow The interrupt is active-high or active-low.
+ @param [in] Shared The interrupt can be shared with other
+ devices or not (Exclusive).
+ @param [in] IrqList Interrupt list. Must be non-NULL.
+ @param [in] IrqCount Interrupt count. Must be non-zero.
+
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+ @retval EFI_OUT_OF_RESOURCES Could not allocate memory.
+**/
+EFI_STATUS
+EFIAPI
+AmlCodeGenCrsAddRdInterrupt (
+ IN AML_OBJECT_NODE_HANDLE NameOpCrsNode,
+ IN BOOLEAN ResourceConsumer,
+ IN BOOLEAN EdgeTriggered,
+ IN BOOLEAN ActiveLow,
+ IN BOOLEAN Shared,
+ IN UINT32 * IrqList,
+ IN UINT8 IrqCount
+ );
+
+#endif // DISABLE_NEW_DEPRECATED_INTERFACES
+
#endif // AML_LIB_H_
diff --git a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c
index cc730cd90fea..fb93a5d2e70c 100644
--- a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c
+++ b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c
@@ -286,7 +286,7 @@ FixupCmn600Info (

// Get the first Rd node in the "_CRS" object.
// This is the PERIPHBASE node.
- Status = AmlNameOpCrsGetFirstRdNode (NameOpCrsNode, &CmnPeriphBaseRdNode);
+ Status = AmlNameOpGetFirstRdNode (NameOpCrsNode, &CmnPeriphBaseRdNode);
if (EFI_ERROR (Status)) {
goto error_handler;
}
@@ -309,7 +309,7 @@ FixupCmn600Info (
// Get the QWord node corresponding to the ROOTNODEBASE.
// It is the second Resource Data element in the BufferNode's
// variable list of arguments.
- Status = AmlNameOpCrsGetNextRdNode (
+ Status = AmlNameOpGetNextRdNode (
CmnPeriphBaseRdNode,
&CmnRootNodeBaseRdNode
);
@@ -338,7 +338,7 @@ FixupCmn600Info (
// Resource Data nodes.
for (Index = 0; Index < Cmn600Info->DtcCount; Index++) {
DtcInt = &Cmn600Info->DtcInterrupt[Index];
- Status = AmlCodeGenCrsAddRdInterrupt (
+ Status = AmlCodeGenAddRdInterrupt (
NameOpCrsNode,
((DtcInt->Flags &
EFI_ACPI_EXTENDED_INTERRUPT_FLAG_PRODUCER_CONSUMER_MASK) != 0),
diff --git a/DynamicTablesPkg/Library/Common/AmlLib/Api/AmlApi.c b/DynamicTablesPkg/Library/Common/AmlLib/Api/AmlApi.c
index fdf04acc6212..6f9e3f6f2805 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/Api/AmlApi.c
+++ b/DynamicTablesPkg/Library/Common/AmlLib/Api/AmlApi.c
@@ -1,7 +1,7 @@
/** @file
AML Api.

- Copyright (c) 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2020 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent
**/
@@ -222,7 +222,7 @@ AmlNameOpUpdateString (
return Status;
}

-/** Get the first Resource Data element contained in a "_CRS" object.
+/** Get the first Resource Data element contained in a named object.

In the following ASL code, the function will return the Resource Data
node corresponding to the "QWordMemory ()" ASL macro.
@@ -233,35 +233,33 @@ AmlNameOpUpdateString (
)

Note:
- - The "_CRS" object must be declared using ASL "Name (Declare Named Object)".
- - "_CRS" declared using ASL "Method (Declare Control Method)" is not
- supported.
+ "_CRS" names defined as methods are not handled by this function.
+ They must be defined as names, using the "Name ()" statement.

- @param [in] NameOpCrsNode NameOp object node defining a "_CRS" object.
- Must have an OpCode=AML_NAME_OP, SubOpCode=0.
- NameOp object nodes are defined in ASL
- using the "Name ()" function.
- @param [out] OutRdNode Pointer to the first Resource Data element of
- the "_CRS" object. A Resource Data element
- is stored in a data node.
+ @param [in] NameOpNode NameOp object node defining a named object.
+ Must have an OpCode=AML_NAME_OP, SubOpCode=0.
+ NameOp object nodes are defined in ASL
+ using the "Name ()" function.
+ @param [out] OutRdNode Pointer to the first Resource Data element of
+ the named object. A Resource Data element
+ is stored in a data node.

@retval EFI_SUCCESS The function completed successfully.
@retval EFI_INVALID_PARAMETER Invalid parameter.
**/
EFI_STATUS
EFIAPI
-AmlNameOpCrsGetFirstRdNode (
- IN AML_OBJECT_NODE_HANDLE NameOpCrsNode,
+AmlNameOpGetFirstRdNode (
+ IN AML_OBJECT_NODE_HANDLE NameOpNode,
OUT AML_DATA_NODE_HANDLE * OutRdNode
)
{
AML_OBJECT_NODE_HANDLE BufferOpNode;
AML_DATA_NODE_HANDLE FirstRdNode;

- if ((NameOpCrsNode == NULL) ||
- (AmlGetNodeType ((AML_NODE_HANDLE)NameOpCrsNode) != EAmlNodeObject) ||
- (!AmlNodeHasOpCode (NameOpCrsNode, AML_NAME_OP, 0)) ||
- (!AmlNameOpCompareName (NameOpCrsNode, "_CRS")) ||
+ if ((NameOpNode == NULL) ||
+ (AmlGetNodeType ((AML_NODE_HANDLE)NameOpNode) != EAmlNodeObject) ||
+ (!AmlNodeHasOpCode (NameOpNode, AML_NAME_OP, 0)) ||
(OutRdNode == NULL)) {
ASSERT (0);
return EFI_INVALID_PARAMETER;
@@ -269,10 +267,10 @@ AmlNameOpCrsGetFirstRdNode (

*OutRdNode = NULL;

- // Get the _CRS value which is represented as a BufferOp object node
- // which is the 2nd fixed argument (i.e. index 1).
+ // Get the value of the variable which is represented as a BufferOp object
+ // node which is the 2nd fixed argument (i.e. index 1).
BufferOpNode = (AML_OBJECT_NODE_HANDLE)AmlGetFixedArgument (
- NameOpCrsNode,
+ NameOpNode,
EAmlParseIndexTerm1
);
if ((BufferOpNode == NULL) ||
@@ -310,11 +308,12 @@ AmlNameOpCrsGetFirstRdNode (
}
)

- The CurrRdNode Resource Data node must be defined in an object named "_CRS"
- and defined by a "Name ()" ASL function.
+ Note:
+ "_CRS" names defined as methods are not handled by this function.
+ They must be defined as names, using the "Name ()" statement.

@param [in] CurrRdNode Pointer to the current Resource Data element of
- the "_CRS" object.
+ the named object.
@param [out] OutRdNode Pointer to the Resource Data element following
the CurrRdNode.
Contain a NULL pointer if CurrRdNode is the
@@ -327,12 +326,12 @@ AmlNameOpCrsGetFirstRdNode (
**/
EFI_STATUS
EFIAPI
-AmlNameOpCrsGetNextRdNode (
+AmlNameOpGetNextRdNode (
IN AML_DATA_NODE_HANDLE CurrRdNode,
OUT AML_DATA_NODE_HANDLE * OutRdNode
)
{
- AML_OBJECT_NODE_HANDLE NameOpCrsNode;
+ AML_OBJECT_NODE_HANDLE NameOpNode;
AML_OBJECT_NODE_HANDLE BufferOpNode;

if ((CurrRdNode == NULL) ||
@@ -356,12 +355,11 @@ AmlNameOpCrsGetNextRdNode (
}

// The parent of the BufferOpNode must be a NameOp node.
- NameOpCrsNode = (AML_OBJECT_NODE_HANDLE)AmlGetParent (
- (AML_NODE_HANDLE)BufferOpNode
- );
- if ((NameOpCrsNode == NULL) ||
- (!AmlNodeHasOpCode (NameOpCrsNode, AML_NAME_OP, 0)) ||
- (!AmlNameOpCompareName (NameOpCrsNode, "_CRS"))) {
+ NameOpNode = (AML_OBJECT_NODE_HANDLE)AmlGetParent (
+ (AML_NODE_HANDLE)BufferOpNode
+ );
+ if ((NameOpNode == NULL) ||
+ (!AmlNodeHasOpCode (NameOpNode, AML_NAME_OP, 0))) {
ASSERT (0);
return EFI_INVALID_PARAMETER;
}
@@ -380,3 +378,88 @@ AmlNameOpCrsGetNextRdNode (

return EFI_SUCCESS;
}
+
+// DEPRECATED APIS
+#ifndef DISABLE_NEW_DEPRECATED_INTERFACES
+
+/** DEPRECATED API
+
+ Get the first Resource Data element contained in a "_CRS" object.
+
+ In the following ASL code, the function will return the Resource Data
+ node corresponding to the "QWordMemory ()" ASL macro.
+ Name (_CRS, ResourceTemplate() {
+ QWordMemory (...) {...},
+ Interrupt (...) {...}
+ }
+ )
+
+ Note:
+ - The "_CRS" object must be declared using ASL "Name (Declare Named Object)".
+ - "_CRS" declared using ASL "Method (Declare Control Method)" is not
+ supported.
+
+ @ingroup UserApis
+
+ @param [in] NameOpCrsNode NameOp object node defining a "_CRS" object.
+ Must have an OpCode=AML_NAME_OP, SubOpCode=0.
+ NameOp object nodes are defined in ASL
+ using the "Name ()" function.
+ @param [out] OutRdNode Pointer to the first Resource Data element of
+ the "_CRS" object. A Resource Data element
+ is stored in a data node.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+**/
+EFI_STATUS
+EFIAPI
+AmlNameOpCrsGetFirstRdNode (
+ IN AML_OBJECT_NODE_HANDLE NameOpCrsNode,
+ OUT AML_DATA_NODE_HANDLE * OutRdNode
+ )
+{
+ return AmlNameOpGetFirstRdNode (NameOpCrsNode, OutRdNode);
+}
+
+/** DEPRECATED API
+
+ Get the Resource Data element following the CurrRdNode Resource Data.
+
+ In the following ASL code, if CurrRdNode corresponds to the first
+ "QWordMemory ()" ASL macro, the function will return the Resource Data
+ node corresponding to the "Interrupt ()" ASL macro.
+ Name (_CRS, ResourceTemplate() {
+ QwordMemory (...) {...},
+ Interrupt (...) {...}
+ }
+ )
+
+ The CurrRdNode Resource Data node must be defined in an object named "_CRS"
+ and defined by a "Name ()" ASL function.
+
+ @ingroup UserApis
+
+ @param [in] CurrRdNode Pointer to the current Resource Data element of
+ the "_CRS" variable.
+ @param [out] OutRdNode Pointer to the Resource Data element following
+ the CurrRdNode.
+ Contain a NULL pointer if CurrRdNode is the
+ last Resource Data element in the list.
+ The "End Tag" is not considered as a resource
+ data element and is not returned.
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+**/
+EFI_STATUS
+EFIAPI
+AmlNameOpCrsGetNextRdNode (
+ IN AML_DATA_NODE_HANDLE CurrRdNode,
+ OUT AML_DATA_NODE_HANDLE * OutRdNode
+ )
+{
+ return AmlNameOpGetNextRdNode (CurrRdNode, OutRdNode);
+}
+
+#endif // DISABLE_NEW_DEPRECATED_INTERFACES
diff --git a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
index d40a27410dd6..c7348aa5daf7 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
+++ b/DynamicTablesPkg/Library/Common/AmlLib/CodeGen/AmlResourceDataCodeGen.c
@@ -1,7 +1,7 @@
/** @file
AML Resource Data Code Generation.

- Copyright (c) 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2020 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent

@@ -161,7 +161,7 @@ AmlCodeGenInterrupt (
This function creates a Resource Data element corresponding to the
"Interrupt ()" ASL function, stores it in an AML Data Node.

- It then adds it after the input CurrRdNode in the list of resource data
+ It then adds it after the input NameOpNode in the list of resource data
element.

The Resource Data effectively created is an Extended Interrupt Resource
@@ -175,12 +175,12 @@ AmlCodeGenInterrupt (
- attach this node to an AML tree;
- delete this node.

- Note: The _CRS node must be defined using the ASL Name () function.
- e.g. Name (_CRS, ResourceTemplate () {
- ...
- }
+ Note:
+ The named node must be defined using the ASL "Name ()" statement.
+ E.g. Name (_CRS, ResourceTemplate () { ... })
+ Methods cannot be modified with this function.

- @param [in] NameOpCrsNode NameOp object node defining a "_CRS" object.
+ @param [in] NameOpNode NameOp object node defining a named object.
Must have an OpCode=AML_NAME_OP, SubOpCode=0.
NameOp object nodes are defined in ASL
using the "Name ()" function.
@@ -201,8 +201,8 @@ AmlCodeGenInterrupt (
**/
EFI_STATUS
EFIAPI
-AmlCodeGenCrsAddRdInterrupt (
- IN AML_OBJECT_NODE_HANDLE NameOpCrsNode,
+AmlCodeGenAddRdInterrupt (
+ IN AML_OBJECT_NODE_HANDLE NameOpNode,
IN BOOLEAN ResourceConsumer,
IN BOOLEAN EdgeTriggered,
IN BOOLEAN ActiveLow,
@@ -215,18 +215,17 @@ AmlCodeGenCrsAddRdInterrupt (

AML_OBJECT_NODE_HANDLE BufferOpNode;

- if ((IrqList == NULL) ||
- (IrqCount == 0) ||
- (!AmlNodeHasOpCode (NameOpCrsNode, AML_NAME_OP, 0)) ||
- (!AmlNameOpCompareName (NameOpCrsNode, "_CRS"))) {
+ if ((IrqList == NULL) ||
+ (IrqCount == 0) ||
+ (!AmlNodeHasOpCode (NameOpNode, AML_NAME_OP, 0))) {
ASSERT (0);
return EFI_INVALID_PARAMETER;
}

- // Get the _CRS value which is represented as a BufferOp object node
+ // Get the value which is represented as a BufferOp object node
// which is the 2nd fixed argument (i.e. index 1).
BufferOpNode = (AML_OBJECT_NODE_HANDLE)AmlGetFixedArgument (
- NameOpCrsNode,
+ NameOpNode,
EAmlParseIndexTerm1
);
if ((BufferOpNode == NULL) ||
@@ -254,3 +253,79 @@ AmlCodeGenCrsAddRdInterrupt (

return Status;
}
+
+// DEPRECATED APIS
+#ifndef DISABLE_NEW_DEPRECATED_INTERFACES
+
+/** DEPRECATED API
+
+ Add an Interrupt Resource Data node.
+
+ This function creates a Resource Data element corresponding to the
+ "Interrupt ()" ASL function, stores it in an AML Data Node.
+
+ It then adds it after the input CurrRdNode in the list of resource data
+ element.
+
+ The Resource Data effectively created is an Extended Interrupt Resource
+ Data. See ACPI 6.3 specification, s6.4.3.6 "Extended Interrupt Descriptor"
+ for more information about Extended Interrupt Resource Data.
+
+ The Extended Interrupt contains one single interrupt.
+
+ This function allocates memory to create a data node. It is the caller's
+ responsibility to either:
+ - attach this node to an AML tree;
+ - delete this node.
+
+ Note: The _CRS node must be defined using the ASL Name () function.
+ e.g. Name (_CRS, ResourceTemplate () {
+ ...
+ }
+
+ @ingroup UserApis
+
+ @param [in] NameOpCrsNode NameOp object node defining a "_CRS" object.
+ Must have an OpCode=AML_NAME_OP, SubOpCode=0.
+ NameOp object nodes are defined in ASL
+ using the "Name ()" function.
+ @param [in] ResourceConsumer The device consumes the specified interrupt
+ or produces it for use by a child device.
+ @param [in] EdgeTriggered The interrupt is edge triggered or
+ level triggered.
+ @param [in] ActiveLow The interrupt is active-high or active-low.
+ @param [in] Shared The interrupt can be shared with other
+ devices or not (Exclusive).
+ @param [in] IrqList Interrupt list. Must be non-NULL.
+ @param [in] IrqCount Interrupt count. Must be non-zero.
+
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+ @retval EFI_OUT_OF_RESOURCES Could not allocate memory.
+**/
+EFI_STATUS
+EFIAPI
+AmlCodeGenCrsAddRdInterrupt (
+ IN AML_OBJECT_NODE_HANDLE NameOpCrsNode,
+ IN BOOLEAN ResourceConsumer,
+ IN BOOLEAN EdgeTriggered,
+ IN BOOLEAN ActiveLow,
+ IN BOOLEAN Shared,
+ IN UINT32 * IrqList,
+ IN UINT8 IrqCount
+ )
+{
+ return AmlCodeGenAddRdInterrupt (
+ NameOpCrsNode,
+ NameOpNode,
+ ResourceConsumer,
+ EdgeTriggered,
+ ActiveLow,
+ Shared,
+ IrqList,
+ IrqCount
+ );
+}
+
+#endif // DISABLE_NEW_DEPRECATED_INTERFACES
diff --git a/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.c b/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.c
index 8c77f172b795..6966410b2c34 100644
--- a/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.c
+++ b/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.c
@@ -275,7 +275,7 @@ FixupCrs (
}

// Get the first Rd node in the "_CRS" object.
- Status = AmlNameOpCrsGetFirstRdNode (NameOpCrsNode, &QWordRdNode);
+ Status = AmlNameOpGetFirstRdNode (NameOpCrsNode, &QWordRdNode);
if (EFI_ERROR (Status)) {
return Status;
}
@@ -298,7 +298,7 @@ FixupCrs (
// Get the Interrupt node.
// It is the second Resource Data element in the NameOpCrsNode's
// variable list of arguments.
- Status = AmlNameOpCrsGetNextRdNode (QWordRdNode, &InterruptRdNode);
+ Status = AmlNameOpGetNextRdNode (QWordRdNode, &InterruptRdNode);
if (EFI_ERROR (Status)) {
return Status;
}
--
2.17.1


[PATCH v1 08/10] DynamicTablesPkg: Update DynamicTablesPkg.ci.yaml

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

To prepare edk2 upstream CI for incoming modifications:
1- Disable the Ecc check 9005:
"Only Doxygen commands '@bug', '@todo', [...], '@{', '@}'
are allowed to mark the code Unknown doxygen command [...]"
2- Disable the Ecc check 8003 for the following keyword:
"DISABLE_NEW_DEPRECATED_INTERFACES"
Indeed, this error has been corrected on the latest version of
BaseTools, but is still triggered when using the older python
packages containing the BaseTools.
3- Add word exceptions for the cspell tool.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
DynamicTablesPkg/DynamicTablesPkg.ci.yaml | 29 +++++++++++++++++++++++
1 file changed, 29 insertions(+)

diff --git a/DynamicTablesPkg/DynamicTablesPkg.ci.yaml b/DynamicTablesPkg/DynamicTablesPkg.ci.yaml
index 211615bc80e2..bfa282926e48 100644
--- a/DynamicTablesPkg/DynamicTablesPkg.ci.yaml
+++ b/DynamicTablesPkg/DynamicTablesPkg.ci.yaml
@@ -5,6 +5,28 @@
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
{
+ "EccCheck": {
+ ## Exception sample looks like below:
+ ## "ExceptionList": [
+ ## "<ErrorID>", "<KeyWord>"
+ ## ]
+ "ExceptionList": [
+ # "The #ifndef at the start of an include file should use
+ # both prefix and postfix underscore characters, '_'"
+ # This error is not triggered for the latest BaseTools code.
+ # @TODO The error should be re-enabled when the python packages
+ # containing the BaseTools are updated to the latest version.
+ "8003", "DISABLE_NEW_DEPRECATED_INTERFACES",
+ "9005", "@defgroup", # Use extra Doxygen commands
+ "9005", "@ingroup", # Use extra Doxygen commands
+ "9005", "@mainpage", # Use extra Doxygen commands
+ "9005", "@ref", # Use extra Doxygen commands
+ ],
+ ## Both file path and directory path are accepted.
+ "IgnoreFiles": [
+ ]
+ },
+
## options defined .pytool/Plugin/CompilerPlugin
"CompilerPlugin": {
"DscPath": "DynamicTablesPkg.dsc"
@@ -23,6 +45,7 @@
## options defined .pytool/Plugin/DependencyCheck
"DependencyCheck": {
"AcceptableDependencies": [
+ "ArmPkg/ArmPkg.dec",
"ArmPlatformPkg/ArmPlatformPkg.dec",
"EmbeddedPkg/EmbeddedPkg.dec",
"DynamicTablesPkg/DynamicTablesPkg.dec",
@@ -77,19 +100,25 @@
"CCIDX",
"CCSIDR",
"countof",
+ "edynamic",
"EOBJECT",
"invoc",
+ "ITARGETSR",
"GTBLOCK",
"lgreater",
"lless",
"MPIDR",
"PERIPHBASE",
+ "phandle",
"pytool",
+ "Rdword",
"Roadmap",
"ROOTNODEBASE",
"ssdtcmn",
"ssdtserialporttemplate",
"SMMUV",
+ "ssdtpcieosctemplate",
+ "SSDTPC",
"standardised",
"TABLEEX",
"TNSID",
--
2.17.1


[PATCH v1 07/10] DynamicTablesPkg: Use %a formatter in AmlDbgPrint

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

The correct formatter to print a CHAR8 char in edk2 is '%a'.
Replace the '%s' formatters by '%a'.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Common/AmlLib/AmlDbgPrint/AmlDbgPrint.c | 16 ++++++++--------
1 file changed, 8 insertions(+), 8 deletions(-)

diff --git a/DynamicTablesPkg/Library/Common/AmlLib/AmlDbgPrint/AmlDbgPrint.c b/DynamicTablesPkg/Library/Common/AmlLib/AmlDbgPrint/AmlDbgPrint.c
index 00a61a2fe63a..7f4cd3404dbb 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/AmlDbgPrint/AmlDbgPrint.c
+++ b/DynamicTablesPkg/Library/Common/AmlLib/AmlDbgPrint/AmlDbgPrint.c
@@ -2,7 +2,7 @@
AML Print Function.

Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved. <BR>
- Copyright (c) 2019 - 2020, Arm Limited. All rights reserved.<BR>
+ Copyright (c) 2019 - 2021, Arm Limited. All rights reserved.<BR>

SPDX-License-Identifier: BSD-2-Clause-Patent
**/
@@ -199,7 +199,7 @@ AmlDbgPrintNodeHeader (

DEBUG ((
DEBUG_INFO,
- "%3d | %-15s | ",
+ "%3d | %-15a | ",
Level,
NodeTypeStrTbl[Node->NodeType]
));
@@ -227,7 +227,7 @@ AmlDbgPrintDataNode (

AmlDbgPrintNodeHeader ((AML_NODE_HEADER*)DataNode, Level);

- DEBUG ((DEBUG_INFO, "%-36s | ", NodeDataTypeStrTbl[DataNode->DataType]));
+ DEBUG ((DEBUG_INFO, "%-36a | ", NodeDataTypeStrTbl[DataNode->DataType]));
DEBUG ((DEBUG_INFO, "0x%04x | ", DataNode->Size));

if ((DataNode->DataType == EAmlNodeDataTypeNameString) ||
@@ -300,13 +300,13 @@ AmlDbgPrintObjectNode (

// Print a string corresponding to the field object OpCode/SubOpCode.
if (AmlNodeHasAttribute (ObjectNode, AML_IS_FIELD_ELEMENT)) {
- DEBUG ((DEBUG_INFO, "%-15s ", AmlGetFieldOpCodeStr (
+ DEBUG ((DEBUG_INFO, "%-15a ", AmlGetFieldOpCodeStr (
ObjectNode->AmlByteEncoding->OpCode,
0
)));
} else {
// Print a string corresponding to the object OpCode/SubOpCode.
- DEBUG ((DEBUG_INFO, "%-15s | ", AmlGetOpCodeStr (
+ DEBUG ((DEBUG_INFO, "%-15a | ", AmlGetOpCodeStr (
ObjectNode->AmlByteEncoding->OpCode,
ObjectNode->AmlByteEncoding->SubOpCode)
));
@@ -378,19 +378,19 @@ AmlDbgPrintTableHeader (
DEBUG ((DEBUG_INFO, "Lvl | Node Type |\n"));
DEBUG ((
DEBUG_INFO,
- " | %-15s | Signature| Length | Rev | CSum | OemId | "
+ " | %-15a | Signature| Length | Rev | CSum | OemId | "
"OemTableId | OemRev | CreatorId| CreatorRev\n",
NodeTypeStrTbl[EAmlNodeRoot]
));
DEBUG ((
DEBUG_INFO,
- " | %-15s | Op | SubOp| OpName | MaxI| Attribute | "
+ " | %-15a | Op | SubOp| OpName | MaxI| Attribute | "
"PkgLen | NodeName (opt)\n",
NodeTypeStrTbl[EAmlNodeObject]
));
DEBUG ((
DEBUG_INFO,
- " | %-15s | Data Type | Size | "
+ " | %-15a | Data Type | Size | "
"Buffer\n",
NodeTypeStrTbl[EAmlNodeData]
));
--
2.17.1


[PATCH v1 06/10] DynamicTablesPkg: Add Configuration Manager Object parser

PierreGondois
 

From: Sami Mujawar <sami.mujawar@...>

The Platform information repository in the Configuration Manager
may be dynamically populated, for e.g. by a Hardware Information
Parser like FdtHwInfoParser. In such cases it is useful to trace
the CM objects that were populated by the parser.

Therefore, introduce helper functions that can parse and trace
the Configuration Manager Objects.

Signed-off-by: Sami Mujawar <sami.mujawar@...>
Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Include/Library/TableHelperLib.h | 10 +
.../ConfigurationManagerObjectParser.c | 678 ++++++++++++++++++
.../ConfigurationManagerObjectParser.h | 73 ++
.../Common/TableHelperLib/TableHelperLib.inf | 2 +
4 files changed, 763 insertions(+)
create mode 100644 DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.c
create mode 100644 DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.h

diff --git a/DynamicTablesPkg/Include/Library/TableHelperLib.h b/DynamicTablesPkg/Include/Library/TableHelperLib.h
index 57af51134546..6d362ff99a27 100644
--- a/DynamicTablesPkg/Include/Library/TableHelperLib.h
+++ b/DynamicTablesPkg/Include/Library/TableHelperLib.h
@@ -107,4 +107,14 @@ FindDuplicateValue (
IN PFN_IS_EQUAL EqualTestFunction
);

+/** Parse and print a CmObjDesc.
+
+ @param [in] CmObjDesc The CmObjDesc to parse and print.
+**/
+VOID
+EFIAPI
+ParseCmObjDesc (
+ IN CONST CM_OBJ_DESCRIPTOR * CmObjDesc
+ );
+
#endif // TABLE_HELPER_LIB_H_
diff --git a/DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.c b/DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.c
new file mode 100644
index 000000000000..654ead6878e6
--- /dev/null
+++ b/DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.c
@@ -0,0 +1,678 @@
+/** @file
+ Configuration Manager Object parser.
+
+ Copyright (c) 2021, ARM Limited. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+#include <ConfigurationManagerObject.h>
+#include "ConfigurationManagerObjectParser.h"
+
+STATIC
+VOID
+EFIAPI
+PrintOemId (
+ CONST CHAR8* Format,
+ UINT8* Ptr
+ );
+
+/** A parser for EArmObjBootArchInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmBootArchInfoParser[] = {
+ {"BootArchFlags", 2, "0x%x", NULL}
+};
+
+/** A parser for EArmObjPowerManagementProfileInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmPowerManagementProfileInfoParser[] = {
+ {"PowerManagementProfile", 1, "0x%x", NULL}
+};
+
+/** A parser for EArmObjGicCInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGicCInfoParser[] = {
+ {"CPUInterfaceNumber", 4, "0x%x", NULL},
+ {"AcpiProcessorUid", 4, "0x%x", NULL},
+ {"Flags", 4, "0x%x", NULL},
+ {"ParkingProtocolVersion", 4, "0x%x", NULL},
+ {"PerformanceInterruptGsiv", 4, "0x%x", NULL},
+ {"ParkedAddress", 8, "0x%llx", NULL},
+ {"PhysicalBaseAddress", 8, "0x%llx", NULL},
+ {"GICV", 8, "0x%llx", NULL},
+ {"GICH", 8, "0x%llx", NULL},
+ {"VGICMaintenanceInterrupt", 4, "0x%x", NULL},
+ {"GICRBaseAddress", 8, "0x%llx", NULL},
+ {"MPIDR", 8, "0x%llx", NULL},
+ {"ProcessorPowerEfficiencyClass", 1, "0x%x", NULL},
+ {"SpeOverflowInterrupt", 2, "0x%x", NULL},
+ {"ProximityDomain", 4, "0x%x", NULL},
+ {"ClockDomain", 4, "0x%x", NULL},
+ {"AffinityFlags", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjGicDInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGicDInfoParser[] = {
+ {"PhysicalBaseAddress", 8, "0x%llx", NULL},
+ {"SystemVectorBase", 4, "0x%x", NULL},
+ {"GicVersion", 1, "0x%x", NULL},
+};
+
+/** A parser for EArmObjGicMsiFrameInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGicMsiFrameInfoParser[] = {
+ {"GicMsiFrameId", 4, "0x%x", NULL},
+ {"PhysicalBaseAddress", 8, "0x%llx", NULL},
+ {"Flags", 4, "0x%x", NULL},
+ {"SPICount", 2, "0x%x", NULL},
+ {"SPIBase", 2, "0x%x", NULL}
+};
+
+/** A parser for EArmObjGicRedistributorInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGicRedistInfoParser[] = {
+ {"DiscoveryRangeBaseAddress", 8, "0x%llx", NULL},
+ {"DiscoveryRangeLength", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjGicItsInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGicItsInfoParser[] = {
+ {"GicItsId", 4, "0x%x", NULL},
+ {"PhysicalBaseAddress", 8, "0x%llx", NULL},
+ {"ProximityDomain", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjSerialConsolePortInfo,
+ EArmObjSerialDebugPortInfo and EArmObjSerialPortInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmSerialPortInfoParser[] = {
+ {"BaseAddress", 8, "0x%llx", NULL},
+ {"Interrupt", 4, "0x%x", NULL},
+ {"BaudRate", 8, "0x%llx", NULL},
+ {"Clock", 4, "0x%x", NULL},
+ {"PortSubtype", 2, "0x%x", NULL},
+ {"BaseAddressLength", 8, "0x%llx", NULL},
+ {"AccessSize", 1, "0x%d", NULL}
+};
+
+/** A parser for EArmObjGenericTimerInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGenericTimerInfoParser[] = {
+ {"CounterControlBaseAddress", 8, "0x%llx", NULL},
+ {"CounterReadBaseAddress", 8, "0x%llx", NULL},
+ {"SecurePL1TimerGSIV", 4, "0x%x", NULL},
+ {"SecurePL1TimerFlags", 4, "0x%x", NULL},
+ {"NonSecurePL1TimerGSIV", 4, "0x%x", NULL},
+ {"NonSecurePL1TimerFlags", 4, "0x%x", NULL},
+ {"VirtualTimerGSIV", 4, "0x%x", NULL},
+ {"VirtualTimerFlags", 4, "0x%x", NULL},
+ {"NonSecurePL2TimerGSIV", 4, "0x%x", NULL},
+ {"NonSecurePL2TimerFlags", 4, "0x%x", NULL},
+ {"VirtualPL2TimerGSIV", 4, "0x%x", NULL},
+ {"VirtualPL2TimerFlags", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjPlatformGTBlockInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGTBlockTimerFrameInfoParser[] = {
+ {"FrameNumber", 1, "0x%x", NULL},
+ {"PhysicalAddressCntBase", 8, "0x%llx", NULL},
+ {"PhysicalAddressCntEL0Base", 8, "0x%llx", NULL},
+ {"PhysicalTimerGSIV", 4, "0x%x", NULL},
+ {"PhysicalTimerFlags", 4, "0x%x", NULL},
+ {"VirtualTimerGSIV", 4, "0x%x", NULL},
+ {"VirtualTimerFlags", 4, "0x%x", NULL},
+ {"CommonFlags", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjGTBlockTimerFrameInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGTBlockInfoParser[] = {
+ {"GTBlockPhysicalAddress", 8, "0x%llx", NULL},
+ {"GTBlockTimerFrameCount", 4, "0x%x", NULL},
+ {"GTBlockTimerFrameToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL}
+};
+
+/** A parser for EArmObjPlatformGenericWatchdogInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGenericWatchdogInfoParser[] = {
+ {"ControlFrameAddress", 8, "0x%llx", NULL},
+ {"RefreshFrameAddress", 8, "0x%llx", NULL},
+ {"TimerGSIV", 4, "0x%x", NULL},
+ {"Flags", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjPciConfigSpaceInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmPciConfigSpaceInfoParser[] = {
+ {"BaseAddress", 8, "0x%llx", NULL},
+ {"PciSegmentGroupNumber", 2, "0x%x", NULL},
+ {"StartBusNumber", 1, "0x%x", NULL},
+ {"EndBusNumber", 1, "0x%x", NULL}
+};
+
+/** A parser for EArmObjHypervisorVendorIdentity.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmHypervisorVendorIdParser[] = {
+ {"HypervisorVendorId", 8, "0x%llx", NULL}
+};
+
+/** A parser for EArmObjFixedFeatureFlags.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmFixedFeatureFlagsParser[] = {
+ {"Flags", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjItsGroup.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmItsGroupNodeParser[] = {
+ {"GTBlockTimerFrameToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"ItsIdCount", 4, "0x%x", NULL},
+ {"ItsIdToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL}
+};
+
+/** A parser for EArmObjNamedComponent.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmNamedComponentNodeParser[] = {
+ {"Token", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"IdMappingCount", 4, "0x%x", NULL},
+ {"IdMappingToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"Flags", 4, "0x%x", NULL},
+ {"CacheCoherent", 4, "0x%x", NULL},
+ {"AllocationHints", 1, "0x%x", NULL},
+ {"MemoryAccessFlags", 1, "0x%x", NULL},
+ {"AddressSizeLimit", 1, "0x%x", NULL},
+ {"ObjectName", sizeof (CHAR8*), "%a", NULL}
+};
+
+/** A parser for EArmObjRootComplex.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmRootComplexNodeParser[] = {
+ {"Token", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"IdMappingCount", 4, "0x%x", NULL},
+ {"IdMappingToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"CacheCoherent", 4, "0x%x", NULL},
+ {"AllocationHints", 1, "0x%x", NULL},
+ {"MemoryAccessFlags", 1, "0x%x", NULL},
+ {"AtsAttribute", 4, "0x%x", NULL},
+ {"PciSegmentNumber", 4, "0x%x", NULL},
+ {"MemoryAddressSize", 1, "0x%x", NULL}
+};
+
+/** A parser for EArmObjSmmuV1SmmuV2.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmSmmuV1SmmuV2NodeParser[] = {
+ {"Token", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"IdMappingCount", 4, "0x%x", NULL},
+ {"IdMappingToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"BaseAddress", 8, "0x%llx", NULL},
+ {"Span", 8, "0x%llx", NULL},
+ {"Model", 4, "0x%x", NULL},
+ {"Flags", 4, "0x%x", NULL},
+ {"ContextInterruptCount", 4, "0x%x", NULL},
+ {"ContextInterruptToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"PmuInterruptCount", 4, "0x%x", NULL},
+ {"PmuInterruptToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"SMMU_NSgIrpt", 4, "0x%x", NULL},
+ {"SMMU_NSgIrptFlags", 4, "0x%x", NULL},
+ {"SMMU_NSgCfgIrpt", 4, "0x%x", NULL},
+ {"SMMU_NSgCfgIrptFlags", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjSmmuV3.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmSmmuV3NodeParser[] = {
+ {"Token", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"IdMappingCount", 4, "0x%x", NULL},
+ {"IdMappingToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"BaseAddress", 8, "0x%llx", NULL},
+ {"Flags", 4, "0x%x", NULL},
+ {"VatosAddress", 8, "0x%llx", NULL},
+ {"Model", 4, "0x%x", NULL},
+ {"EventInterrupt", 4, "0x%x", NULL},
+ {"PriInterrupt", 4, "0x%x", NULL},
+ {"GerrInterrupt", 4, "0x%x", NULL},
+ {"SyncInterrupt", 4, "0x%x", NULL},
+ {"ProximityDomain", 4, "0x%x", NULL},
+ {"DeviceIdMappingIndex", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjPmcg.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmPmcgNodeParser[] = {
+ {"Token", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"IdMappingCount", 4, "0x%x", NULL},
+ {"IdMappingToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"BaseAddress", 8, "0x%llx", NULL},
+ {"OverflowInterrupt", 4, "0x%x", NULL},
+ {"Page1BaseAddress", 8, "0x%llx", NULL},
+ {"ReferenceToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL}
+};
+
+/** A parser for EArmObjGicItsIdentifierArray.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGicItsIdentifierParser[] = {
+ {"ItsId", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjIdMappingArray.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmIdMappingParser[] = {
+ {"InputBase", 4, "0x%x", NULL},
+ {"NumIds", 4, "0x%x", NULL},
+ {"OutputBase", 4, "0x%x", NULL},
+ {"OutputReferenceToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"Flags", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjSmmuInterruptArray.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGenericInterruptParser[] = {
+ {"Interrupt", 4, "0x%x", NULL},
+ {"Flags", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjProcHierarchyInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmProcHierarchyInfoParser[] = {
+ {"Token", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"Flags", 4, "0x%x", NULL},
+ {"ParentToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"GicCToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"NoOfPrivateResources", 4, "0x%x", NULL},
+ {"PrivateResourcesArrayToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL}
+};
+
+/** A parser for EArmObjCacheInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmCacheInfoParser[] = {
+ {"Token", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"NextLevelOfCacheToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"Size", 4, "0x%x", NULL},
+ {"NumberOfSets", 4, "0x%x", NULL},
+ {"Associativity", 4, "0x%x", NULL},
+ {"Attributes", 1, "0x%x", NULL},
+ {"LineSize", 2, "0x%x", NULL}
+};
+
+/** A parser for EArmObjProcNodeIdInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmProcNodeIdInfoParser[] = {
+ {"Token", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL},
+ {"VendorId", 4, "0x%p", NULL},
+ {"Level1Id", 8, "0x%x", NULL},
+ {"Level2Id", 8, "0x%x", NULL},
+ {"MajorRev", 2, "0x%x", NULL},
+ {"MinorRev", 2, "0x%x", NULL},
+ {"SpinRev", 2, "0x%x", NULL}
+};
+
+/** A parser for EArmObjCmRef.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmObjRefParser[] = {
+ {"ReferenceToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL}
+};
+
+/** A parser for EArmObjMemoryAffinityInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmMemoryAffinityInfoParser[] = {
+ {"ProximityDomain", 4, "0x%x", NULL},
+ {"BaseAddress", 8, "0x%llx", NULL},
+ {"Length", 8, "0x%llx", NULL},
+ {"Flags", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjDeviceHandleAcpi.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmDeviceHandleAcpiParser[] = {
+ {"Hid", 8, "0x%llx", NULL},
+ {"Uid", 4, "0x%x", NULL}
+};
+
+/** A parser for EArmObjDeviceHandlePci.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmDeviceHandlePciParser[] = {
+ {"SegmentNumber", 2, "0x%x", NULL},
+ {"BusNumber", 1, "0x%x", NULL},
+ {"DeviceNumber", 1, "0x%x", NULL},
+ {"FunctionNumber", 1, "0x%x", NULL}
+};
+
+/** A parser for EArmObjGenericInitiatorAffinityInfo.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmGenericInitiatorAffinityInfoParser[] = {
+ {"ProximityDomain", 4, "0x%x", NULL},
+ {"Flags", 4, "0x%x", NULL},
+ {"DeviceHandleType", 1, "0x%x", NULL},
+ {"DeviceHandleToken", sizeof (CM_OBJECT_TOKEN), "0x%p", NULL}
+};
+
+/** A parser for EArmObjCmn600Info.
+*/
+STATIC CONST CM_OBJ_PARSER CmArmCmn600InfoParser[] = {
+ {"PeriphBaseAddress", 8, "0x%llx", NULL},
+ {"PeriphBaseAddressLength", 8, "0x%llx", NULL},
+ {"RootNodeBaseAddress", 8, "0x%llx", NULL},
+ {"DtcCount", 1, "0x%x", NULL},
+ {"DtcInterrupt[0]", 4, "0x%x", NULL},
+ {"DtcFlags[0]", 4, "0x%x", NULL},
+ {"DtcInterrupt[1]", 4, "0x%x", NULL},
+ {"DtcFlags[1]", 4, "0x%x", NULL},
+ {"DtcInterrupt[2]", 4, "0x%x", NULL},
+ {"DtcFlags[2]", 4, "0x%x", NULL},
+ {"DtcInterrupt[3]", 4, "0x%x", NULL},
+ {"DtcFlags[3]", 4, "0x%x", NULL}
+};
+
+/** A parser for Arm namespace objects.
+*/
+STATIC CONST CM_OBJ_PARSER_ARRAY ArmNamespaceObjectParser[] = {
+ {"EArmObjReserved", NULL, 0},
+ {"EArmObjBootArchInfo", CmArmBootArchInfoParser,
+ ARRAY_SIZE (CmArmBootArchInfoParser)},
+ {"EArmObjCpuInfo", NULL, 0},
+ {"EArmObjPowerManagementProfileInfo", CmArmPowerManagementProfileInfoParser,
+ ARRAY_SIZE (CmArmPowerManagementProfileInfoParser)},
+ {"EArmObjGicCInfo", CmArmGicCInfoParser, ARRAY_SIZE (CmArmGicCInfoParser)},
+ {"EArmObjGicDInfo", CmArmGicDInfoParser, ARRAY_SIZE (CmArmGicDInfoParser)},
+ {"EArmObjGicMsiFrameInfo", CmArmGicMsiFrameInfoParser,
+ ARRAY_SIZE (CmArmGicMsiFrameInfoParser)},
+ {"EArmObjGicRedistributorInfo", CmArmGicRedistInfoParser,
+ ARRAY_SIZE (CmArmGicRedistInfoParser)},
+ {"EArmObjGicItsInfo", CmArmGicItsInfoParser,
+ ARRAY_SIZE (CmArmGicItsInfoParser)},
+ {"EArmObjSerialConsolePortInfo", CmArmSerialPortInfoParser,
+ ARRAY_SIZE (CmArmSerialPortInfoParser)},
+ {"EArmObjSerialDebugPortInfo", CmArmSerialPortInfoParser,
+ ARRAY_SIZE (CmArmSerialPortInfoParser)},
+ {"EArmObjGenericTimerInfo", CmArmGenericTimerInfoParser,
+ ARRAY_SIZE (CmArmGenericTimerInfoParser)},
+ {"EArmObjPlatformGTBlockInfo", CmArmGTBlockTimerFrameInfoParser,
+ ARRAY_SIZE (CmArmGTBlockTimerFrameInfoParser)},
+ {"EArmObjGTBlockTimerFrameInfo", CmArmGTBlockInfoParser,
+ ARRAY_SIZE (CmArmGTBlockInfoParser)},
+ {"EArmObjPlatformGenericWatchdogInfo", CmArmGenericWatchdogInfoParser,
+ ARRAY_SIZE (CmArmGenericWatchdogInfoParser)},
+ {"EArmObjPciConfigSpaceInfo", CmArmPciConfigSpaceInfoParser,
+ ARRAY_SIZE (CmArmPciConfigSpaceInfoParser)},
+ {"EArmObjHypervisorVendorIdentity", CmArmHypervisorVendorIdParser,
+ ARRAY_SIZE (CmArmHypervisorVendorIdParser)},
+ {"EArmObjFixedFeatureFlags", CmArmFixedFeatureFlagsParser,
+ ARRAY_SIZE (CmArmFixedFeatureFlagsParser)},
+ {"EArmObjItsGroup", CmArmItsGroupNodeParser,
+ ARRAY_SIZE (CmArmItsGroupNodeParser)},
+ {"EArmObjNamedComponent", CmArmNamedComponentNodeParser,
+ ARRAY_SIZE (CmArmNamedComponentNodeParser)},
+ {"EArmObjRootComplex", CmArmRootComplexNodeParser,
+ ARRAY_SIZE (CmArmRootComplexNodeParser)},
+ {"EArmObjSmmuV1SmmuV2", CmArmSmmuV1SmmuV2NodeParser,
+ ARRAY_SIZE (CmArmSmmuV1SmmuV2NodeParser)},
+ {"EArmObjSmmuV3", CmArmSmmuV3NodeParser,
+ ARRAY_SIZE (CmArmSmmuV3NodeParser)},
+ {"EArmObjPmcg", CmArmPmcgNodeParser, ARRAY_SIZE (CmArmPmcgNodeParser)},
+ {"EArmObjGicItsIdentifierArray", CmArmGicItsIdentifierParser,
+ ARRAY_SIZE (CmArmGicItsIdentifierParser)},
+ {"EArmObjIdMappingArray", CmArmIdMappingParser,
+ ARRAY_SIZE (CmArmIdMappingParser)},
+ {"EArmObjSmmuInterruptArray", CmArmGenericInterruptParser,
+ ARRAY_SIZE (CmArmGenericInterruptParser)},
+ {"EArmObjProcHierarchyInfo", CmArmProcHierarchyInfoParser,
+ ARRAY_SIZE (CmArmProcHierarchyInfoParser)},
+ {"EArmObjCacheInfo", CmArmCacheInfoParser,
+ ARRAY_SIZE (CmArmCacheInfoParser)},
+ {"EArmObjProcNodeIdInfo", CmArmProcNodeIdInfoParser,
+ ARRAY_SIZE (CmArmProcNodeIdInfoParser)},
+ {"EArmObjCmRef", CmArmObjRefParser, ARRAY_SIZE (CmArmObjRefParser)},
+ {"EArmObjMemoryAffinityInfo", CmArmMemoryAffinityInfoParser,
+ ARRAY_SIZE (CmArmMemoryAffinityInfoParser)},
+ {"EArmObjDeviceHandleAcpi", CmArmDeviceHandleAcpiParser,
+ ARRAY_SIZE (CmArmDeviceHandleAcpiParser)},
+ {"EArmObjDeviceHandlePci", CmArmDeviceHandlePciParser,
+ ARRAY_SIZE (CmArmDeviceHandlePciParser)},
+ {"EArmObjGenericInitiatorAffinityInfo",
+ CmArmGenericInitiatorAffinityInfoParser,
+ ARRAY_SIZE (CmArmGenericInitiatorAffinityInfoParser)},
+ {"EArmObjSerialPortInfo", CmArmSerialPortInfoParser,
+ ARRAY_SIZE (CmArmSerialPortInfoParser)},
+ {"EArmObjCmn600Info", CmArmCmn600InfoParser,
+ ARRAY_SIZE (CmArmCmn600InfoParser)},
+ {"EArmObjMax", NULL, 0},
+};
+
+/** A parser for EStdObjCfgMgrInfo.
+*/
+STATIC CONST CM_OBJ_PARSER StdObjCfgMgrInfoParser[] = {
+ {"Revision", 4, "0x%x", NULL},
+ {"OemId[6]", 6, "%C%C%C%C%C%C", PrintOemId}
+};
+
+/** A parser for EStdObjAcpiTableList.
+*/
+STATIC CONST CM_OBJ_PARSER StdObjAcpiTableInfoParser[] = {
+ {"AcpiTableSignature", 4, "0x%x", NULL},
+ {"AcpiTableRevision", 1, "%d", NULL},
+ {"TableGeneratorId", sizeof (ACPI_TABLE_GENERATOR_ID), "0x%x", NULL},
+ {"AcpiTableData", sizeof (EFI_ACPI_DESCRIPTION_HEADER*), "0x%p", NULL},
+ {"OemTableId", 8, "0x%LLX", NULL},
+ {"OemRevision", 4, "0x%x", NULL}
+};
+
+/** A parser for EStdObjSmbiosTableList.
+*/
+STATIC CONST CM_OBJ_PARSER StdObjSmbiosTableInfoParser[] = {
+ {"TableGeneratorId", sizeof (SMBIOS_TABLE_GENERATOR_ID), "0x%x", NULL},
+ {"SmbiosTableData", sizeof (SMBIOS_STRUCTURE*), "0x%p", NULL}
+};
+
+/** A parser for Standard namespace objects.
+*/
+STATIC CONST CM_OBJ_PARSER_ARRAY StdNamespaceObjectParser[] = {
+ {"EStdObjCfgMgrInfo", StdObjCfgMgrInfoParser,
+ ARRAY_SIZE (StdObjCfgMgrInfoParser)},
+ {"EStdObjAcpiTableList", StdObjAcpiTableInfoParser,
+ ARRAY_SIZE (StdObjAcpiTableInfoParser)},
+ {"EStdObjSmbiosTableList", StdObjSmbiosTableInfoParser,
+ ARRAY_SIZE (StdObjSmbiosTableInfoParser)},
+};
+
+/** Print OEM Id.
+
+ @param [in] Format Format to print the Ptr.
+ @param [in] Ptr Pointer to the OEM Id.
+**/
+STATIC
+VOID
+EFIAPI
+PrintOemId (
+ IN CONST CHAR8 * Format,
+ IN UINT8 * Ptr
+ )
+{
+ DEBUG ((
+ DEBUG_ERROR,
+ (Format != NULL) ? Format : "%C%C%C%C%C%C",
+ Ptr[0],
+ Ptr[1],
+ Ptr[2],
+ Ptr[3],
+ Ptr[4],
+ Ptr[5]
+ ));
+}
+
+/** Print fields of the objects.
+
+ @param [in] Data Pointer to the object to print.
+ @param [in] Parser Parser containing the object fields.
+ @param [in] ItemCount Number of entries/fields in the Parser.
+ @param [in] RemainingSize Parse at most *RemainingSize bytes.
+ This function decrements the value
+ from the number bytes consumed.
+ @param [in] IndentLevel Indentation to use when printing.
+**/
+STATIC
+VOID
+PrintCmObjDesc (
+ IN VOID *Data,
+ IN CONST CM_OBJ_PARSER *Parser,
+ IN UINTN ItemCount,
+ IN INTN *RemainingSize,
+ IN UINT32 IndentLevel
+ )
+{
+ UINT32 Index;
+ UINT32 IndentIndex;
+ INTN SubStructSize;
+
+ if ((Data == NULL) ||
+ (Parser == NULL) ||
+ (ItemCount == 0) ||
+ (RemainingSize == NULL)) {
+ ASSERT (0);
+ return;
+ }
+
+ // Print each field.
+ for (Index = 0; Index < ItemCount; Index++) {
+ // Check there is enough space in left.
+ *RemainingSize -= Parser[Index].Length;
+ if (*RemainingSize < 0) {
+ DEBUG ((
+ DEBUG_ERROR,
+ "\nERROR: %a: Buffer overrun\n",
+ Parser[Index].NameStr
+ ));
+ ASSERT (0);
+ return;
+ }
+
+ // Indentation
+ for (IndentIndex = 0; IndentIndex < IndentLevel; IndentIndex++) {
+ DEBUG ((DEBUG_ERROR, " "));
+ }
+
+ DEBUG ((
+ DEBUG_ERROR,
+ "%-*a :",
+ OUTPUT_FIELD_COLUMN_WIDTH - 2 * IndentLevel,
+ Parser[Index].NameStr
+ ));
+ if (Parser[Index].PrintFormatter != NULL) {
+ Parser[Index].PrintFormatter (Parser[Index].Format, Data);
+ } else if (Parser[Index].Format != NULL) {
+ switch (Parser[Index].Length) {
+ case 1:
+ DEBUG ((DEBUG_ERROR, Parser[Index].Format, *(UINT8*)Data));
+ break;
+ case 2:
+ DEBUG ((DEBUG_ERROR, Parser[Index].Format, *(UINT16*)Data));
+ break;
+ case 4:
+ DEBUG ((DEBUG_ERROR, Parser[Index].Format, *(UINT32*)Data));
+ break;
+ case 8:
+ DEBUG ((DEBUG_ERROR, Parser[Index].Format, ReadUnaligned64(Data)));
+ break;
+ default:
+ DEBUG ((
+ DEBUG_ERROR,
+ "\nERROR: %a: CANNOT PARSE THIS FIELD, Field Length = %d\n",
+ Parser[Index].NameStr,
+ Parser[Index].Length
+ ));
+ } // switch
+ } else if (Parser[Index].SubObjParser != NULL) {
+ SubStructSize = Parser[Index].Length;
+
+ DEBUG ((DEBUG_ERROR, "\n"));
+ PrintCmObjDesc (
+ Data,
+ Parser[Index].SubObjParser,
+ Parser[Index].SubObjItemCount,
+ &SubStructSize,
+ IndentLevel + 1
+ );
+ } else {
+ ASSERT (0);
+ DEBUG ((
+ DEBUG_ERROR,
+ "\nERROR: %a: CANNOT PARSE THIS FIELD, Field Length = %d\n",
+ Parser[Index].NameStr,
+ Parser[Index].Length
+ ));
+ }
+ DEBUG ((DEBUG_ERROR, "\n"));
+ Data += Parser[Index].Length;
+ } // for
+}
+
+/** Parse and print a CmObjDesc.
+
+ @param [in] CmObjDesc The CmObjDesc to parse and print.
+**/
+VOID
+EFIAPI
+ParseCmObjDesc (
+ IN CONST CM_OBJ_DESCRIPTOR * CmObjDesc
+ )
+{
+ UINTN ObjId;
+ UINTN NameSpaceId;
+ UINT32 ObjIndex;
+ UINT32 ObjectCount;
+ INTN RemainingSize;
+ CONST CM_OBJ_PARSER_ARRAY * ParserArray;
+
+ if ((CmObjDesc == NULL) || (CmObjDesc->Data == NULL)) {
+ return;
+ }
+
+ NameSpaceId = GET_CM_NAMESPACE_ID (CmObjDesc->ObjectId);
+ ObjId = GET_CM_OBJECT_ID (CmObjDesc->ObjectId);
+
+ switch (NameSpaceId) {
+ case EObjNameSpaceStandard:
+ if (ObjId >= EStdObjMax) {
+ ASSERT (0);
+ return;
+ }
+ ParserArray = &StdNamespaceObjectParser[ObjId];
+ break;
+ case EObjNameSpaceArm:
+ if (ObjId >= EArmObjMax) {
+ ASSERT (0);
+ return;
+ }
+ ParserArray = &ArmNamespaceObjectParser[ObjId];
+ break;
+ default:
+ // Not supported
+ ASSERT (0);
+ return;
+ } // switch
+
+ ObjectCount = CmObjDesc->Count;
+ RemainingSize = CmObjDesc->Size;
+
+ for (ObjIndex = 0; ObjIndex < ObjectCount; ObjIndex++) {
+ DEBUG ((
+ DEBUG_ERROR,
+ "\n%-*a [%d/%d]:\n",
+ OUTPUT_FIELD_COLUMN_WIDTH,
+ ParserArray->ObjectName,
+ ObjIndex + 1,
+ ObjectCount
+ ));
+ PrintCmObjDesc (
+ CmObjDesc->Data,
+ ParserArray->Parser,
+ ParserArray->ItemCount,
+ &RemainingSize,
+ 1
+ );
+ } // for
+}
diff --git a/DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.h b/DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.h
new file mode 100644
index 000000000000..e229df7095d9
--- /dev/null
+++ b/DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.h
@@ -0,0 +1,73 @@
+/** @file
+ Configuration Manager Object parser.
+
+ Copyright (c) 2021, ARM Limited. All rights reserved.<BR>
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+
+**/
+
+#ifndef CONFIGURATION_MANAGER_OBJECT_PARSER_H_
+#define CONFIGURATION_MANAGER_OBJECT_PARSER_H_
+
+#define OUTPUT_FIELD_COLUMN_WIDTH 32
+
+/** Function prototype to format a field print.
+
+ @param [in] Format Format string for tracing the data as specified by
+ the 'Format' member of ACPI_PARSER.
+ @param [in] Ptr Pointer to the start of the buffer.
+**/
+typedef VOID (EFIAPI *FNPTR_PRINT_FORMATTER)(CONST CHAR8* Format, UINT8* Ptr);
+
+/**
+ The CM_OBJ_PARSER structure describes the fields of an CmObject and
+ provides means for the parser to interpret and trace appropriately.
+
+ ParseAcpi() uses the format string specified by 'Format' for tracing
+ the field data.
+*/
+typedef struct CmObjParser CM_OBJ_PARSER;
+struct CmObjParser {
+
+ /// String describing the Cm Object
+ CONST CHAR8* NameStr;
+
+ /// The length of the field.
+ UINT32 Length;
+
+ /// Optional Print() style format string for tracing the data. If not
+ /// used this must be set to NULL.
+ CONST CHAR8* Format;
+
+ /// Optional pointer to a print formatter function which
+ /// is typically used to trace complex field information.
+ /// If not used this must be set to NULL.
+ /// The Format string is passed to the PrintFormatter function
+ /// but may be ignored by the implementation code.
+ FNPTR_PRINT_FORMATTER PrintFormatter;
+
+ /// Optional pointer to print the fields of another CM_OBJ_PARSER
+ /// structure. This is useful to print sub-structures.
+ CONST CM_OBJ_PARSER *SubObjParser;
+
+ /// Count of items in the SubObj.
+ UINTN SubObjItemCount;
+};
+
+/**
+ A structure mapping an array of Configuration Manager Object parsers
+ with their object names.
+*/
+typedef struct CmObjParserArray {
+
+ /// Object name
+ CONST CHAR8 * ObjectName;
+
+ /// Function pointer to the parser
+ CONST CM_OBJ_PARSER * Parser;
+
+ /// Count of items
+ UINTN ItemCount;
+} CM_OBJ_PARSER_ARRAY;
+
+#endif // CONFIGURATION_MANAGER_OBJECT_PARSER_H_
diff --git a/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf b/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf
index 5435f74aa0b8..abbf4bc38cab 100644
--- a/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf
+++ b/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf
@@ -15,6 +15,8 @@ [Defines]
LIBRARY_CLASS = TableHelperLib

[Sources]
+ ConfigurationManagerObjectParser.c
+ ConfigurationManagerObjectParser.h
TableHelper.c

[Packages]
--
2.17.1


[PATCH v1 05/10] DynamicTablesPkg: Add AmlGetEisaIdFromString() to AcpiHelperLib

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Add a function converting a 7 characters string to its UINT32
EISAID. The algorithm used to create the EISAID is described
in the ACPI 6.4 specification, s19.3.4 "ASL Macros".

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Include/Library/AcpiHelperLib.h | 17 +++++
.../Library/Common/AcpiHelperLib/AcpiHelper.c | 69 +++++++++++++++++++
2 files changed, 86 insertions(+)

diff --git a/DynamicTablesPkg/Include/Library/AcpiHelperLib.h b/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
index eec0cf75e084..e7962a2b931a 100644
--- a/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
+++ b/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
@@ -71,4 +71,21 @@ IsValidAcpiId (
IN CONST CHAR8 * Hid
);

+/** Convert a EisaId string to its compressed UINT32 equivalent.
+
+ Cf. ACPI 6.4 specification, s19.3.4 "ASL Macros": "Eisaid"
+
+ @param [in] EisaIdStr Input EisaId string.
+ @param [out] EisaIdInt Output EisaId UINT32 (compressed).
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+**/
+EFI_STATUS
+EFIAPI
+AmlGetEisaIdFromString (
+ IN CONST CHAR8 * EisaIdStr,
+ OUT UINT32 * EisaIdInt
+ );
+
#endif // ACPI_HELPER_LIB_H_
diff --git a/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
index c7097c8ff432..4b6756054c0c 100644
--- a/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
+++ b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
@@ -137,3 +137,72 @@ IsValidAcpiId (

return TRUE;
}
+
+/** Convert a EisaId string to its compressed UINT32 equivalent.
+
+ Cf. ACPI 6.4 specification, s19.3.4 "ASL Macros": "Eisaid"
+
+ @param [in] EisaIdStr Input EisaId string.
+ @param [out] EisaIdInt Output EisaId UINT32 (compressed).
+
+ @retval EFI_SUCCESS The function completed successfully.
+ @retval EFI_INVALID_PARAMETER Invalid parameter.
+**/
+EFI_STATUS
+EFIAPI
+AmlGetEisaIdFromString (
+ IN CONST CHAR8 * EisaIdStr,
+ OUT UINT32 * EisaIdInt
+ )
+{
+ if ((EisaIdStr == NULL) ||
+ (!IsValidPnpId (EisaIdStr)) ||
+ (EisaIdInt == NULL)) {
+ ASSERT (0);
+ return EFI_INVALID_PARAMETER;
+ }
+
+ /* Cf. ACPI 6.4 specification, s19.3.4 "ASL Macros": "Eisaid"
+
+ Converts and compresses the 7-character text argument into its corresponding
+ 4-byte numeric EISA ID encoding (Integer). This can be used when declaring
+ IDs for devices that are EISA IDs.
+
+ The algorithm used to convert the TextID is as shown in the following
+ example:
+ Starting with a seven character input string "PNP0303", we want to create
+ a DWordConst. This string contains a three character manufacturer code
+ "PNP", a three character hex product identifier "030", and a one character
+ revision identifier "3".
+ The compressed manufacturer code is created as follows:
+ 1) Find hex ASCII value for each letter
+ 2) Subtract 40h from each ASCII value
+ 3) Retain 5 least significant bits for each letter and discard remaining
+ 0's:
+
+ Byte 0:
+ Bit 7: reserved (0)
+ Bit 6-2: 1st character of compressed mfg code "P"
+ Bit 1-0: Upper 2 bits of 2nd character of mfg code "N"
+ Byte 1:
+ Bit 7-5: Lower 3 bits of 2nd character of mfg code "N"
+ Bit 4-0: 3rd character of mfg code "P"
+ Byte 2:
+ Bit 7-4: 1st hex digit of product number "0"
+ Bit 3-0: 2nd hex digit of product number "3"
+ Byte 3:
+ Bit 7-4: 3rd hex digit of product number "0"
+ Bit 3-0: 4th hex digit of product number "3"
+ */
+ *EisaIdInt = SwapBytes32 (
+ ((EisaIdStr[0] - 0x40) << 26) |
+ ((EisaIdStr[1] - 0x40) << 21) |
+ ((EisaIdStr[2] - 0x40) << 16) |
+ (HexFromAscii (EisaIdStr[3]) << 12) |
+ (HexFromAscii (EisaIdStr[4]) << 8) |
+ (HexFromAscii (EisaIdStr[5]) << 4) |
+ (HexFromAscii (EisaIdStr[6]))
+ );
+
+ return EFI_SUCCESS;
+}
--
2.17.1


[PATCH v1 04/10] DynamicTablesPkg: Add HexFromAscii() to AcpiHelperLib

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Add HexFromAscii(), converting an hexadecimal ascii char
to an integer.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Include/Library/AcpiHelperLib.h | 14 +++++++++
.../Library/Common/AcpiHelperLib/AcpiHelper.c | 30 +++++++++++++++++++
2 files changed, 44 insertions(+)

diff --git a/DynamicTablesPkg/Include/Library/AcpiHelperLib.h b/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
index b653c3cb69ef..eec0cf75e084 100644
--- a/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
+++ b/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
@@ -33,6 +33,20 @@ AsciiFromHex (
IN UINT8 Hex
);

+/** Convert an ASCII char representing an hexadecimal number
+ to its integer value.
+
+ @param [in] Char Char to convert.
+ Must be between '0'-'9' or 'A'-'F' or 'a'-'f'.
+
+ @return The corresponding integer (between 0-16).
+**/
+UINT8
+EFIAPI
+HexFromAscii (
+ IN CHAR8 Char
+ );
+
/** Check if a HID is a valid PNP ID.

@param [in] Hid The Hid to validate.
diff --git a/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
index 19840fb173eb..c7097c8ff432 100644
--- a/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
+++ b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
@@ -37,6 +37,36 @@ AsciiFromHex (
return (UINT8)-1;
}

+/** Convert an ASCII char representing an hexadecimal number
+ to its integer value.
+
+ @param [in] Char Char to convert.
+ Must be between '0'-'9' or 'A'-'F' or 'a'-'f'.
+
+ @return The corresponding integer (between 0-16).
+**/
+UINT8
+EFIAPI
+HexFromAscii (
+ IN CHAR8 Char
+ )
+{
+ if ((Char >= '0') && (Char <= '9')) {
+ return (UINT8)(Char - '0');
+ }
+
+ if ((Char >= 'A') && (Char <= 'F')) {
+ return (UINT8)(Char - 'A' + 10);
+ }
+
+ if ((Char >= 'a') && (Char <= 'f')) {
+ return (UINT8)(Char - 'a' + 10);
+ }
+
+ ASSERT (FALSE);
+ return (UINT8)-1;
+}
+
/** Check if a HID is a valid PNP ID.

@param [in] Hid The Hid to validate.
--
2.17.1


[PATCH v1 03/10] DynamicTablesPkg: Rename single char input parameter

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

The Ecc tool forbids the usage of one char variable: Ecc error 8007:
"There should be no use of short (single character) variable names"

To follow this policy, rename this one letter parameter.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
DynamicTablesPkg/Include/Library/AcpiHelperLib.h | 6 +++---
.../Library/Common/AcpiHelperLib/AcpiHelper.c | 14 +++++++-------
2 files changed, 10 insertions(+), 10 deletions(-)

diff --git a/DynamicTablesPkg/Include/Library/AcpiHelperLib.h b/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
index 2731a2e4fb27..b653c3cb69ef 100644
--- a/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
+++ b/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
@@ -22,15 +22,15 @@

/** Convert a hex number to its ASCII code.

- @param [in] x Hex number to convert.
- Must be 0 <= x < 16.
+ @param [in] Hex Hex number to convert.
+ Must be 0 <= x < 16.

@return The ASCII code corresponding to x.
**/
UINT8
EFIAPI
AsciiFromHex (
- IN UINT8 x
+ IN UINT8 Hex
);

/** Check if a HID is a valid PNP ID.
diff --git a/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
index 85a32269aae5..19840fb173eb 100644
--- a/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
+++ b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
@@ -14,23 +14,23 @@

/** Convert a hex number to its ASCII code.

- @param [in] x Hex number to convert.
- Must be 0 <= x < 16.
+ @param [in] Hex Hex number to convert.
+ Must be 0 <= x < 16.

@return The ASCII code corresponding to x.
**/
UINT8
EFIAPI
AsciiFromHex (
- IN UINT8 x
+ IN UINT8 Hex
)
{
- if (x < 10) {
- return (UINT8)(x + '0');
+ if (Hex < 10) {
+ return (UINT8)(Hex + '0');
}

- if (x < 16) {
- return (UINT8)(x - 10 + 'A');
+ if (Hex < 16) {
+ return (UINT8)(Hex - 10 + 'A');
}

ASSERT (FALSE);
--
2.17.1


[PATCH v1 02/10] DynamicTablesPkg: Update TableHelperLib.inf

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

Update the inf file version and BASE_NAME of the library.
Remove unused sections.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
.../Library/Common/TableHelperLib/TableHelperLib.inf | 11 +++--------
1 file changed, 3 insertions(+), 8 deletions(-)

diff --git a/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf b/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf
index 26d82e68501b..5435f74aa0b8 100644
--- a/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf
+++ b/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf
@@ -1,14 +1,14 @@
## @file
# Table Helper
#
-# Copyright (c) 2017 - 2018, ARM Limited. All rights reserved.
+# Copyright (c) 2017 - 2021, ARM Limited. All rights reserved.
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
##

[Defines]
- INF_VERSION = 0x00010019
- BASE_NAME = DynamicTableHelperLib
+ INF_VERSION = 0x0001001B
+ BASE_NAME = TableHelperLib
FILE_GUID = E315C738-3A39-4D0D-A0AF-8EDFA770AB39
VERSION_STRING = 1.0
MODULE_TYPE = DXE_DRIVER
@@ -23,8 +23,3 @@ [Packages]

[LibraryClasses]
BaseLib
-
-[Protocols]
-
-[Guids]
-
--
2.17.1


[PATCH v1 01/10] DynamicTablesPkg: Extract AcpiTableHelperLib from TableHelperLib

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

The TableHelperLib contains helper functions. Some rely on
DynamicTablesPkg definitions (they use Configuration Manager objects).
Some others are more generic.

To allow using these generic functions without including
DynamicTablesPkg definitions, move them to a new AcpiTableHelperLib
library.

Signed-off-by: Pierre Gondois <Pierre.Gondois@...>
---
DynamicTablesPkg/DynamicTables.dsc.inc | 3 +-
DynamicTablesPkg/DynamicTablesPkg.dec | 4 +
DynamicTablesPkg/DynamicTablesPkg.dsc | 1 +
.../Include/Library/AcpiHelperLib.h | 60 ++++++++++
.../Include/Library/TableHelperLib.h | 49 --------
.../SsdtCmn600Generator.c | 2 +-
.../AcpiSsdtCmn600LibArm/SsdtCmn600LibArm.inf | 3 +-
.../SsdtSerialPortGenerator.c | 3 +-
.../SsdtSerialPortLibArm.inf | 4 +-
.../Library/Common/AcpiHelperLib/AcpiHelper.c | 109 ++++++++++++++++++
.../Common/AcpiHelperLib/AcpiHelperLib.inf | 25 ++++
.../Library/Common/AmlLib/AmlLib.inf | 3 +-
.../SsdtSerialPortFixupLib.c | 2 +-
.../SsdtSerialPortFixupLib.inf | 1 +
.../Common/TableHelperLib/TableHelper.c | 96 ---------------
15 files changed, 212 insertions(+), 153 deletions(-)
create mode 100644 DynamicTablesPkg/Include/Library/AcpiHelperLib.h
create mode 100644 DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
create mode 100644 DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelperLib.inf

diff --git a/DynamicTablesPkg/DynamicTables.dsc.inc b/DynamicTablesPkg/DynamicTables.dsc.inc
index fa33b7ee67e6..ed221d1681eb 100644
--- a/DynamicTablesPkg/DynamicTables.dsc.inc
+++ b/DynamicTablesPkg/DynamicTables.dsc.inc
@@ -1,7 +1,7 @@
## @file
# Dsc include file for Dynamic Tables Framework.
#
-# Copyright (c) 2017 - 2020, Arm Limited. All rights reserved.<BR>
+# Copyright (c) 2017 - 2021, Arm Limited. All rights reserved.<BR>
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
#
@@ -13,6 +13,7 @@ [BuildOptions]
RELEASE_*_*_CC_FLAGS = -DMDEPKG_NDEBUG

[LibraryClasses.common]
+ AcpiHelperLib|DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelperLib.inf
AmlLib|DynamicTablesPkg/Library/Common/AmlLib/AmlLib.inf
SsdtSerialPortFixupLib|DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.inf
TableHelperLib|DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf
diff --git a/DynamicTablesPkg/DynamicTablesPkg.dec b/DynamicTablesPkg/DynamicTablesPkg.dec
index b242df010587..9996bdf6f520 100644
--- a/DynamicTablesPkg/DynamicTablesPkg.dec
+++ b/DynamicTablesPkg/DynamicTablesPkg.dec
@@ -17,6 +17,10 @@ [Includes]
Include

[LibraryClasses]
+ ## @libraryclass Defines a set of Acpi helper methods
+ # independent from the Dynamic Tables Framework.
+ AcpiHelperLib|Include/Library/AcpiHelperLib.h
+
## @libraryclass Defines a set of APIs for Dynamic AML generation.
AmlLib|Include/Library/AmlLib/AmlLib.h

diff --git a/DynamicTablesPkg/DynamicTablesPkg.dsc b/DynamicTablesPkg/DynamicTablesPkg.dsc
index 33b2a84c9dd9..46b2e667fd25 100644
--- a/DynamicTablesPkg/DynamicTablesPkg.dsc
+++ b/DynamicTablesPkg/DynamicTablesPkg.dsc
@@ -38,6 +38,7 @@ [LibraryClasses.ARM, LibraryClasses.AARCH64]
PL011UartLib|ArmPlatformPkg/Library/PL011UartLib/PL011UartLib.inf

[Components.common]
+ DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelperLib.inf
DynamicTablesPkg/Library/Common/AmlLib/AmlLib.inf
DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.inf
DynamicTablesPkg/Library/Common/TableHelperLib/TableHelperLib.inf
diff --git a/DynamicTablesPkg/Include/Library/AcpiHelperLib.h b/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
new file mode 100644
index 000000000000..2731a2e4fb27
--- /dev/null
+++ b/DynamicTablesPkg/Include/Library/AcpiHelperLib.h
@@ -0,0 +1,60 @@
+/** @file
+
+ Copyright (c) 2017 - 2021, Arm Limited. All rights reserved.<BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#ifndef ACPI_HELPER_LIB_H_
+#define ACPI_HELPER_LIB_H_
+
+/** Is a character upper case
+*/
+#define IS_UPPER_CHAR(x) ((x >= 'A') && (x <= 'Z'))
+
+/** Is a character a decimal digit
+*/
+#define IS_DIGIT(x) ((x >= '0') && (x <= '9'))
+
+/** Is a character an upper case hexadecimal digit
+*/
+#define IS_UPPER_HEX(x) (((x >= 'A') && (x <= 'F')) || IS_DIGIT (x))
+
+/** Convert a hex number to its ASCII code.
+
+ @param [in] x Hex number to convert.
+ Must be 0 <= x < 16.
+
+ @return The ASCII code corresponding to x.
+**/
+UINT8
+EFIAPI
+AsciiFromHex (
+ IN UINT8 x
+ );
+
+/** Check if a HID is a valid PNP ID.
+
+ @param [in] Hid The Hid to validate.
+
+ @retval TRUE The Hid is a valid PNP ID.
+ @retval FALSE The Hid is not a valid PNP ID.
+**/
+BOOLEAN
+IsValidPnpId (
+ IN CONST CHAR8 * Hid
+ );
+
+/** Check if a HID is a valid ACPI ID.
+
+ @param [in] Hid The Hid to validate.
+
+ @retval TRUE The Hid is a valid ACPI ID.
+ @retval FALSE The Hid is not a valid ACPI ID.
+**/
+BOOLEAN
+IsValidAcpiId (
+ IN CONST CHAR8 * Hid
+ );
+
+#endif // ACPI_HELPER_LIB_H_
diff --git a/DynamicTablesPkg/Include/Library/TableHelperLib.h b/DynamicTablesPkg/Include/Library/TableHelperLib.h
index 0f93cdbf0895..57af51134546 100644
--- a/DynamicTablesPkg/Include/Library/TableHelperLib.h
+++ b/DynamicTablesPkg/Include/Library/TableHelperLib.h
@@ -12,18 +12,6 @@
#ifndef TABLE_HELPER_LIB_H_
#define TABLE_HELPER_LIB_H_

-/** Is a character upper case
-*/
-#define IS_UPPER_CHAR(x) ((x >= 'A') && (x <= 'Z'))
-
-/** Is a character a decimal digit
-*/
-#define IS_DIGIT(x) ((x >= '0') && (x <= '9'))
-
-/** Is a character an upper case hexadecimal digit
-*/
-#define IS_UPPER_HEX(x) (((x >= 'A') && (x <= 'F')) || IS_DIGIT (x))
-
/** The GetCgfMgrInfo function gets the CM_STD_OBJ_CONFIGURATION_MANAGER_INFO
object from the Configuration Manager.

@@ -119,41 +107,4 @@ FindDuplicateValue (
IN PFN_IS_EQUAL EqualTestFunction
);

-/** Convert a hex number to its ASCII code.
-
- @param [in] x Hex number to convert.
- Must be 0 <= x < 16.
-
- @return The ASCII code corresponding to x.
-**/
-UINT8
-EFIAPI
-AsciiFromHex (
- IN UINT8 x
- );
-
-/** Check if a HID is a valid PNP ID.
-
- @param [in] Hid The Hid to validate.
-
- @retval TRUE The Hid is a valid PNP ID.
- @retval FALSE The Hid is not a valid PNP ID.
-**/
-BOOLEAN
-IsValidPnpId (
- IN CONST CHAR8 * Hid
- );
-
-/** Check if a HID is a valid ACPI ID.
-
- @param [in] Hid The Hid to validate.
-
- @retval TRUE The Hid is a valid ACPI ID.
- @retval FALSE The Hid is not a valid ACPI ID.
-**/
-BOOLEAN
-IsValidAcpiId (
- IN CONST CHAR8 * Hid
- );
-
#endif // TABLE_HELPER_LIB_H_
diff --git a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c
index 1e8c2bfca5de..cc730cd90fea 100644
--- a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c
+++ b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600Generator.c
@@ -23,8 +23,8 @@
#include <AcpiTableGenerator.h>
#include <ConfigurationManagerObject.h>
#include <ConfigurationManagerHelper.h>
+#include <Library/AcpiHelperLib.h>
#include <Library/AmlLib/AmlLib.h>
-#include <Library/TableHelperLib.h>
#include <Protocol/ConfigurationManagerProtocol.h>
#include "SsdtCmn600Generator.h"

diff --git a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600LibArm.inf b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600LibArm.inf
index 821c0d531b98..12b028fcde22 100644
--- a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600LibArm.inf
+++ b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtCmn600LibArm/SsdtCmn600LibArm.inf
@@ -1,7 +1,7 @@
## @file
# Ssdt CMN-600 Table Generator
#
-# Copyright (c) 2020, Arm Limited. All rights reserved.<BR>
+# Copyright (c) 2021, Arm Limited. All rights reserved.<BR>
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
@@ -29,6 +29,7 @@ [Packages]
DynamicTablesPkg/DynamicTablesPkg.dec

[LibraryClasses]
+ AcpiHelperLib
AmlLib
BaseLib

diff --git a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtSerialPortLibArm/SsdtSerialPortGenerator.c b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtSerialPortLibArm/SsdtSerialPortGenerator.c
index 570f53aacf16..1b70fe1db1d7 100644
--- a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtSerialPortLibArm/SsdtSerialPortGenerator.c
+++ b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtSerialPortLibArm/SsdtSerialPortGenerator.c
@@ -19,8 +19,9 @@
#include <AcpiTableGenerator.h>
#include <ConfigurationManagerObject.h>
#include <ConfigurationManagerHelper.h>
+#include <Library/AcpiHelperLib.h>
+#include <Library/AmlLib/AmlLib.h>
#include <Library/SsdtSerialPortFixupLib.h>
-#include <Library/TableHelperLib.h>
#include <Protocol/ConfigurationManagerProtocol.h>

/** ARM standard SSDT Serial Port Table Generator
diff --git a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtSerialPortLibArm/SsdtSerialPortLibArm.inf b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtSerialPortLibArm/SsdtSerialPortLibArm.inf
index fb7663e280ad..36e61ea9b132 100644
--- a/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtSerialPortLibArm/SsdtSerialPortLibArm.inf
+++ b/DynamicTablesPkg/Library/Acpi/Arm/AcpiSsdtSerialPortLibArm/SsdtSerialPortLibArm.inf
@@ -1,7 +1,7 @@
## @file
# Ssdt Serial Port Table Generator
#
-# Copyright (c) 2019 - 2020, Arm Limited. All rights reserved.<BR>
+# Copyright (c) 2019 - 2021, Arm Limited. All rights reserved.<BR>
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
@@ -27,7 +27,7 @@ [Packages]
DynamicTablesPkg/DynamicTablesPkg.dec

[LibraryClasses]
+ AcpiHelperLib
AmlLib
BaseLib
- TableHelperLib
SsdtSerialPortFixupLib
diff --git a/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
new file mode 100644
index 000000000000..85a32269aae5
--- /dev/null
+++ b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
@@ -0,0 +1,109 @@
+/** @file
+ Acpi Helper
+
+ Copyright (c) 2017 - 2021, Arm Limited. All rights reserved.<BR>
+
+ SPDX-License-Identifier: BSD-2-Clause-Patent
+**/
+
+#include <Library/BaseLib.h>
+#include <Library/DebugLib.h>
+
+// Module specific include files.
+#include <Library/AcpiHelperLib.h>
+
+/** Convert a hex number to its ASCII code.
+
+ @param [in] x Hex number to convert.
+ Must be 0 <= x < 16.
+
+ @return The ASCII code corresponding to x.
+**/
+UINT8
+EFIAPI
+AsciiFromHex (
+ IN UINT8 x
+ )
+{
+ if (x < 10) {
+ return (UINT8)(x + '0');
+ }
+
+ if (x < 16) {
+ return (UINT8)(x - 10 + 'A');
+ }
+
+ ASSERT (FALSE);
+ return (UINT8)-1;
+}
+
+/** Check if a HID is a valid PNP ID.
+
+ @param [in] Hid The Hid to validate.
+
+ @retval TRUE The Hid is a valid PNP ID.
+ @retval FALSE The Hid is not a valid PNP ID.
+**/
+BOOLEAN
+IsValidPnpId (
+ IN CONST CHAR8 * Hid
+ )
+{
+ UINTN Index;
+
+ if (AsciiStrLen (Hid) != 7) {
+ return FALSE;
+ }
+
+ // A valid PNP ID must be of the form "AAA####"
+ // where A is an uppercase letter and # is a hex digit.
+ for (Index = 0; Index < 3; Index++) {
+ if (!IS_UPPER_CHAR (Hid[Index])) {
+ return FALSE;
+ }
+ }
+
+ for (Index = 3; Index < 7; Index++) {
+ if (!IS_UPPER_HEX (Hid[Index])) {
+ return FALSE;
+ }
+ }
+
+ return TRUE;
+}
+
+/** Check if a HID is a valid ACPI ID.
+
+ @param [in] Hid The Hid to validate.
+
+ @retval TRUE The Hid is a valid ACPI ID.
+ @retval FALSE The Hid is not a valid ACPI ID.
+**/
+BOOLEAN
+IsValidAcpiId (
+ IN CONST CHAR8 * Hid
+ )
+{
+ UINTN Index;
+
+ if (AsciiStrLen (Hid) != 8) {
+ return FALSE;
+ }
+
+ // A valid ACPI ID must be of the form "NNNN####"
+ // where N is an uppercase letter or a digit ('0'-'9')
+ // and # is a hex digit.
+ for (Index = 0; Index < 4; Index++) {
+ if (!(IS_UPPER_CHAR (Hid[Index]) || IS_DIGIT (Hid[Index]))) {
+ return FALSE;
+ }
+ }
+
+ for (Index = 4; Index < 8; Index++) {
+ if (!IS_UPPER_HEX (Hid[Index])) {
+ return FALSE;
+ }
+ }
+
+ return TRUE;
+}
diff --git a/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelperLib.inf b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelperLib.inf
new file mode 100644
index 000000000000..ba7a04eb5a77
--- /dev/null
+++ b/DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelperLib.inf
@@ -0,0 +1,25 @@
+## @file
+# Acpi Helper
+#
+# Copyright (c) 2021, ARM Limited. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-2-Clause-Patent
+##
+
+[Defines]
+ INF_VERSION = 0x0001001B
+ BASE_NAME = AcpiHelperLib
+ FILE_GUID = 45968FB4-A724-46FC-822D-F9E557601F9B
+ VERSION_STRING = 1.0
+ MODULE_TYPE = DXE_DRIVER
+ LIBRARY_CLASS = AcpiHelperLib
+
+[Sources]
+ AcpiHelper.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+ DynamicTablesPkg/DynamicTablesPkg.dec
+
+[LibraryClasses]
+ BaseLib
diff --git a/DynamicTablesPkg/Library/Common/AmlLib/AmlLib.inf b/DynamicTablesPkg/Library/Common/AmlLib/AmlLib.inf
index e2babef445d5..723de3ad4482 100644
--- a/DynamicTablesPkg/Library/Common/AmlLib/AmlLib.inf
+++ b/DynamicTablesPkg/Library/Common/AmlLib/AmlLib.inf
@@ -1,7 +1,7 @@
## @file
# AML Generation Library
#
-# Copyright (c) 2019 - 2020, Arm Limited. All rights reserved.<BR>
+# Copyright (c) 2019 - 2021, Arm Limited. All rights reserved.<BR>
#
# SPDX-License-Identifier: BSD-2-Clause-Patent
##
@@ -66,6 +66,7 @@ [Packages]
DynamicTablesPkg/DynamicTablesPkg.dec

[LibraryClasses]
+ AcpiHelperLib
BaseLib

[BuildOptions]
diff --git a/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.c b/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.c
index f2b4831ad596..8c77f172b795 100644
--- a/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.c
+++ b/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.c
@@ -23,8 +23,8 @@
#include <AcpiTableGenerator.h>
#include <ConfigurationManagerObject.h>
#include <ConfigurationManagerHelper.h>
+#include <Library/AcpiHelperLib.h>
#include <Library/AmlLib/AmlLib.h>
-#include <Library/TableHelperLib.h>
#include <Protocol/ConfigurationManagerProtocol.h>

/** C array containing the compiled AML template.
diff --git a/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.inf b/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.inf
index 54bf71a3b739..965167bdc4e1 100644
--- a/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.inf
+++ b/DynamicTablesPkg/Library/Common/SsdtSerialPortFixupLib/SsdtSerialPortFixupLib.inf
@@ -25,6 +25,7 @@ [Packages]
DynamicTablesPkg/DynamicTablesPkg.dec

[LibraryClasses]
+ AcpiHelperLib
AmlLib
BaseLib

diff --git a/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelper.c b/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelper.c
index 9830ce62b3cb..9249e6b87f70 100644
--- a/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelper.c
+++ b/DynamicTablesPkg/Library/Common/TableHelperLib/TableHelper.c
@@ -245,99 +245,3 @@ FindDuplicateValue (
}
return FALSE;
}
-
-/** Convert a hex number to its ASCII code.
-
- @param [in] x Hex number to convert.
- Must be 0 <= x < 16.
-
- @return The ASCII code corresponding to x.
-**/
-UINT8
-EFIAPI
-AsciiFromHex (
- IN UINT8 x
- )
-{
- if (x < 10) {
- return (UINT8)(x + '0');
- }
-
- if (x < 16) {
- return (UINT8)(x - 10 + 'A');
- }
-
- ASSERT (FALSE);
- return (UINT8)0;
-}
-
-/** Check if a HID is a valid PNP ID.
-
- @param [in] Hid The Hid to validate.
-
- @retval TRUE The Hid is a valid PNP ID.
- @retval FALSE The Hid is not a valid PNP ID.
-**/
-BOOLEAN
-IsValidPnpId (
- IN CONST CHAR8 * Hid
- )
-{
- UINTN Index;
-
- if (AsciiStrLen (Hid) != 7) {
- return FALSE;
- }
-
- // A valid PNP ID must be of the form "AAA####"
- // where A is an uppercase letter and # is a hex digit.
- for (Index = 0; Index < 3; Index++) {
- if (!IS_UPPER_CHAR (Hid[Index])) {
- return FALSE;
- }
- }
-
- for (Index = 3; Index < 7; Index++) {
- if (!IS_UPPER_HEX (Hid[Index])) {
- return FALSE;
- }
- }
-
- return TRUE;
-}
-
-/** Check if a HID is a valid ACPI ID.
-
- @param [in] Hid The Hid to validate.
-
- @retval TRUE The Hid is a valid ACPI ID.
- @retval FALSE The Hid is not a valid ACPI ID.
-**/
-BOOLEAN
-IsValidAcpiId (
- IN CONST CHAR8 * Hid
- )
-{
- UINTN Index;
-
- if (AsciiStrLen (Hid) != 8) {
- return FALSE;
- }
-
- // A valid ACPI ID must be of the form "NNNN####"
- // where N is an uppercase letter or a digit ('0'-'9')
- // and # is a hex digit.
- for (Index = 0; Index < 4; Index++) {
- if (!(IS_UPPER_CHAR (Hid[Index]) || IS_DIGIT (Hid[Index]))) {
- return FALSE;
- }
- }
-
- for (Index = 4; Index < 8; Index++) {
- if (!IS_UPPER_HEX (Hid[Index])) {
- return FALSE;
- }
- }
-
- return TRUE;
-}
--
2.17.1


[PATCH v1 00/10] Various DynamicTablesPkg modifications

PierreGondois
 

From: Pierre Gondois <Pierre.Gondois@...>

This patch-set aggregates various modifications in the
DynamicTablesPkg:
- Extract an AcpiTableHelperLib from TableHelperLib to remove
the dependency of some utility functions over configuration
manager definitions
- Add a HexFromAscii() function
- Add a AmlGetEisaIdFromString() function
- Add a configuration manager object parser
- Use %a instead of %s in when printing AmlLib
- Update the .ci.yaml once to prepare for other incoming patches
- Modify the generic prototype of the AmlResourceDataCodeGen
functions. This also means deprecating some functions.

The modifications can be seen at: https://github.com/PierreARM/edk2/tree/1718_Various_DynamicTablesPkg_modifications_v1
The result of the CI can be seen at: https://github.com/tianocore/edk2/pull/1744 (Failed due timed out connection)

Pierre Gondois (9):
DynamicTablesPkg: Extract AcpiTableHelperLib from TableHelperLib
DynamicTablesPkg: Update TableHelperLib.inf
DynamicTablesPkg: Rename single char input parameter
DynamicTablesPkg: Add HexFromAscii() to AcpiHelperLib
DynamicTablesPkg: Add AmlGetEisaIdFromString() to AcpiHelperLib
DynamicTablesPkg: Use %a formatter in AmlDbgPrint
DynamicTablesPkg: Update DynamicTablesPkg.ci.yaml
DynamicTablesPkg: Deprecate Crs specific methods in AmlLib
DynamicTablesPkg: Rework AmlResourceDataCodegen.c/h

Sami Mujawar (1):
DynamicTablesPkg: Add Configuration Manager Object parser

DynamicTablesPkg/DynamicTables.dsc.inc | 3 +-
DynamicTablesPkg/DynamicTablesPkg.ci.yaml | 29 +
DynamicTablesPkg/DynamicTablesPkg.dec | 4 +
DynamicTablesPkg/DynamicTablesPkg.dsc | 1 +
.../Include/Library/AcpiHelperLib.h | 91 +++
.../Include/Library/AmlLib/AmlLib.h | 225 ++++--
.../Include/Library/TableHelperLib.h | 49 +-
.../SsdtCmn600Generator.c | 14 +-
.../AcpiSsdtCmn600LibArm/SsdtCmn600LibArm.inf | 3 +-
.../SsdtSerialPortGenerator.c | 3 +-
.../SsdtSerialPortLibArm.inf | 4 +-
.../Library/Common/AcpiHelperLib/AcpiHelper.c | 208 ++++++
.../Common/AcpiHelperLib/AcpiHelperLib.inf | 25 +
.../Common/AmlLib/AmlDbgPrint/AmlDbgPrint.c | 16 +-
.../Library/Common/AmlLib/AmlLib.inf | 3 +-
.../Library/Common/AmlLib/Api/AmlApi.c | 147 +++-
.../AmlLib/CodeGen/AmlResourceDataCodeGen.c | 194 ++---
.../AmlLib/CodeGen/AmlResourceDataCodeGen.h | 67 +-
.../SsdtSerialPortFixupLib.c | 6 +-
.../SsdtSerialPortFixupLib.inf | 1 +
.../ConfigurationManagerObjectParser.c | 678 ++++++++++++++++++
.../ConfigurationManagerObjectParser.h | 73 ++
.../Common/TableHelperLib/TableHelper.c | 96 ---
.../Common/TableHelperLib/TableHelperLib.inf | 13 +-
24 files changed, 1575 insertions(+), 378 deletions(-)
create mode 100644 DynamicTablesPkg/Include/Library/AcpiHelperLib.h
create mode 100644 DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelper.c
create mode 100644 DynamicTablesPkg/Library/Common/AcpiHelperLib/AcpiHelperLib.inf
create mode 100644 DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.c
create mode 100644 DynamicTablesPkg/Library/Common/TableHelperLib/ConfigurationManagerObjectParser.h

--
2.17.1


Re: [PATCH 1/4] OvmfPkg/Bhyve: enable bus enumeration

Laszlo Ersek
 

On 06/14/21 11:00, Corvin Köhne wrote:
Neccessary for GPU Passthrough of dedicated AMD GPUs. For Linux
guests, AMD GPUs require that their PCI ROM is processed by UEFI.
Enable bus enumeration to process the PCI ROM of all devices.

Signed-off-by: Corvin Köhne <c.koehne@...>
---
OvmfPkg/Bhyve/BhyveX64.dsc | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/OvmfPkg/Bhyve/BhyveX64.dsc b/OvmfPkg/Bhyve/BhyveX64.dsc
index d8792812ab..ef331d556e 100644
--- a/OvmfPkg/Bhyve/BhyveX64.dsc
+++ b/OvmfPkg/Bhyve/BhyveX64.dsc
@@ -431,7 +431,7 @@
gEfiMdeModulePkgTokenSpaceGuid.PcdInstallAcpiSdtProtocol|TRUE

[PcdsFixedAtBuild]
- gEfiMdeModulePkgTokenSpaceGuid.PcdPciDisableBusEnumeration|TRUE
+ gEfiMdeModulePkgTokenSpaceGuid.PcdPciDisableBusEnumeration|FALSE
gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseSerial|FALSE
gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeUseMemory|TRUE
gEfiMdeModulePkgTokenSpaceGuid.PcdStatusCodeMemorySize|1
The right approach -- assuming you reach an agreement with Peter -- is
to revert commist c2f24ba3218a and 8c8f886f2755 first (in this order),
then remove the PcdPciDisableBusEnumeration setting from the DSC
altogether (given the DEC default of the PCD being FALSE).

Independently, please use "python3
$EDK_TOOLS_PATH/Scripts/GetMaintainer.py", for determining the propert
set of CC's for every patch in a series.

I have no comments on the other patches (especially the 4th one), as
they are tied to bhyve platform internals, which I'm unfamiliar with.

Thanks
Laszlo


Re: [PATCH v3 8/8] MdeModulePkg: Use SecureBootVariableLib in PlatformVarCleanupLib.

Grzegorz Bernacki <gjb@...>
 

Hi,

AuthVariableLib must support DXE_DRIVER and UEFI_APPLICATION. Adding
it leads to errors for libraries which are used by AuthVariableLib and
which does not support DXE_DRIVER or UEFI_APPLICATION. This changes
causes a lot of minor changes in another libraries.
The whole problem exists because I wanted to remove a duplicate of
CreateTimeBasedPayload() from PlatformVarCleanupLib. I just leave it
there. This module is not used anyway. I think it can be safely
removed, but I don't want this change to be a part of this patchset.
thanks,
greg

śr., 23 cze 2021 o 05:33 Sunny Wang <Sunny.Wang@...> napisał(a):


Hi Greg,
Why can't we make AuthVariableLib support DXE_DRIVER?

Best Regards,
Sunny Wang

-----Original Message-----
From: Grzegorz Bernacki <gjb@...>
Sent: Monday, June 21, 2021 5:59 PM
To: devel@edk2.groups.io; Grzegorz Bernacki <gjb@...>
Cc: gaoliming@...; leif@...; ardb+tianocore@...; Samer El-Haj-Mahmoud <Samer.El-Haj-Mahmoud@...>; Sunny Wang <Sunny.Wang@...>; Marcin Wojtas <mw@...>; upstream@...; Yao, Jiewen <jiewen.yao@...>; Wang, Jian J <jian.j.wang@...>; Xu, Min M <min.m.xu@...>; Laszlo Ersek <lersek@...>; Sami Mujawar <Sami.Mujawar@...>; afish@...; ray.ni@...; jordan.l.justen@...; rebecca@...; grehan@...; Thomas Abraham <thomas.abraham@...>; chasel.chiu@...; nathaniel.l.desimone@...; eric.dong@...; michael.d.kinney@...; zailiang.sun@...; yi.qian@...; graeme@...; Radosław Biernacki <rad@...>; Pete Batard <pete@...>
Subject: Re: [edk2-devel] [PATCH v3 8/8] MdeModulePkg: Use SecureBootVariableLib in PlatformVarCleanupLib.

Hi,

I moved CreateTimeBasedPayload() to AuthVariableLib, but then I cannot
use it in SecureBootConfigDxe, cause AuthVariableLib does not support
DXE_DRIVER.
So:
- having that function only in AuthVariableLib does not work
- having that function only in SecureBootVariableLib, causes a lot of
changes in platform DSCs files and also causes MdeModulePkg to be
depended on SecurityPkg

Right now I tend to roll back the changes related to
CreateTimeBasedPayload() and just let the modules to have its own copy
of that function. What do you think?
thanks,
greg

pt., 18 cze 2021 o 10:03 Grzegorz Bernacki via groups.io
<gjb@...> napisał(a):

Hi,

Thanks for the comment, I will move that function to AuthVariableLib.
greg

czw., 17 cze 2021 o 04:35 gaoliming <gaoliming@...> napisał(a):

Grzegorz:
MdeModulePkg is generic base package. It should not depend on SecurityPkg.

I agree CreateTimeBasedPayload() is the generic API. It can be shared in
the different modules.
I propose to add it into MdeModulePkg AuthVariableLib.

Thanks
Liming
-----邮件原件-----
发件人: devel@edk2.groups.io <devel@edk2.groups.io> 代表 Grzegorz
Bernacki
发送时间: 2021年6月14日 17:43
收件人: devel@edk2.groups.io
抄送: leif@...; ardb+tianocore@...;
Samer.El-Haj-Mahmoud@...; sunny.Wang@...;
mw@...; upstream@...; jiewen.yao@...;
jian.j.wang@...; min.m.xu@...; lersek@...;
sami.mujawar@...; afish@...; ray.ni@...;
jordan.l.justen@...; rebecca@...; grehan@...;
thomas.abraham@...; chasel.chiu@...;
nathaniel.l.desimone@...; gaoliming@...;
eric.dong@...; michael.d.kinney@...; zailiang.sun@...;
yi.qian@...; graeme@...; rad@...; pete@...;
Grzegorz Bernacki <gjb@...>
主题: [edk2-devel] [PATCH v3 8/8] MdeModulePkg: Use
SecureBootVariableLib in PlatformVarCleanupLib.

This commits removes CreateTimeBasedPayload() function from
PlatformVarCleanupLib and uses exactly the same function from
SecureBootVariableLib.

Signed-off-by: Grzegorz Bernacki <gjb@...>
---
MdeModulePkg/Library/PlatformVarCleanupLib/PlatformVarCleanupLib.inf |
2 +
MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanup.h
| 1 +
MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanupLib.c
| 84 --------------------
3 files changed, 3 insertions(+), 84 deletions(-)

diff --git
a/MdeModulePkg/Library/PlatformVarCleanupLib/PlatformVarCleanupLib.inf
b/MdeModulePkg/Library/PlatformVarCleanupLib/PlatformVarCleanupLib.inf
index 8d5db826a0..493d03e1d8 100644
---
a/MdeModulePkg/Library/PlatformVarCleanupLib/PlatformVarCleanupLib.inf
+++
b/MdeModulePkg/Library/PlatformVarCleanupLib/PlatformVarCleanupLib.inf
@@ -34,6 +34,7 @@
[Packages]
MdePkg/MdePkg.dec
MdeModulePkg/MdeModulePkg.dec
+ SecurityPkg/SecurityPkg.dec

[LibraryClasses]
UefiBootServicesTableLib
@@ -44,6 +45,7 @@
PrintLib
MemoryAllocationLib
HiiLib
+ SecureBootVariableLib

[Guids]
gEfiIfrTianoGuid ## SOMETIMES_PRODUCES ##
GUID
diff --git a/MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanup.h
b/MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanup.h
index c809a7086b..94fbc7d2a4 100644
--- a/MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanup.h
+++ b/MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanup.h
@@ -18,6 +18,7 @@ SPDX-License-Identifier: BSD-2-Clause-Patent
#include <Library/MemoryAllocationLib.h>
#include <Library/HiiLib.h>
#include <Library/PlatformVarCleanupLib.h>
+#include <Library/SecureBootVariableLib.h>

#include <Protocol/Variable.h>
#include <Protocol/VarCheck.h>
diff --git
a/MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanupLib.c
b/MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanupLib.c
index 3875d614bb..204f1e00ad 100644
--- a/MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanupLib.c
+++ b/MdeModulePkg/Library/PlatformVarCleanupLib/PlatVarCleanupLib.c
@@ -319,90 +319,6 @@ DestroyUserVariableNode (
}
}

-/**
- Create a time based data payload by concatenating the
EFI_VARIABLE_AUTHENTICATION_2
- descriptor with the input data. NO authentication is required in this
function.
-
- @param[in, out] DataSize On input, the size of Data buffer in
bytes.
- On output, the size of data
returned in Data
- buffer in bytes.
- @param[in, out] Data On input, Pointer to data buffer to
be wrapped or
- pointer to NULL to wrap an
empty payload.
- On output, Pointer to the new
payload date buffer allocated from pool,
- it's caller's responsibility to free
the memory after using it.
-
- @retval EFI_SUCCESS Create time based payload
successfully.
- @retval EFI_OUT_OF_RESOURCES There are not enough memory
resourses to create time based payload.
- @retval EFI_INVALID_PARAMETER The parameter is invalid.
- @retval Others Unexpected error happens.
-
-**/
-EFI_STATUS
-CreateTimeBasedPayload (
- IN OUT UINTN *DataSize,
- IN OUT UINT8 **Data
- )
-{
- EFI_STATUS Status;
- UINT8 *NewData;
- UINT8 *Payload;
- UINTN PayloadSize;
- EFI_VARIABLE_AUTHENTICATION_2 *DescriptorData;
- UINTN DescriptorSize;
- EFI_TIME Time;
-
- if (Data == NULL || DataSize == NULL) {
- return EFI_INVALID_PARAMETER;
- }
-
- //
- // At user physical presence, the variable does not need to be signed
but
the
- // parameters to the SetVariable() call still need to be prepared as
authenticated
- // variable. So we create EFI_VARIABLE_AUTHENTICATED_2 descriptor
without certificate
- // data in it.
- //
- Payload = *Data;
- PayloadSize = *DataSize;
-
- DescriptorSize = OFFSET_OF (EFI_VARIABLE_AUTHENTICATION_2,
AuthInfo) + OFFSET_OF (WIN_CERTIFICATE_UEFI_GUID, CertData);
- NewData = (UINT8 *) AllocateZeroPool (DescriptorSize + PayloadSize);
- if (NewData == NULL) {
- return EFI_OUT_OF_RESOURCES;
- }
-
- if ((Payload != NULL) && (PayloadSize != 0)) {
- CopyMem (NewData + DescriptorSize, Payload, PayloadSize);
- }
-
- DescriptorData = (EFI_VARIABLE_AUTHENTICATION_2 *) (NewData);
-
- ZeroMem (&Time, sizeof (EFI_TIME));
- Status = gRT->GetTime (&Time, NULL);
- if (EFI_ERROR (Status)) {
- FreePool (NewData);
- return Status;
- }
- Time.Pad1 = 0;
- Time.Nanosecond = 0;
- Time.TimeZone = 0;
- Time.Daylight = 0;
- Time.Pad2 = 0;
- CopyMem (&DescriptorData->TimeStamp, &Time, sizeof (EFI_TIME));
-
- DescriptorData->AuthInfo.Hdr.dwLength = OFFSET_OF
(WIN_CERTIFICATE_UEFI_GUID, CertData);
- DescriptorData->AuthInfo.Hdr.wRevision = 0x0200;
- DescriptorData->AuthInfo.Hdr.wCertificateType =
WIN_CERT_TYPE_EFI_GUID;
- CopyGuid (&DescriptorData->AuthInfo.CertType, &gEfiCertPkcs7Guid);
-
- if (Payload != NULL) {
- FreePool (Payload);
- }
-
- *DataSize = DescriptorSize + PayloadSize;
- *Data = NewData;
- return EFI_SUCCESS;
-}
-
/**
Create a counter based data payload by concatenating the
EFI_VARIABLE_AUTHENTICATION
descriptor with the input data. NO authentication is required in this
function.
--
2.25.1













IMPORTANT NOTICE: The contents of this email and any attachments are confidential and may also be privileged. If you are not the intended recipient, please notify the sender immediately and do not disclose the contents to any other person, use it for any purpose, or store or copy the information in any medium. Thank you.




19861 - 19880 of 96732