Home | History | Annotate | Line # | Download | only in compiler
      1 /******************************************************************************
      2  *
      3  * Module Name: dttable2.c - handling for specific ACPI tables
      4  *
      5  *****************************************************************************/
      6 
      7 /*
      8  * Copyright (C) 2000 - 2026, Intel Corp.
      9  * All rights reserved.
     10  *
     11  * Redistribution and use in source and binary forms, with or without
     12  * modification, are permitted provided that the following conditions
     13  * are met:
     14  * 1. Redistributions of source code must retain the above copyright
     15  *    notice, this list of conditions, and the following disclaimer,
     16  *    without modification.
     17  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
     18  *    substantially similar to the "NO WARRANTY" disclaimer below
     19  *    ("Disclaimer") and any redistribution must be conditioned upon
     20  *    including a substantially similar Disclaimer requirement for further
     21  *    binary redistribution.
     22  * 3. Neither the names of the above-listed copyright holders nor the names
     23  *    of any contributors may be used to endorse or promote products derived
     24  *    from this software without specific prior written permission.
     25  *
     26  * Alternatively, this software may be distributed under the terms of the
     27  * GNU General Public License ("GPL") version 2 as published by the Free
     28  * Software Foundation.
     29  *
     30  * NO WARRANTY
     31  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
     32  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
     33  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
     34  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
     35  * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
     36  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
     37  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     38  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
     39  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
     40  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
     41  * POSSIBILITY OF SUCH DAMAGES.
     42  */
     43 
     44 /* Compile all complex data tables, signatures starting with L-Z */
     45 
     46 #include "aslcompiler.h"
     47 
     48 #define _COMPONENT          DT_COMPILER
     49         ACPI_MODULE_NAME    ("dttable2")
     50 
     51 
     52 /******************************************************************************
     53  *
     54  * FUNCTION:    DtCompileLpit
     55  *
     56  * PARAMETERS:  List                - Current field list pointer
     57  *
     58  * RETURN:      Status
     59  *
     60  * DESCRIPTION: Compile LPIT.
     61  *
     62  *****************************************************************************/
     63 
     64 ACPI_STATUS
     65 DtCompileLpit (
     66     void                    **List)
     67 {
     68     ACPI_STATUS             Status;
     69     DT_SUBTABLE             *Subtable;
     70     DT_SUBTABLE             *ParentTable;
     71     DT_FIELD                **PFieldList = (DT_FIELD **) List;
     72     DT_FIELD                *SubtableStart;
     73     ACPI_DMTABLE_INFO       *InfoTable;
     74     ACPI_LPIT_HEADER        *LpitHeader;
     75 
     76 
     77     /* Note: Main table consists only of the standard ACPI table header */
     78 
     79     while (*PFieldList)
     80     {
     81         SubtableStart = *PFieldList;
     82 
     83         /* LPIT Subtable header */
     84 
     85         Status = DtCompileTable (PFieldList, AcpiDmTableInfoLpitHdr,
     86             &Subtable);
     87         if (ACPI_FAILURE (Status))
     88         {
     89             return (Status);
     90         }
     91 
     92         ParentTable = DtPeekSubtable ();
     93         DtInsertSubtable (ParentTable, Subtable);
     94         DtPushSubtable (Subtable);
     95 
     96         LpitHeader = ACPI_CAST_PTR (ACPI_LPIT_HEADER, Subtable->Buffer);
     97 
     98         switch (LpitHeader->Type)
     99         {
    100         case ACPI_LPIT_TYPE_NATIVE_CSTATE:
    101 
    102             InfoTable = AcpiDmTableInfoLpit0;
    103             break;
    104 
    105         default:
    106 
    107             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "LPIT");
    108             return (AE_ERROR);
    109         }
    110 
    111         /* LPIT Subtable */
    112 
    113         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
    114         if (ACPI_FAILURE (Status))
    115         {
    116             return (Status);
    117         }
    118 
    119         ParentTable = DtPeekSubtable ();
    120         DtInsertSubtable (ParentTable, Subtable);
    121         DtPopSubtable ();
    122     }
    123 
    124     return (AE_OK);
    125 }
    126 
    127 
    128 /******************************************************************************
    129  *
    130  * FUNCTION:    DtCompileMadt
    131  *
    132  * PARAMETERS:  List                - Current field list pointer
    133  *
    134  * RETURN:      Status
    135  *
    136  * DESCRIPTION: Compile MADT.
    137  *
    138  *****************************************************************************/
    139 
    140 ACPI_STATUS
    141 DtCompileMadt (
    142     void                    **List)
    143 {
    144     ACPI_STATUS             Status;
    145     DT_SUBTABLE             *Subtable;
    146     DT_SUBTABLE             *ParentTable;
    147     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    148     DT_FIELD                *SubtableStart;
    149     ACPI_TABLE_HEADER       *Table;
    150     ACPI_SUBTABLE_HEADER    *MadtHeader;
    151     ACPI_DMTABLE_INFO       *InfoTable;
    152     UINT8                   Revision;
    153 
    154 
    155     Status = DtCompileTable (PFieldList, AcpiDmTableInfoMadt,
    156         &Subtable);
    157     if (ACPI_FAILURE (Status))
    158     {
    159         return (Status);
    160     }
    161 
    162     ParentTable = DtPeekSubtable ();
    163     DtInsertSubtable (ParentTable, Subtable);
    164 
    165     Table = ACPI_CAST_PTR (ACPI_TABLE_HEADER, ParentTable->Buffer);
    166     Revision = Table->Revision;
    167 
    168     while (*PFieldList)
    169     {
    170         SubtableStart = *PFieldList;
    171         Status = DtCompileTable (PFieldList, AcpiDmTableInfoMadtHdr,
    172             &Subtable);
    173         if (ACPI_FAILURE (Status))
    174         {
    175             return (Status);
    176         }
    177 
    178         ParentTable = DtPeekSubtable ();
    179         DtInsertSubtable (ParentTable, Subtable);
    180         DtPushSubtable (Subtable);
    181 
    182         MadtHeader = ACPI_CAST_PTR (ACPI_SUBTABLE_HEADER, Subtable->Buffer);
    183 
    184         switch (MadtHeader->Type)
    185         {
    186         case ACPI_MADT_TYPE_LOCAL_APIC:
    187 
    188             InfoTable = AcpiDmTableInfoMadt0;
    189             break;
    190 
    191         case ACPI_MADT_TYPE_IO_APIC:
    192 
    193             InfoTable = AcpiDmTableInfoMadt1;
    194             break;
    195 
    196         case ACPI_MADT_TYPE_INTERRUPT_OVERRIDE:
    197 
    198             InfoTable = AcpiDmTableInfoMadt2;
    199             break;
    200 
    201         case ACPI_MADT_TYPE_NMI_SOURCE:
    202 
    203             InfoTable = AcpiDmTableInfoMadt3;
    204             break;
    205 
    206         case ACPI_MADT_TYPE_LOCAL_APIC_NMI:
    207 
    208             InfoTable = AcpiDmTableInfoMadt4;
    209             break;
    210 
    211         case ACPI_MADT_TYPE_LOCAL_APIC_OVERRIDE:
    212 
    213             InfoTable = AcpiDmTableInfoMadt5;
    214             break;
    215 
    216         case ACPI_MADT_TYPE_IO_SAPIC:
    217 
    218             InfoTable = AcpiDmTableInfoMadt6;
    219             break;
    220 
    221         case ACPI_MADT_TYPE_LOCAL_SAPIC:
    222 
    223             InfoTable = AcpiDmTableInfoMadt7;
    224             break;
    225 
    226         case ACPI_MADT_TYPE_INTERRUPT_SOURCE:
    227 
    228             InfoTable = AcpiDmTableInfoMadt8;
    229             break;
    230 
    231         case ACPI_MADT_TYPE_LOCAL_X2APIC:
    232 
    233             InfoTable = AcpiDmTableInfoMadt9;
    234             break;
    235 
    236         case ACPI_MADT_TYPE_LOCAL_X2APIC_NMI:
    237 
    238             InfoTable = AcpiDmTableInfoMadt10;
    239             break;
    240 
    241         case ACPI_MADT_TYPE_GENERIC_INTERRUPT:
    242 
    243             if (Revision > 6)
    244                     InfoTable = AcpiDmTableInfoMadt11b;
    245             else if (Revision == 6)
    246                     InfoTable = AcpiDmTableInfoMadt11a;
    247             else
    248                     InfoTable = AcpiDmTableInfoMadt11;
    249             break;
    250 
    251         case ACPI_MADT_TYPE_GENERIC_DISTRIBUTOR:
    252 
    253             InfoTable = AcpiDmTableInfoMadt12;
    254             break;
    255 
    256         case ACPI_MADT_TYPE_GENERIC_MSI_FRAME:
    257 
    258             InfoTable = AcpiDmTableInfoMadt13;
    259             break;
    260 
    261         case ACPI_MADT_TYPE_GENERIC_REDISTRIBUTOR:
    262 
    263             InfoTable = Revision > 6 ? AcpiDmTableInfoMadt14a
    264                                      : AcpiDmTableInfoMadt14;
    265             break;
    266 
    267         case ACPI_MADT_TYPE_GENERIC_TRANSLATOR:
    268 
    269             InfoTable = Revision > 6 ? AcpiDmTableInfoMadt15a
    270                                      : AcpiDmTableInfoMadt15;
    271 
    272             break;
    273 
    274         case ACPI_MADT_TYPE_MULTIPROC_WAKEUP:
    275 
    276             InfoTable = AcpiDmTableInfoMadt16;
    277             break;
    278 
    279         case ACPI_MADT_TYPE_CORE_PIC:
    280 
    281             InfoTable = AcpiDmTableInfoMadt17;
    282             break;
    283 
    284         case ACPI_MADT_TYPE_LIO_PIC:
    285 
    286             InfoTable = AcpiDmTableInfoMadt18;
    287             break;
    288 
    289         case ACPI_MADT_TYPE_HT_PIC:
    290 
    291             InfoTable = AcpiDmTableInfoMadt19;
    292             break;
    293 
    294         case ACPI_MADT_TYPE_EIO_PIC:
    295 
    296             InfoTable = AcpiDmTableInfoMadt20;
    297             break;
    298 
    299         case ACPI_MADT_TYPE_MSI_PIC:
    300 
    301             InfoTable = AcpiDmTableInfoMadt21;
    302             break;
    303 
    304         case ACPI_MADT_TYPE_BIO_PIC:
    305 
    306             InfoTable = AcpiDmTableInfoMadt22;
    307             break;
    308 
    309         case ACPI_MADT_TYPE_LPC_PIC:
    310 
    311             InfoTable = AcpiDmTableInfoMadt23;
    312             break;
    313 
    314         case ACPI_MADT_TYPE_RINTC:
    315 
    316             InfoTable = AcpiDmTableInfoMadt24;
    317             break;
    318 
    319         case ACPI_MADT_TYPE_IMSIC:
    320 
    321             InfoTable = AcpiDmTableInfoMadt25;
    322             break;
    323 
    324         case ACPI_MADT_TYPE_APLIC:
    325 
    326             InfoTable = AcpiDmTableInfoMadt26;
    327             break;
    328 
    329         case ACPI_MADT_TYPE_PLIC:
    330 
    331             InfoTable = AcpiDmTableInfoMadt27;
    332             break;
    333 
    334 		case ACPI_MADT_TYPE_GICV5_IRS:
    335 
    336             InfoTable = AcpiDmTableInfoMadt28;
    337             break;
    338 
    339 		case ACPI_MADT_TYPE_GICV5_ITS:
    340 
    341             InfoTable = AcpiDmTableInfoMadt29;
    342             break;
    343 
    344 		case ACPI_MADT_TYPE_GICV5_ITS_TRANSLATE:
    345 
    346             InfoTable = AcpiDmTableInfoMadt30;
    347             break;
    348 
    349         default:
    350 
    351             if (MadtHeader->Type >= ACPI_MADT_TYPE_OEM_RESERVED)
    352             {
    353                 InfoTable = AcpiDmTableInfoMadt128;
    354             }
    355             else
    356             {
    357                 DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "MADT");
    358                 return (AE_ERROR);
    359             }
    360 
    361             break;
    362         }
    363 
    364         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
    365         if (ACPI_FAILURE (Status))
    366         {
    367             return (Status);
    368         }
    369 
    370         ParentTable = DtPeekSubtable ();
    371         DtInsertSubtable (ParentTable, Subtable);
    372         DtPopSubtable ();
    373     }
    374 
    375     return (AE_OK);
    376 }
    377 
    378 
    379 /******************************************************************************
    380  *
    381  * FUNCTION:    DtCompileMcfg
    382  *
    383  * PARAMETERS:  List                - Current field list pointer
    384  *
    385  * RETURN:      Status
    386  *
    387  * DESCRIPTION: Compile MCFG.
    388  *
    389  *****************************************************************************/
    390 
    391 ACPI_STATUS
    392 DtCompileMcfg (
    393     void                    **List)
    394 {
    395     ACPI_STATUS             Status;
    396 
    397 
    398     Status = DtCompileTwoSubtables (List,
    399         AcpiDmTableInfoMcfg, AcpiDmTableInfoMcfg0);
    400     return (Status);
    401 }
    402 
    403 /******************************************************************************
    404  *
    405  * FUNCTION:    DtCompileMpam
    406  *
    407  * PARAMETERS:  List                - Current field list pointer
    408  *
    409  * RETURN:      Status
    410  *
    411  * DESCRIPTION: Compile MPAM.
    412  *
    413  *****************************************************************************/
    414 
    415 ACPI_STATUS
    416 DtCompileMpam (
    417     void                    **List)
    418 {
    419     ACPI_STATUS             Status;
    420     DT_SUBTABLE             *ParentTable;
    421     DT_SUBTABLE             *Subtable;
    422     DT_FIELD                *SubtableStart;
    423     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    424     ACPI_MPAM_MSC_NODE      *MpamMscNode;
    425     ACPI_MPAM_RESOURCE_NODE *MpamResourceNode;
    426     UINT32                  FuncDepsCount;
    427     UINT32                  RisLength;
    428     ACPI_DMTABLE_INFO       *InfoTable;
    429 
    430     ParentTable = DtPeekSubtable ();
    431 
    432     while (*PFieldList)
    433     {
    434         SubtableStart = *PFieldList;
    435 
    436         /* Main MSC Node table */
    437         Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpam0,
    438             &Subtable);
    439         if (ACPI_FAILURE (Status))
    440         {
    441             return (Status);
    442         }
    443 
    444         MpamMscNode = ACPI_CAST_PTR (ACPI_MPAM_MSC_NODE, Subtable->Buffer);
    445 
    446         ParentTable = DtPeekSubtable ();
    447         DtInsertSubtable (ParentTable, Subtable);
    448         DtPushSubtable (Subtable);
    449 
    450         ParentTable = DtPeekSubtable ();
    451 
    452         /*
    453          * RIS(es) per MSC node have variable lengths depending on how many RISes there and
    454          * any how many functional dependencies per RIS. Calculate it in order
    455          * to properly set the overall MSC length.
    456          */
    457         RisLength = 0;
    458 
    459         /* Iterate over RIS subtables per MSC node */
    460         for (UINT32 ris = 0; ris < MpamMscNode->NumResourceNodes; ris++)
    461         {
    462             /* Compile RIS subtable */
    463             Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpam1,
    464                 &Subtable);
    465             if (ACPI_FAILURE (Status))
    466             {
    467                 return (Status);
    468             }
    469 
    470             MpamResourceNode = ACPI_CAST_PTR (ACPI_MPAM_RESOURCE_NODE, Subtable->Buffer);
    471             DtInsertSubtable (ParentTable, Subtable);
    472             DtPushSubtable (Subtable);
    473 
    474             ParentTable = DtPeekSubtable ();
    475 
    476             switch (MpamResourceNode->LocatorType)
    477             {
    478                 case ACPI_MPAM_LOCATION_TYPE_PROCESSOR_CACHE:
    479                     InfoTable = AcpiDmTableInfoMpam1A;
    480                     break;
    481                 case ACPI_MPAM_LOCATION_TYPE_MEMORY:
    482                     InfoTable = AcpiDmTableInfoMpam1B;
    483                     break;
    484                 case ACPI_MPAM_LOCATION_TYPE_SMMU:
    485                     InfoTable = AcpiDmTableInfoMpam1C;
    486                     break;
    487                 case ACPI_MPAM_LOCATION_TYPE_MEMORY_CACHE:
    488                     InfoTable = AcpiDmTableInfoMpam1D;
    489                     break;
    490                 case ACPI_MPAM_LOCATION_TYPE_ACPI_DEVICE:
    491                     InfoTable = AcpiDmTableInfoMpam1E;
    492                     break;
    493                 case ACPI_MPAM_LOCATION_TYPE_INTERCONNECT:
    494                     InfoTable = AcpiDmTableInfoMpam1F;
    495                     break;
    496                 case ACPI_MPAM_LOCATION_TYPE_UNKNOWN:
    497                     InfoTable = AcpiDmTableInfoMpam1G;
    498                 default:
    499                     DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "Resource Locator Type");
    500                     return (AE_ERROR);
    501             }
    502 
    503             /* Compile Resource Locator Table */
    504             Status = DtCompileTable (PFieldList, InfoTable,
    505                 &Subtable);
    506 
    507             if (ACPI_FAILURE (Status))
    508             {
    509                 return (Status);
    510             }
    511 
    512             DtInsertSubtable (ParentTable, Subtable);
    513 
    514             /* Compile the number of functional dependencies per RIS */
    515             Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpam1Deps,
    516                 &Subtable);
    517 
    518             if (ACPI_FAILURE (Status))
    519             {
    520                 return (Status);
    521             }
    522 
    523             DtInsertSubtable (ParentTable, Subtable);
    524             FuncDepsCount = *ACPI_CAST_PTR (UINT32, Subtable->Buffer);
    525 
    526             RisLength += sizeof(ACPI_MPAM_RESOURCE_NODE) +
    527                 FuncDepsCount * sizeof(ACPI_MPAM_FUNC_DEPS);
    528 
    529             /* Iterate over functional dependencies per RIS */
    530             for (UINT32 funcDep = 0; funcDep < FuncDepsCount; funcDep++)
    531             {
    532                 /* Compiler functional dependencies table */
    533                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpam2,
    534                     &Subtable);
    535 
    536                 if (ACPI_FAILURE (Status))
    537                 {
    538                     return (Status);
    539                 }
    540 
    541                 DtInsertSubtable (ParentTable, Subtable);
    542             }
    543 
    544             DtPopSubtable ();
    545         }
    546 
    547         /* Check if the length of the MSC is correct and override with the correct length */
    548         if (MpamMscNode->Length != sizeof(ACPI_MPAM_MSC_NODE) + RisLength)
    549         {
    550             MpamMscNode->Length = (UINT16) (sizeof(ACPI_MPAM_MSC_NODE) + RisLength);
    551             DbgPrint (ASL_DEBUG_OUTPUT, "Overriding MSC->Length: %X\n", MpamMscNode->Length);
    552         }
    553 
    554         DtPopSubtable ();
    555     }
    556 
    557     return (AE_OK);
    558 }
    559 
    560 
    561 /******************************************************************************
    562  *
    563  * FUNCTION:    DtCompileMpst
    564  *
    565  * PARAMETERS:  List                - Current field list pointer
    566  *
    567  * RETURN:      Status
    568  *
    569  * DESCRIPTION: Compile MPST.
    570  *
    571  *****************************************************************************/
    572 
    573 ACPI_STATUS
    574 DtCompileMpst (
    575     void                    **List)
    576 {
    577     ACPI_STATUS             Status;
    578     DT_SUBTABLE             *Subtable;
    579     DT_SUBTABLE             *ParentTable;
    580     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    581     ACPI_MPST_CHANNEL       *MpstChannelInfo;
    582     ACPI_MPST_POWER_NODE    *MpstPowerNode;
    583     ACPI_MPST_DATA_HDR      *MpstDataHeader;
    584     UINT16                  SubtableCount;
    585     UINT32                  PowerStateCount;
    586     UINT32                  ComponentCount;
    587 
    588 
    589     /* Main table */
    590 
    591     Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst, &Subtable);
    592     if (ACPI_FAILURE (Status))
    593     {
    594         return (Status);
    595     }
    596 
    597     ParentTable = DtPeekSubtable ();
    598     DtInsertSubtable (ParentTable, Subtable);
    599     DtPushSubtable (Subtable);
    600 
    601     MpstChannelInfo = ACPI_CAST_PTR (ACPI_MPST_CHANNEL, Subtable->Buffer);
    602     SubtableCount = MpstChannelInfo->PowerNodeCount;
    603 
    604     while (*PFieldList && SubtableCount)
    605     {
    606         /* Subtable: Memory Power Node(s) */
    607 
    608         Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst0,
    609             &Subtable);
    610         if (ACPI_FAILURE (Status))
    611         {
    612             return (Status);
    613         }
    614 
    615         ParentTable = DtPeekSubtable ();
    616         DtInsertSubtable (ParentTable, Subtable);
    617         DtPushSubtable (Subtable);
    618 
    619         MpstPowerNode = ACPI_CAST_PTR (ACPI_MPST_POWER_NODE, Subtable->Buffer);
    620         PowerStateCount = MpstPowerNode->NumPowerStates;
    621         ComponentCount = MpstPowerNode->NumPhysicalComponents;
    622 
    623         ParentTable = DtPeekSubtable ();
    624 
    625         /* Sub-subtables - Memory Power State Structure(s) */
    626 
    627         while (*PFieldList && PowerStateCount)
    628         {
    629             Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst0A,
    630                 &Subtable);
    631             if (ACPI_FAILURE (Status))
    632             {
    633                 return (Status);
    634             }
    635 
    636             DtInsertSubtable (ParentTable, Subtable);
    637             PowerStateCount--;
    638         }
    639 
    640         /* Sub-subtables - Physical Component ID Structure(s) */
    641 
    642         while (*PFieldList && ComponentCount)
    643         {
    644             Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst0B,
    645                 &Subtable);
    646             if (ACPI_FAILURE (Status))
    647             {
    648                 return (Status);
    649             }
    650 
    651             DtInsertSubtable (ParentTable, Subtable);
    652             ComponentCount--;
    653         }
    654 
    655         SubtableCount--;
    656         DtPopSubtable ();
    657     }
    658 
    659     /* Subtable: Count of Memory Power State Characteristic structures */
    660 
    661     DtPopSubtable ();
    662 
    663     Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst1, &Subtable);
    664     if (ACPI_FAILURE (Status))
    665     {
    666         return (Status);
    667     }
    668 
    669     ParentTable = DtPeekSubtable ();
    670     DtInsertSubtable (ParentTable, Subtable);
    671     DtPushSubtable (Subtable);
    672 
    673     MpstDataHeader = ACPI_CAST_PTR (ACPI_MPST_DATA_HDR, Subtable->Buffer);
    674     SubtableCount = MpstDataHeader->CharacteristicsCount;
    675 
    676     ParentTable = DtPeekSubtable ();
    677 
    678     /* Subtable: Memory Power State Characteristics structure(s) */
    679 
    680     while (*PFieldList && SubtableCount)
    681     {
    682         Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst2,
    683             &Subtable);
    684         if (ACPI_FAILURE (Status))
    685         {
    686             return (Status);
    687         }
    688 
    689         DtInsertSubtable (ParentTable, Subtable);
    690         SubtableCount--;
    691     }
    692 
    693     DtPopSubtable ();
    694     return (AE_OK);
    695 }
    696 
    697 
    698 /******************************************************************************
    699  *
    700  * FUNCTION:    DtCompileMrrm
    701  *
    702  * PARAMETERS:  List                - Current field list pointer
    703  *
    704  * RETURN:      Status
    705  *
    706  * DESCRIPTION: Compile MRRM.
    707  *
    708  *****************************************************************************/
    709 
    710 ACPI_STATUS
    711 DtCompileMrrm (
    712     void                    **List)
    713 {
    714     ACPI_STATUS             Status;
    715     DT_SUBTABLE             *Subtable;
    716     DT_SUBTABLE             *ParentTable;
    717     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    718 
    719     /* Main table */
    720 
    721     Status = DtCompileTable (PFieldList, AcpiDmTableInfoMrrm,
    722         &Subtable);
    723     if (ACPI_FAILURE (Status))
    724     {
    725         return (Status);
    726     }
    727 
    728     ParentTable = DtPeekSubtable ();
    729     DtInsertSubtable (ParentTable, Subtable);
    730 
    731     /* Subtables (all are same type) */
    732 
    733     while (*PFieldList)
    734     {
    735         Status = DtCompileTable (PFieldList, AcpiDmTableInfoMrrm0,
    736             &Subtable);
    737         if (ACPI_FAILURE (Status))
    738         {
    739             return (Status);
    740         }
    741 
    742         DtInsertSubtable (ParentTable, Subtable);
    743     }
    744 
    745     return (AE_OK);
    746 }
    747 
    748 
    749 /******************************************************************************
    750  *
    751  * FUNCTION:    DtCompileMsct
    752  *
    753  * PARAMETERS:  List                - Current field list pointer
    754  *
    755  * RETURN:      Status
    756  *
    757  * DESCRIPTION: Compile MSCT.
    758  *
    759  *****************************************************************************/
    760 
    761 ACPI_STATUS
    762 DtCompileMsct (
    763     void                    **List)
    764 {
    765     ACPI_STATUS             Status;
    766 
    767 
    768     Status = DtCompileTwoSubtables (List,
    769         AcpiDmTableInfoMsct, AcpiDmTableInfoMsct0);
    770     return (Status);
    771 }
    772 
    773 
    774 /******************************************************************************
    775  *
    776  * FUNCTION:    DtCompileNfit
    777  *
    778  * PARAMETERS:  List                - Current field list pointer
    779  *
    780  * RETURN:      Status
    781  *
    782  * DESCRIPTION: Compile NFIT.
    783  *
    784  *****************************************************************************/
    785 
    786 ACPI_STATUS
    787 DtCompileNfit (
    788     void                    **List)
    789 {
    790     ACPI_STATUS             Status;
    791     DT_SUBTABLE             *Subtable;
    792     DT_SUBTABLE             *ParentTable;
    793     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    794     DT_FIELD                *SubtableStart;
    795     ACPI_NFIT_HEADER        *NfitHeader;
    796     ACPI_DMTABLE_INFO       *InfoTable;
    797     UINT32                  Count;
    798     ACPI_NFIT_INTERLEAVE    *Interleave = NULL;
    799     ACPI_NFIT_FLUSH_ADDRESS *Hint = NULL;
    800 
    801 
    802     /* Main table */
    803 
    804     Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfit,
    805         &Subtable);
    806     if (ACPI_FAILURE (Status))
    807     {
    808         return (Status);
    809     }
    810 
    811     ParentTable = DtPeekSubtable ();
    812     DtInsertSubtable (ParentTable, Subtable);
    813     DtPushSubtable (Subtable);
    814 
    815     /* Subtables */
    816 
    817     while (*PFieldList)
    818     {
    819         SubtableStart = *PFieldList;
    820         Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfitHdr,
    821             &Subtable);
    822         if (ACPI_FAILURE (Status))
    823         {
    824             return (Status);
    825         }
    826 
    827         ParentTable = DtPeekSubtable ();
    828         DtInsertSubtable (ParentTable, Subtable);
    829         DtPushSubtable (Subtable);
    830 
    831         NfitHeader = ACPI_CAST_PTR (ACPI_NFIT_HEADER, Subtable->Buffer);
    832 
    833         switch (NfitHeader->Type)
    834         {
    835         case ACPI_NFIT_TYPE_SYSTEM_ADDRESS:
    836 
    837             InfoTable = AcpiDmTableInfoNfit0;
    838             break;
    839 
    840         case ACPI_NFIT_TYPE_MEMORY_MAP:
    841 
    842             InfoTable = AcpiDmTableInfoNfit1;
    843             break;
    844 
    845         case ACPI_NFIT_TYPE_INTERLEAVE:
    846 
    847             Interleave = ACPI_CAST_PTR (ACPI_NFIT_INTERLEAVE, Subtable->Buffer);
    848             InfoTable = AcpiDmTableInfoNfit2;
    849             break;
    850 
    851         case ACPI_NFIT_TYPE_SMBIOS:
    852 
    853             InfoTable = AcpiDmTableInfoNfit3;
    854             break;
    855 
    856         case ACPI_NFIT_TYPE_CONTROL_REGION:
    857 
    858             InfoTable = AcpiDmTableInfoNfit4;
    859             break;
    860 
    861         case ACPI_NFIT_TYPE_DATA_REGION:
    862 
    863             InfoTable = AcpiDmTableInfoNfit5;
    864             break;
    865 
    866         case ACPI_NFIT_TYPE_FLUSH_ADDRESS:
    867 
    868             Hint = ACPI_CAST_PTR (ACPI_NFIT_FLUSH_ADDRESS, Subtable->Buffer);
    869             InfoTable = AcpiDmTableInfoNfit6;
    870             break;
    871 
    872         case ACPI_NFIT_TYPE_CAPABILITIES:
    873 
    874             InfoTable = AcpiDmTableInfoNfit7;
    875             break;
    876 
    877         default:
    878 
    879             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "NFIT");
    880             return (AE_ERROR);
    881         }
    882 
    883         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
    884         if (ACPI_FAILURE (Status))
    885         {
    886             return (Status);
    887         }
    888 
    889         ParentTable = DtPeekSubtable ();
    890         DtInsertSubtable (ParentTable, Subtable);
    891         DtPopSubtable ();
    892 
    893         switch (NfitHeader->Type)
    894         {
    895         case ACPI_NFIT_TYPE_INTERLEAVE:
    896 
    897             Count = 0;
    898             DtPushSubtable (Subtable);
    899             while (*PFieldList)
    900             {
    901                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfit2a,
    902                     &Subtable);
    903                 if (ACPI_FAILURE (Status))
    904                 {
    905                     return (Status);
    906                 }
    907 
    908                 if (!Subtable)
    909                 {
    910                     DtPopSubtable ();
    911                     break;
    912                 }
    913 
    914                 ParentTable = DtPeekSubtable ();
    915                 DtInsertSubtable (ParentTable, Subtable);
    916                 Count++;
    917             }
    918 
    919             Interleave->LineCount = Count;
    920             break;
    921 
    922         case ACPI_NFIT_TYPE_SMBIOS:
    923 
    924             if (*PFieldList)
    925             {
    926                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfit3a,
    927                     &Subtable);
    928                 if (ACPI_FAILURE (Status))
    929                 {
    930                     return (Status);
    931                 }
    932 
    933                 if (Subtable)
    934                 {
    935                     DtInsertSubtable (ParentTable, Subtable);
    936                 }
    937             }
    938             break;
    939 
    940         case ACPI_NFIT_TYPE_FLUSH_ADDRESS:
    941 
    942             Count = 0;
    943             DtPushSubtable (Subtable);
    944             while (*PFieldList)
    945             {
    946                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfit6a,
    947                     &Subtable);
    948                 if (ACPI_FAILURE (Status))
    949                 {
    950                     return (Status);
    951                 }
    952 
    953                 if (!Subtable)
    954                 {
    955                     DtPopSubtable ();
    956                     break;
    957                 }
    958 
    959                 ParentTable = DtPeekSubtable ();
    960                 DtInsertSubtable (ParentTable, Subtable);
    961                 Count++;
    962             }
    963 
    964             Hint->HintCount = (UINT16) Count;
    965             break;
    966 
    967         default:
    968             break;
    969         }
    970     }
    971 
    972     return (AE_OK);
    973 }
    974 
    975 
    976 /******************************************************************************
    977  *
    978  * FUNCTION:    DtCompilePcct
    979  *
    980  * PARAMETERS:  List                - Current field list pointer
    981  *
    982  * RETURN:      Status
    983  *
    984  * DESCRIPTION: Compile PCCT.
    985  *
    986  *****************************************************************************/
    987 
    988 ACPI_STATUS
    989 DtCompilePcct (
    990     void                    **List)
    991 {
    992     ACPI_STATUS             Status;
    993     DT_SUBTABLE             *Subtable;
    994     DT_SUBTABLE             *ParentTable;
    995     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    996     DT_FIELD                *SubtableStart;
    997     ACPI_SUBTABLE_HEADER    *PcctHeader;
    998     ACPI_DMTABLE_INFO       *InfoTable;
    999 
   1000 
   1001     /* Main table */
   1002 
   1003     Status = DtCompileTable (PFieldList, AcpiDmTableInfoPcct,
   1004         &Subtable);
   1005     if (ACPI_FAILURE (Status))
   1006     {
   1007         return (Status);
   1008     }
   1009 
   1010     ParentTable = DtPeekSubtable ();
   1011     DtInsertSubtable (ParentTable, Subtable);
   1012 
   1013     /* Subtables */
   1014 
   1015     while (*PFieldList)
   1016     {
   1017         SubtableStart = *PFieldList;
   1018         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPcctHdr,
   1019             &Subtable);
   1020         if (ACPI_FAILURE (Status))
   1021         {
   1022             return (Status);
   1023         }
   1024 
   1025         ParentTable = DtPeekSubtable ();
   1026         DtInsertSubtable (ParentTable, Subtable);
   1027         DtPushSubtable (Subtable);
   1028 
   1029         PcctHeader = ACPI_CAST_PTR (ACPI_SUBTABLE_HEADER, Subtable->Buffer);
   1030 
   1031         switch (PcctHeader->Type)
   1032         {
   1033         case ACPI_PCCT_TYPE_GENERIC_SUBSPACE:
   1034 
   1035             InfoTable = AcpiDmTableInfoPcct0;
   1036             break;
   1037 
   1038         case ACPI_PCCT_TYPE_HW_REDUCED_SUBSPACE:
   1039 
   1040             InfoTable = AcpiDmTableInfoPcct1;
   1041             break;
   1042 
   1043         case ACPI_PCCT_TYPE_HW_REDUCED_SUBSPACE_TYPE2:
   1044 
   1045             InfoTable = AcpiDmTableInfoPcct2;
   1046             break;
   1047 
   1048         case ACPI_PCCT_TYPE_EXT_PCC_MASTER_SUBSPACE:
   1049 
   1050             InfoTable = AcpiDmTableInfoPcct3;
   1051             break;
   1052 
   1053         case ACPI_PCCT_TYPE_EXT_PCC_SLAVE_SUBSPACE:
   1054 
   1055             InfoTable = AcpiDmTableInfoPcct4;
   1056             break;
   1057 
   1058         case ACPI_PCCT_TYPE_HW_REG_COMM_SUBSPACE:
   1059 
   1060             InfoTable = AcpiDmTableInfoPcct5;
   1061             break;
   1062 
   1063         default:
   1064 
   1065             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "PCCT");
   1066             return (AE_ERROR);
   1067         }
   1068 
   1069         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   1070         if (ACPI_FAILURE (Status))
   1071         {
   1072             return (Status);
   1073         }
   1074 
   1075         ParentTable = DtPeekSubtable ();
   1076         DtInsertSubtable (ParentTable, Subtable);
   1077         DtPopSubtable ();
   1078     }
   1079 
   1080     return (AE_OK);
   1081 }
   1082 
   1083 
   1084 /******************************************************************************
   1085  *
   1086  * FUNCTION:    DtCompilePdtt
   1087  *
   1088  * PARAMETERS:  List                - Current field list pointer
   1089  *
   1090  * RETURN:      Status
   1091  *
   1092  * DESCRIPTION: Compile PDTT.
   1093  *
   1094  *****************************************************************************/
   1095 
   1096 ACPI_STATUS
   1097 DtCompilePdtt (
   1098     void                    **List)
   1099 {
   1100     ACPI_STATUS             Status;
   1101     DT_SUBTABLE             *Subtable;
   1102     DT_SUBTABLE             *ParentTable;
   1103     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1104     ACPI_TABLE_PDTT         *PdttHeader;
   1105     UINT32                  Count = 0;
   1106 
   1107 
   1108     /* Main table */
   1109 
   1110     Status = DtCompileTable (PFieldList, AcpiDmTableInfoPdtt, &Subtable);
   1111     if (ACPI_FAILURE (Status))
   1112     {
   1113         return (Status);
   1114     }
   1115 
   1116     ParentTable = DtPeekSubtable ();
   1117     DtInsertSubtable (ParentTable, Subtable);
   1118 
   1119     PdttHeader = ACPI_CAST_PTR (ACPI_TABLE_PDTT, ParentTable->Buffer);
   1120     PdttHeader->ArrayOffset = sizeof (ACPI_TABLE_PDTT);
   1121 
   1122     /* There is only one type of subtable at this time, no need to decode */
   1123 
   1124     while (*PFieldList)
   1125     {
   1126         /* List of subchannel IDs, each 2 bytes */
   1127 
   1128         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPdtt0,
   1129             &Subtable);
   1130         if (ACPI_FAILURE (Status))
   1131         {
   1132             return (Status);
   1133         }
   1134 
   1135         DtInsertSubtable (ParentTable, Subtable);
   1136         Count++;
   1137     }
   1138 
   1139     PdttHeader->TriggerCount = (UINT8) Count;
   1140     return (AE_OK);
   1141 }
   1142 
   1143 
   1144 /******************************************************************************
   1145  *
   1146  * FUNCTION:    DtCompilePhat
   1147  *
   1148  * PARAMETERS:  List                - Current field list pointer
   1149  *
   1150  * RETURN:      Status
   1151  *
   1152  * DESCRIPTION: Compile Phat.
   1153  *
   1154  *****************************************************************************/
   1155 
   1156 ACPI_STATUS
   1157 DtCompilePhat (
   1158     void                    **List)
   1159 {
   1160     ACPI_STATUS             Status = AE_OK;
   1161     DT_SUBTABLE             *Subtable;
   1162     DT_SUBTABLE             *ParentTable;
   1163     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1164     ACPI_PHAT_HEADER        *PhatHeader;
   1165     ACPI_DMTABLE_INFO       *Info;
   1166     ACPI_PHAT_VERSION_DATA  *VersionData;
   1167     UINT32                  DeviceDataLength;
   1168     UINT32                  RecordCount;
   1169     DT_FIELD                *DataOffsetField;
   1170     DT_FIELD                *DevicePathField;
   1171     UINT32                  TableOffset = 0;
   1172     UINT32                  DataOffsetValue;
   1173     UINT32                  i;
   1174 
   1175 
   1176     /* The table consists of subtables */
   1177 
   1178     while (*PFieldList)
   1179     {
   1180         /* Compile the common subtable header */
   1181 
   1182         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPhatHdr, &Subtable);
   1183         if (ACPI_FAILURE (Status))
   1184         {
   1185             return (Status);
   1186         }
   1187 
   1188         TableOffset += Subtable->Length;
   1189         DbgPrint (ASL_DEBUG_OUTPUT, "0 Subtable->Length: %X\n", Subtable->Length);
   1190 
   1191         ParentTable = DtPeekSubtable ();
   1192         DtInsertSubtable (ParentTable, Subtable);
   1193         DtPushSubtable (Subtable);
   1194 
   1195         PhatHeader = ACPI_CAST_PTR (ACPI_PHAT_HEADER, Subtable->Buffer);
   1196 
   1197         switch (PhatHeader->Type)
   1198         {
   1199         case ACPI_PHAT_TYPE_FW_VERSION_DATA:
   1200 
   1201             /* Compile the middle portion of the Firmware Version Data */
   1202 
   1203             Info = AcpiDmTableInfoPhat0;
   1204             PhatHeader->Length = sizeof (ACPI_PHAT_VERSION_DATA);
   1205             DataOffsetField = NULL;
   1206             break;
   1207 
   1208         case ACPI_PHAT_TYPE_FW_HEALTH_DATA:
   1209 
   1210             DbgPrint (ASL_DEBUG_OUTPUT, "1 Offset: %X, Name: \"%s\" Length: %X\n",
   1211                 (*PFieldList)->TableOffset, (*PFieldList)->Name, Subtable->Length);
   1212 
   1213             DataOffsetField = *PFieldList;
   1214 
   1215             /* Walk the field list to get to the "Device-specific data Offset" field */
   1216 
   1217             TableOffset = sizeof (ACPI_PHAT_HEALTH_DATA);
   1218             for (i = 0; i < 3; i++)
   1219             {
   1220                 DataOffsetField = DataOffsetField->Next;
   1221                 DbgPrint (ASL_DEBUG_OUTPUT, "2 Offset: %X, Name: \"%s\" Length: %X Value: %s:\n",
   1222                     TableOffset, DataOffsetField->Name, DataOffsetField->StringLength, DataOffsetField->Value);
   1223             }
   1224 
   1225             /* Convert DataOffsetField->Value (a char * string) to an integer value */
   1226 
   1227             sscanf (DataOffsetField->Value, "%X", &DataOffsetValue);
   1228 
   1229             /*
   1230              * Get the next field (Device Path):
   1231              * DataOffsetField points to "Device-Specific Offset", next field is
   1232              * "Device Path".
   1233              */
   1234             DevicePathField = DataOffsetField->Next;
   1235 
   1236             /* Compute the size of the input ASCII string as a unicode string (*2 + 2) */
   1237 
   1238             DevicePathField->StringLength = (strlen ((const char *) DevicePathField->Value) * 2) + 2;
   1239             TableOffset += DevicePathField->StringLength;
   1240 
   1241             DbgPrint (ASL_DEBUG_OUTPUT, "3 Offset: %X, Length: %X devicepathLength: %X\n",
   1242                 TableOffset, Subtable->Length, DevicePathField->StringLength);
   1243 
   1244             /* Set the DataOffsetField to the current TableOffset */
   1245             /* Must set the DataOffsetField here (not later) */
   1246 
   1247             if (DataOffsetValue != 0)
   1248             {
   1249                 snprintf (DataOffsetField->Value, Subtable->Length, "%X", TableOffset);
   1250             }
   1251 
   1252             DbgPrint (ASL_DEBUG_OUTPUT, "4 Offset: %X, Length: %X\n", TableOffset, Subtable->Length);
   1253 
   1254             DbgPrint (ASL_DEBUG_OUTPUT, "5 TableOffset: %X, DataOffsetField->StringLength: "
   1255                 "%X DevicePathField Length: %X DevicePathField->Value: %s, DataOffsetField->Value: %s DataOffsetField->ByteOffset %X\n",
   1256                 TableOffset, DataOffsetField->StringLength, DevicePathField->StringLength,
   1257                 DevicePathField->Value, DataOffsetField->Value, DataOffsetField->ByteOffset);
   1258 
   1259             /* Compile the middle portion of the Health Data Record */
   1260 
   1261             Info = AcpiDmTableInfoPhat1;
   1262             PhatHeader->Length = sizeof (ACPI_PHAT_HEALTH_DATA);
   1263             break;
   1264 
   1265         default:
   1266 
   1267             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, *PFieldList, "PHAT");
   1268             return (AE_ERROR);
   1269         }
   1270 
   1271         /* Compile either the Version Data or the Health Data */
   1272 
   1273         Status = DtCompileTable (PFieldList, Info, &Subtable);
   1274         if (ACPI_FAILURE (Status))
   1275         {
   1276             return (Status);
   1277         }
   1278 
   1279         DbgPrint (ASL_DEBUG_OUTPUT, "6 Offset: %X, Name: \"%s\" SubtableLength: %X\n",
   1280             TableOffset /* - StartTableOffset*/, (*PFieldList)->Name, Subtable->Length);
   1281 
   1282         ParentTable = DtPeekSubtable ();
   1283         DtInsertSubtable (ParentTable, Subtable);
   1284 
   1285         switch (PhatHeader->Type)
   1286         {
   1287         case ACPI_PHAT_TYPE_FW_VERSION_DATA:
   1288 
   1289             VersionData = ACPI_CAST_PTR (ACPI_PHAT_VERSION_DATA,
   1290                 (Subtable->Buffer - sizeof (ACPI_PHAT_HEADER)));
   1291             RecordCount = VersionData->ElementCount;
   1292 
   1293             /* Compile all of the Version Elements */
   1294 
   1295             while (RecordCount)
   1296             {
   1297                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoPhat0a,
   1298                     &Subtable);
   1299                 if (ACPI_FAILURE (Status))
   1300                 {
   1301                     return (Status);
   1302                 }
   1303 
   1304                 ParentTable = DtPeekSubtable ();
   1305                 DtInsertSubtable (ParentTable, Subtable);
   1306 
   1307                 TableOffset += Subtable->Length;
   1308                 RecordCount--;
   1309                 PhatHeader->Length += sizeof (ACPI_PHAT_VERSION_ELEMENT);
   1310             }
   1311 
   1312             DtPopSubtable ();
   1313             break;
   1314 
   1315         case ACPI_PHAT_TYPE_FW_HEALTH_DATA:
   1316 
   1317             /* Compile the Device Path */
   1318 
   1319             DeviceDataLength = Subtable->Length;
   1320             TableOffset += Subtable->Length;
   1321 
   1322             DbgPrint (ASL_DEBUG_OUTPUT, "7 Device Path Length: %X FieldName: \"%s\" FieldLength: "
   1323                 "%s FieldValue: %s SubtableLength: %X TableOffset: %X\n", DeviceDataLength,
   1324                 (*PFieldList)->Name, DataOffsetField->Value, (*PFieldList)->Value,
   1325                 Subtable->Length, TableOffset);
   1326 
   1327             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPhat1a, &Subtable);
   1328             if (ACPI_FAILURE (Status))
   1329             {
   1330                 return (Status);
   1331             }
   1332             ParentTable = DtPeekSubtable ();
   1333             DtInsertSubtable (ParentTable, Subtable);
   1334 
   1335             /* *PFieldList will be null if previous field was at the end-of-ParseTree (EOF) */
   1336 
   1337             if (!*PFieldList)
   1338             {
   1339                 DbgPrint (ASL_DEBUG_OUTPUT, "8 Exit on end-of-ParseTree\n");
   1340                 return (AE_OK);
   1341             }
   1342 
   1343             DbgPrint (ASL_DEBUG_OUTPUT, "9 Device Data Length: %X FieldName: \"%s"
   1344                 " TableOffset: %X FieldLength: %X Field Value: %s SubtableLength: %X\n",
   1345                 DeviceDataLength, (*PFieldList)->Name, TableOffset,
   1346                 (*PFieldList)->StringLength, (*PFieldList)->Value, Subtable->Length);
   1347 
   1348             PhatHeader->Length += (UINT16) Subtable->Length;
   1349 
   1350             /* Convert DataOffsetField->Value (a hex char * string) to an integer value */
   1351 
   1352             sscanf (DataOffsetField->Value, "%X", &DataOffsetValue);
   1353 
   1354             DbgPrint (ASL_DEBUG_OUTPUT, "10 Device-Specific Offset: %X Table Offset: %X\n",
   1355                 DataOffsetValue, TableOffset);
   1356             if (DataOffsetValue != 0)
   1357             {
   1358                 /* Compile Device-Specific Data - only if the Data Offset is non-zero */
   1359 
   1360                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoPhat1b, &Subtable);
   1361                 if (ACPI_FAILURE (Status))
   1362                 {
   1363                     return (Status);
   1364                 }
   1365 
   1366                 DbgPrint (ASL_DEBUG_OUTPUT, "11 Subtable: %p Table Offset: %X\n",
   1367                     Subtable, TableOffset);
   1368                 if (Subtable)
   1369                 {
   1370                     DbgPrint (ASL_DEBUG_OUTPUT, "12 Device Specific Offset: "
   1371                         "%X FieldName \"%s\" SubtableLength %X\n",
   1372                         DeviceDataLength, DataOffsetField->Name, Subtable->Length);
   1373 
   1374                     DeviceDataLength += Subtable->Length;
   1375 
   1376                     ParentTable = DtPeekSubtable ();
   1377                     DtInsertSubtable (ParentTable, Subtable);
   1378 
   1379                     PhatHeader->Length += (UINT16) Subtable->Length;
   1380                 }
   1381             }
   1382 
   1383             DtPopSubtable ();
   1384 
   1385             DbgPrint (ASL_DEBUG_OUTPUT, "13 FieldName: \"%s\" FieldLength: %X Field Value: %s\n",
   1386                 DataOffsetField->Name, DataOffsetField->StringLength, DataOffsetField->Value);
   1387             break;
   1388 
   1389         default:
   1390 
   1391             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, *PFieldList, "PHAT");
   1392             return (AE_ERROR);
   1393         }
   1394     }
   1395 
   1396     return (Status);
   1397 }
   1398 
   1399 
   1400 /******************************************************************************
   1401  *
   1402  * FUNCTION:    DtCompilePmtt
   1403  *
   1404  * PARAMETERS:  List                - Current field list pointer
   1405  *
   1406  * RETURN:      Status
   1407  *
   1408  * DESCRIPTION: Compile PMTT.
   1409  *
   1410  *****************************************************************************/
   1411 
   1412 ACPI_STATUS
   1413 DtCompilePmtt (
   1414     void                    **List)
   1415 {
   1416     ACPI_STATUS             Status;
   1417     DT_SUBTABLE             *Subtable;
   1418     DT_SUBTABLE             *ParentTable;
   1419     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1420     DT_FIELD                *SubtableStart;
   1421     UINT16                  Type;
   1422 
   1423 
   1424     /* Main table */
   1425 
   1426     Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmtt, &Subtable);
   1427     if (ACPI_FAILURE (Status))
   1428     {
   1429         return (Status);
   1430     }
   1431 
   1432     ParentTable = DtPeekSubtable ();
   1433     DtInsertSubtable (ParentTable, Subtable);
   1434     DtPushSubtable (Subtable);
   1435 
   1436     /* Subtables */
   1437 
   1438     while (*PFieldList)
   1439     {
   1440         SubtableStart = *PFieldList;
   1441         DtCompileInteger ((UINT8 *) &Type, *PFieldList, 2, 0);
   1442 
   1443         switch (Type)
   1444         {
   1445         case ACPI_PMTT_TYPE_SOCKET:
   1446 
   1447             /* Subtable: Socket Structure */
   1448 
   1449             DbgPrint (ASL_DEBUG_OUTPUT, "Compile PMTT_TYPE_SOCKET (0)\n");
   1450 
   1451             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmtt0,
   1452                 &Subtable);
   1453             if (ACPI_FAILURE (Status))
   1454             {
   1455                 return (Status);
   1456             }
   1457 
   1458             break;
   1459 
   1460         case ACPI_PMTT_TYPE_CONTROLLER:
   1461 
   1462             /* Subtable: Memory Controller Structure */
   1463 
   1464             DbgPrint (ASL_DEBUG_OUTPUT, "Compile PMTT_TYPE_CONTROLLER (1)\n");
   1465 
   1466             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmtt1,
   1467                 &Subtable);
   1468             if (ACPI_FAILURE (Status))
   1469             {
   1470                 return (Status);
   1471             }
   1472 
   1473             break;
   1474 
   1475         case ACPI_PMTT_TYPE_DIMM:
   1476 
   1477             /* Subtable: Physical Component (DIMM) Structure */
   1478 
   1479             DbgPrint (ASL_DEBUG_OUTPUT, "Compile PMTT_TYPE_DIMM (2)\n");
   1480             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmtt2,
   1481                 &Subtable);
   1482             if (ACPI_FAILURE (Status))
   1483             {
   1484                 return (Status);
   1485             }
   1486 
   1487             break;
   1488 
   1489         case ACPI_PMTT_TYPE_VENDOR:
   1490 
   1491             /* Subtable: Vendor-specific Structure */
   1492 
   1493             DbgPrint (ASL_DEBUG_OUTPUT, "Compile PMTT_TYPE_VENDOR(FF)\n");
   1494             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmttVendor,
   1495                 &Subtable);
   1496             if (ACPI_FAILURE (Status))
   1497             {
   1498                 return (Status);
   1499             }
   1500 
   1501             break;
   1502 
   1503         default:
   1504 
   1505             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "PMTT");
   1506             return (AE_ERROR);
   1507         }
   1508 
   1509         DtInsertSubtable (ParentTable, Subtable);
   1510     }
   1511 
   1512     return (Status);
   1513 }
   1514 
   1515 
   1516 /******************************************************************************
   1517  *
   1518  * FUNCTION:    DtCompilePptt
   1519  *
   1520  * PARAMETERS:  List                - Current field list pointer
   1521  *
   1522  * RETURN:      Status
   1523  *
   1524  * DESCRIPTION: Compile PPTT.
   1525  *
   1526  *****************************************************************************/
   1527 
   1528 ACPI_STATUS
   1529 DtCompilePptt (
   1530     void                    **List)
   1531 {
   1532     ACPI_STATUS             Status;
   1533     ACPI_SUBTABLE_HEADER    *PpttHeader;
   1534     ACPI_PPTT_PROCESSOR     *PpttProcessor = NULL;
   1535     DT_SUBTABLE             *Subtable;
   1536     DT_SUBTABLE             *ParentTable;
   1537     ACPI_DMTABLE_INFO       *InfoTable;
   1538     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1539     DT_FIELD                *SubtableStart;
   1540     ACPI_TABLE_HEADER       *PpttAcpiHeader;
   1541 
   1542 
   1543     ParentTable = DtPeekSubtable ();
   1544 
   1545     PpttAcpiHeader = ACPI_CAST_PTR (ACPI_TABLE_HEADER, ParentTable->Buffer);
   1546 
   1547     while (*PFieldList)
   1548     {
   1549         SubtableStart = *PFieldList;
   1550 
   1551         /* Compile PPTT subtable header */
   1552 
   1553         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPpttHdr,
   1554             &Subtable);
   1555         if (ACPI_FAILURE (Status))
   1556         {
   1557             return (Status);
   1558         }
   1559         DtInsertSubtable (ParentTable, Subtable);
   1560         PpttHeader = ACPI_CAST_PTR (ACPI_SUBTABLE_HEADER, Subtable->Buffer);
   1561         PpttHeader->Length = (UINT8)(Subtable->Length);
   1562 
   1563         switch (PpttHeader->Type)
   1564         {
   1565         case ACPI_PPTT_TYPE_PROCESSOR:
   1566 
   1567             InfoTable = AcpiDmTableInfoPptt0;
   1568             break;
   1569 
   1570         case ACPI_PPTT_TYPE_CACHE:
   1571 
   1572             if (PpttAcpiHeader->Revision < 3)
   1573             {
   1574                 InfoTable = AcpiDmTableInfoPptt1;
   1575             }
   1576             else
   1577             {
   1578                 InfoTable = AcpiDmTableInfoPptt1a;
   1579             }
   1580             break;
   1581 
   1582         case ACPI_PPTT_TYPE_ID:
   1583 
   1584             InfoTable = AcpiDmTableInfoPptt2;
   1585             break;
   1586 
   1587         default:
   1588 
   1589             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "PPTT");
   1590             return (AE_ERROR);
   1591         }
   1592 
   1593         /* Compile PPTT subtable body */
   1594 
   1595         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   1596         if (ACPI_FAILURE (Status))
   1597         {
   1598             return (Status);
   1599         }
   1600         DtInsertSubtable (ParentTable, Subtable);
   1601         PpttHeader->Length += (UINT8)(Subtable->Length);
   1602 
   1603         /* Compile PPTT subtable additional */
   1604 
   1605         switch (PpttHeader->Type)
   1606         {
   1607         case ACPI_PPTT_TYPE_PROCESSOR:
   1608 
   1609             PpttProcessor = ACPI_SUB_PTR (ACPI_PPTT_PROCESSOR,
   1610                 Subtable->Buffer, sizeof (ACPI_SUBTABLE_HEADER));
   1611             if (PpttProcessor)
   1612             {
   1613                 /* Compile initiator proximity domain list */
   1614 
   1615                 PpttProcessor->NumberOfPrivResources = 0;
   1616                 while (*PFieldList)
   1617                 {
   1618                     Status = DtCompileTable (PFieldList,
   1619                         AcpiDmTableInfoPptt0a, &Subtable);
   1620                     if (ACPI_FAILURE (Status))
   1621                     {
   1622                         return (Status);
   1623                     }
   1624                     if (!Subtable)
   1625                     {
   1626                         break;
   1627                     }
   1628 
   1629                     DtInsertSubtable (ParentTable, Subtable);
   1630                     PpttHeader->Length += (UINT8)(Subtable->Length);
   1631                     PpttProcessor->NumberOfPrivResources++;
   1632                 }
   1633             }
   1634             break;
   1635         default:
   1636 
   1637             break;
   1638         }
   1639     }
   1640 
   1641     return (AE_OK);
   1642 }
   1643 
   1644 
   1645 /******************************************************************************
   1646  *
   1647  * FUNCTION:    DtCompilePrmt
   1648  *
   1649  * PARAMETERS:  List                - Current field list pointer
   1650  *
   1651  * RETURN:      Status
   1652  *
   1653  * DESCRIPTION: Compile PRMT.
   1654  *
   1655  *****************************************************************************/
   1656 
   1657 ACPI_STATUS
   1658 DtCompilePrmt (
   1659     void                    **List)
   1660 {
   1661     ACPI_STATUS             Status;
   1662     ACPI_TABLE_PRMT_HEADER  *PrmtHeader;
   1663     ACPI_PRMT_MODULE_INFO   *PrmtModuleInfo;
   1664     DT_SUBTABLE             *Subtable;
   1665     DT_SUBTABLE             *ParentTable;
   1666     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1667     UINT32                  i, j;
   1668 
   1669     ParentTable = DtPeekSubtable ();
   1670 
   1671     /* Compile PRMT subtable header */
   1672 
   1673     Status = DtCompileTable (PFieldList, AcpiDmTableInfoPrmtHdr,
   1674         &Subtable);
   1675     if (ACPI_FAILURE (Status))
   1676     {
   1677         return (Status);
   1678     }
   1679     DtInsertSubtable (ParentTable, Subtable);
   1680     PrmtHeader = ACPI_CAST_PTR (ACPI_TABLE_PRMT_HEADER, Subtable->Buffer);
   1681 
   1682     for (i = 0; i < PrmtHeader->ModuleInfoCount; i++)
   1683     {
   1684         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPrmtModule,
   1685             &Subtable);
   1686         if (ACPI_FAILURE (Status))
   1687         {
   1688             return (Status);
   1689         }
   1690         DtInsertSubtable (ParentTable, Subtable);
   1691         PrmtModuleInfo = ACPI_CAST_PTR (ACPI_PRMT_MODULE_INFO, Subtable->Buffer);
   1692 
   1693         for (j = 0; j < PrmtModuleInfo->HandlerInfoCount; j++)
   1694         {
   1695             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPrmtHandler,
   1696                 &Subtable);
   1697             if (ACPI_FAILURE (Status))
   1698             {
   1699                 return (Status);
   1700             }
   1701             DtInsertSubtable (ParentTable, Subtable);
   1702         }
   1703     }
   1704 
   1705     return (AE_OK);
   1706 }
   1707 
   1708 
   1709 /******************************************************************************
   1710  *
   1711  * FUNCTION:    DtCompileRas2
   1712  *
   1713  * PARAMETERS:  List                - Current field list pointer
   1714  *
   1715  * RETURN:      Status
   1716  *
   1717  * DESCRIPTION: Compile RAS2.
   1718  *
   1719  *****************************************************************************/
   1720 
   1721 ACPI_STATUS
   1722 DtCompileRas2 (
   1723     void                    **List)
   1724 {
   1725     ACPI_STATUS             Status;
   1726     DT_SUBTABLE             *Subtable;
   1727     DT_SUBTABLE             *ParentTable;
   1728     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1729     ACPI_TABLE_RAS2         *Ras2Header;
   1730     UINT32                  Count = 0;
   1731 
   1732 
   1733     /* Main table */
   1734 
   1735     Status = DtCompileTable (PFieldList, AcpiDmTableInfoRas2, &Subtable);
   1736     if (ACPI_FAILURE (Status))
   1737     {
   1738         return (Status);
   1739     }
   1740 
   1741     ParentTable = DtPeekSubtable ();
   1742     DtInsertSubtable (ParentTable, Subtable);
   1743 
   1744     Ras2Header = ACPI_CAST_PTR (ACPI_TABLE_RAS2, ParentTable->Buffer);
   1745 
   1746     /* There is only one type of subtable at this time, no need to decode */
   1747 
   1748     while (*PFieldList)
   1749     {
   1750         /* List of RAS2 PCC descriptors, each 8 bytes */
   1751 
   1752         Status = DtCompileTable (PFieldList, AcpiDmTableInfoRas2PccDesc,
   1753             &Subtable);
   1754         if (ACPI_FAILURE (Status))
   1755         {
   1756             return (Status);
   1757         }
   1758 
   1759         DtInsertSubtable (ParentTable, Subtable);
   1760         Count++;
   1761     }
   1762 
   1763     Ras2Header->NumPccDescs = (UINT8) Count;
   1764     return (AE_OK);
   1765 }
   1766 
   1767 
   1768 /******************************************************************************
   1769  *
   1770  * FUNCTION:    DtCompileRgrt
   1771  *
   1772  * PARAMETERS:  List                - Current field list pointer
   1773  *
   1774  * RETURN:      Status
   1775  *
   1776  * DESCRIPTION: Compile RGRT.
   1777  *
   1778  *****************************************************************************/
   1779 
   1780 ACPI_STATUS
   1781 DtCompileRgrt (
   1782     void                    **List)
   1783 {
   1784     ACPI_STATUS             Status;
   1785     DT_SUBTABLE             *Subtable;
   1786     DT_SUBTABLE             *ParentTable;
   1787     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1788 
   1789 
   1790     /* Compile the main table */
   1791 
   1792     Status = DtCompileTable (PFieldList, AcpiDmTableInfoRgrt,
   1793         &Subtable);
   1794     if (ACPI_FAILURE (Status))
   1795     {
   1796         return (Status);
   1797     }
   1798 
   1799     ParentTable = DtPeekSubtable ();
   1800     DtInsertSubtable (ParentTable, Subtable);
   1801 
   1802     /* Compile the "Subtable" -- actually just the binary (PNG) image */
   1803 
   1804     Status = DtCompileTable (PFieldList, AcpiDmTableInfoRgrt0,
   1805         &Subtable);
   1806     if (ACPI_FAILURE (Status))
   1807     {
   1808         return (Status);
   1809     }
   1810 
   1811     DtInsertSubtable (ParentTable, Subtable);
   1812     return (AE_OK);
   1813 }
   1814 
   1815 
   1816 /******************************************************************************
   1817  *
   1818  * FUNCTION:    DtCompileRhct
   1819  *
   1820  * PARAMETERS:  List                - Current field list pointer
   1821  *
   1822  * RETURN:      Status
   1823  *
   1824  * DESCRIPTION: Compile RHCT.
   1825  *
   1826  *****************************************************************************/
   1827 
   1828 ACPI_STATUS
   1829 DtCompileRhct (
   1830     void                    **List)
   1831 {
   1832     ACPI_STATUS             Status;
   1833     ACPI_RHCT_NODE_HEADER   *RhctHeader;
   1834     ACPI_RHCT_HART_INFO     *RhctHartInfo;
   1835     DT_SUBTABLE             *Subtable;
   1836     DT_SUBTABLE             *ParentTable;
   1837     ACPI_DMTABLE_INFO       *InfoTable;
   1838     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1839     DT_FIELD                *SubtableStart;
   1840     ACPI_TABLE_RHCT         *Table;
   1841     BOOLEAN                 FirstNode = TRUE;
   1842 
   1843 
   1844     /* Compile the main table */
   1845 
   1846     ParentTable = DtPeekSubtable ();
   1847     Status = DtCompileTable (PFieldList, AcpiDmTableInfoRhct,
   1848         &Subtable);
   1849     if (ACPI_FAILURE (Status))
   1850     {
   1851         return (Status);
   1852     }
   1853     DtInsertSubtable (ParentTable, Subtable);
   1854     Table = ACPI_CAST_PTR (ACPI_TABLE_RHCT, ParentTable->Buffer);
   1855     Table->NodeCount = 0;
   1856     Table->NodeOffset = sizeof (ACPI_TABLE_RHCT);
   1857 
   1858     while (*PFieldList)
   1859     {
   1860         SubtableStart = *PFieldList;
   1861 
   1862         /* Compile RHCT subtable header */
   1863 
   1864         Status = DtCompileTable (PFieldList, AcpiDmTableInfoRhctNodeHdr,
   1865             &Subtable);
   1866         if (ACPI_FAILURE (Status))
   1867         {
   1868             return (Status);
   1869         }
   1870         DtInsertSubtable (ParentTable, Subtable);
   1871         RhctHeader = ACPI_CAST_PTR (ACPI_RHCT_NODE_HEADER, Subtable->Buffer);
   1872 
   1873         DtPushSubtable (Subtable);
   1874         ParentTable = DtPeekSubtable ();
   1875         Table->NodeCount++;
   1876 
   1877         switch (RhctHeader->Type)
   1878         {
   1879         case ACPI_RHCT_NODE_TYPE_ISA_STRING:
   1880 
   1881             InfoTable = AcpiDmTableInfoRhctIsa1;
   1882             break;
   1883 
   1884         case ACPI_RHCT_NODE_TYPE_HART_INFO:
   1885 
   1886             InfoTable = AcpiDmTableInfoRhctHartInfo1;
   1887             break;
   1888 
   1889         case ACPI_RHCT_NODE_TYPE_CMO:
   1890 
   1891             InfoTable = AcpiDmTableInfoRhctCmo1;
   1892             break;
   1893 
   1894         case ACPI_RHCT_NODE_TYPE_MMU:
   1895 
   1896             InfoTable = AcpiDmTableInfoRhctMmu1;
   1897             break;
   1898 
   1899         default:
   1900 
   1901             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "RHCT");
   1902             return (AE_ERROR);
   1903         }
   1904 
   1905         /* Compile RHCT subtable body */
   1906 
   1907         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   1908         if (ACPI_FAILURE (Status))
   1909         {
   1910             return (Status);
   1911         }
   1912         DtInsertSubtable (ParentTable, Subtable);
   1913         if (FirstNode)
   1914         {
   1915             Table->NodeOffset = ACPI_PTR_DIFF(ParentTable->Buffer, Table);
   1916             FirstNode = FALSE;
   1917         }
   1918 
   1919         /* Compile RHCT subtable additionals */
   1920 
   1921         switch (RhctHeader->Type)
   1922         {
   1923         case ACPI_RHCT_NODE_TYPE_ISA_STRING:
   1924 
   1925             /*
   1926              * Padding - Variable-length data
   1927              * Optionally allows the padding of the ISA string to be used
   1928              * for filling this field.
   1929              */
   1930             Status = DtCompileTable (PFieldList, AcpiDmTableInfoRhctIsaPad,
   1931                                      &Subtable);
   1932             if (ACPI_FAILURE (Status))
   1933             {
   1934                 return (Status);
   1935             }
   1936             if (Subtable)
   1937             {
   1938                 DtInsertSubtable (ParentTable, Subtable);
   1939             }
   1940             break;
   1941 
   1942         case ACPI_RHCT_NODE_TYPE_HART_INFO:
   1943 
   1944             RhctHartInfo = ACPI_CAST_PTR (ACPI_RHCT_HART_INFO,
   1945                 Subtable->Buffer);
   1946             RhctHartInfo->NumOffsets = 0;
   1947             while (*PFieldList)
   1948             {
   1949                 Status = DtCompileTable (PFieldList,
   1950                     AcpiDmTableInfoRhctHartInfo2, &Subtable);
   1951                 if (ACPI_FAILURE (Status))
   1952                 {
   1953                     return (Status);
   1954                 }
   1955                 if (!Subtable)
   1956                 {
   1957                     break;
   1958                 }
   1959                 DtInsertSubtable (ParentTable, Subtable);
   1960                 RhctHartInfo->NumOffsets++;
   1961             }
   1962             break;
   1963 
   1964         default:
   1965 
   1966             break;
   1967         }
   1968 
   1969         DtPopSubtable ();
   1970         ParentTable = DtPeekSubtable ();
   1971     }
   1972 
   1973     return (AE_OK);
   1974 }
   1975 
   1976 
   1977 /******************************************************************************
   1978  *
   1979  * FUNCTION:    DtCompileRsdt
   1980  *
   1981  * PARAMETERS:  List                - Current field list pointer
   1982  *
   1983  * RETURN:      Status
   1984  *
   1985  * DESCRIPTION: Compile RSDT.
   1986  *
   1987  *****************************************************************************/
   1988 
   1989 ACPI_STATUS
   1990 DtCompileRsdt (
   1991     void                    **List)
   1992 {
   1993     DT_SUBTABLE             *Subtable;
   1994     DT_SUBTABLE             *ParentTable;
   1995     DT_FIELD                *FieldList = *(DT_FIELD **) List;
   1996     UINT32                  Address;
   1997 
   1998 
   1999     ParentTable = DtPeekSubtable ();
   2000 
   2001     while (FieldList)
   2002     {
   2003         DtCompileInteger ((UINT8 *) &Address, FieldList, 4, DT_NON_ZERO);
   2004 
   2005         DtCreateSubtable ((UINT8 *) &Address, 4, &Subtable);
   2006         DtInsertSubtable (ParentTable, Subtable);
   2007         FieldList = FieldList->Next;
   2008     }
   2009 
   2010     return (AE_OK);
   2011 }
   2012 
   2013 
   2014 /******************************************************************************
   2015  *
   2016  * FUNCTION:    DtCompileS3pt
   2017  *
   2018  * PARAMETERS:  PFieldList          - Current field list pointer
   2019  *
   2020  * RETURN:      Status
   2021  *
   2022  * DESCRIPTION: Compile S3PT (Pointed to by FPDT)
   2023  *
   2024  *****************************************************************************/
   2025 
   2026 ACPI_STATUS
   2027 DtCompileS3pt (
   2028     DT_FIELD                **PFieldList)
   2029 {
   2030     ACPI_STATUS             Status;
   2031     ACPI_FPDT_HEADER        *S3ptHeader;
   2032     DT_SUBTABLE             *Subtable;
   2033     DT_SUBTABLE             *ParentTable;
   2034     ACPI_DMTABLE_INFO       *InfoTable;
   2035     DT_FIELD                *SubtableStart;
   2036 
   2037 
   2038     Status = DtCompileTable (PFieldList, AcpiDmTableInfoS3pt,
   2039         &AslGbl_RootTable);
   2040     if (ACPI_FAILURE (Status))
   2041     {
   2042         return (Status);
   2043     }
   2044 
   2045     DtPushSubtable (AslGbl_RootTable);
   2046 
   2047     while (*PFieldList)
   2048     {
   2049         SubtableStart = *PFieldList;
   2050         Status = DtCompileTable (PFieldList, AcpiDmTableInfoS3ptHdr,
   2051             &Subtable);
   2052         if (ACPI_FAILURE (Status))
   2053         {
   2054             return (Status);
   2055         }
   2056 
   2057         ParentTable = DtPeekSubtable ();
   2058         DtInsertSubtable (ParentTable, Subtable);
   2059         DtPushSubtable (Subtable);
   2060 
   2061         S3ptHeader = ACPI_CAST_PTR (ACPI_FPDT_HEADER, Subtable->Buffer);
   2062 
   2063         switch (S3ptHeader->Type)
   2064         {
   2065         case ACPI_S3PT_TYPE_RESUME:
   2066 
   2067             InfoTable = AcpiDmTableInfoS3pt0;
   2068             break;
   2069 
   2070         case ACPI_S3PT_TYPE_SUSPEND:
   2071 
   2072             InfoTable = AcpiDmTableInfoS3pt1;
   2073             break;
   2074 
   2075         default:
   2076 
   2077             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "S3PT");
   2078             return (AE_ERROR);
   2079         }
   2080 
   2081         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   2082         if (ACPI_FAILURE (Status))
   2083         {
   2084             return (Status);
   2085         }
   2086 
   2087         ParentTable = DtPeekSubtable ();
   2088         DtInsertSubtable (ParentTable, Subtable);
   2089         DtPopSubtable ();
   2090     }
   2091 
   2092     return (AE_OK);
   2093 }
   2094 
   2095 
   2096 /******************************************************************************
   2097  *
   2098  * FUNCTION:    DtCompileSdev
   2099  *
   2100  * PARAMETERS:  List                - Current field list pointer
   2101  *
   2102  * RETURN:      Status
   2103  *
   2104  * DESCRIPTION: Compile SDEV.
   2105  *
   2106  *****************************************************************************/
   2107 
   2108 ACPI_STATUS
   2109 DtCompileSdev (
   2110     void                    **List)
   2111 {
   2112     ACPI_STATUS                 Status;
   2113     ACPI_SDEV_HEADER            *SdevHeader;
   2114     ACPI_SDEV_HEADER            *SecureComponentHeader;
   2115     DT_SUBTABLE                 *Subtable;
   2116     DT_SUBTABLE                 *ParentTable;
   2117     ACPI_DMTABLE_INFO           *InfoTable;
   2118     ACPI_DMTABLE_INFO           *SecureComponentInfoTable = NULL;
   2119     DT_FIELD                    **PFieldList = (DT_FIELD **) List;
   2120     DT_FIELD                    *SubtableStart;
   2121     ACPI_SDEV_PCIE              *Pcie = NULL;
   2122     ACPI_SDEV_NAMESPACE         *Namesp = NULL;
   2123     UINT32                      EntryCount;
   2124     ACPI_SDEV_SECURE_COMPONENT  *SecureComponent = NULL;
   2125     UINT16                      ComponentLength = 0;
   2126 
   2127 
   2128     /* Subtables */
   2129 
   2130     while (*PFieldList)
   2131     {
   2132         /* Compile common SDEV subtable header */
   2133 
   2134         SubtableStart = *PFieldList;
   2135         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdevHdr,
   2136             &Subtable);
   2137         if (ACPI_FAILURE (Status))
   2138         {
   2139             return (Status);
   2140         }
   2141 
   2142         ParentTable = DtPeekSubtable ();
   2143         DtInsertSubtable (ParentTable, Subtable);
   2144         DtPushSubtable (Subtable);
   2145 
   2146         SdevHeader = ACPI_CAST_PTR (ACPI_SDEV_HEADER, Subtable->Buffer);
   2147         SdevHeader->Length = (UINT8)(sizeof (ACPI_SDEV_HEADER));
   2148 
   2149         switch (SdevHeader->Type)
   2150         {
   2151         case ACPI_SDEV_TYPE_NAMESPACE_DEVICE:
   2152 
   2153             InfoTable = AcpiDmTableInfoSdev0;
   2154             Namesp = ACPI_CAST_PTR (ACPI_SDEV_NAMESPACE, Subtable->Buffer);
   2155             SecureComponent = ACPI_CAST_PTR (ACPI_SDEV_SECURE_COMPONENT,
   2156                 ACPI_ADD_PTR (UINT8, Subtable->Buffer, sizeof(ACPI_SDEV_NAMESPACE)));
   2157             break;
   2158 
   2159         case ACPI_SDEV_TYPE_PCIE_ENDPOINT_DEVICE:
   2160 
   2161             InfoTable = AcpiDmTableInfoSdev1;
   2162             Pcie = ACPI_CAST_PTR (ACPI_SDEV_PCIE, Subtable->Buffer);
   2163             break;
   2164 
   2165         default:
   2166 
   2167             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "SDEV");
   2168             return (AE_ERROR);
   2169         }
   2170 
   2171         /* Compile SDEV subtable body */
   2172 
   2173         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   2174         if (ACPI_FAILURE (Status))
   2175         {
   2176             return (Status);
   2177         }
   2178 
   2179         ParentTable = DtPeekSubtable ();
   2180         DtInsertSubtable (ParentTable, Subtable);
   2181 
   2182         /* Optional data fields are appended to the main subtable body */
   2183 
   2184         switch (SdevHeader->Type)
   2185         {
   2186         case ACPI_SDEV_TYPE_NAMESPACE_DEVICE:
   2187 
   2188             /*
   2189              * Device Id Offset will be be calculated differently depending on
   2190              * the presence of secure access components.
   2191              */
   2192             Namesp->DeviceIdOffset = 0;
   2193             ComponentLength = 0;
   2194 
   2195             /* If the secure access component exists, get the structures */
   2196 
   2197             if (SdevHeader->Flags & ACPI_SDEV_SECURE_COMPONENTS_PRESENT)
   2198             {
   2199                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev0b,
   2200                     &Subtable);
   2201                 if (ACPI_FAILURE (Status))
   2202                 {
   2203                     return (Status);
   2204                 }
   2205                 ParentTable = DtPeekSubtable ();
   2206                 DtInsertSubtable (ParentTable, Subtable);
   2207 
   2208                 Namesp->DeviceIdOffset += sizeof (ACPI_SDEV_SECURE_COMPONENT);
   2209 
   2210                 /* Compile a secure access component header */
   2211 
   2212                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdevSecCompHdr,
   2213                     &Subtable);
   2214                 if (ACPI_FAILURE (Status))
   2215                 {
   2216                     return (Status);
   2217                 }
   2218                 ParentTable = DtPeekSubtable ();
   2219                 DtInsertSubtable (ParentTable, Subtable);
   2220 
   2221                 /* Compile the secure access component */
   2222 
   2223                 SecureComponentHeader = ACPI_CAST_PTR (ACPI_SDEV_HEADER, Subtable->Buffer);
   2224                 switch (SecureComponentHeader->Type)
   2225                 {
   2226                 case ACPI_SDEV_TYPE_ID_COMPONENT:
   2227 
   2228                     SecureComponentInfoTable = AcpiDmTableInfoSdevSecCompId;
   2229                     Namesp->DeviceIdOffset += sizeof (ACPI_SDEV_ID_COMPONENT);
   2230                     ComponentLength = sizeof (ACPI_SDEV_ID_COMPONENT);
   2231                     break;
   2232 
   2233                 case ACPI_SDEV_TYPE_MEM_COMPONENT:
   2234 
   2235                     SecureComponentInfoTable = AcpiDmTableInfoSdevSecCompMem;
   2236                     Namesp->DeviceIdOffset += sizeof (ACPI_SDEV_MEM_COMPONENT);
   2237                     ComponentLength = sizeof (ACPI_SDEV_MEM_COMPONENT);
   2238                     break;
   2239 
   2240                 default:
   2241 
   2242                     /* Any other secure component types are undefined */
   2243 
   2244                     return (AE_ERROR);
   2245                 }
   2246 
   2247                 Status = DtCompileTable (PFieldList, SecureComponentInfoTable,
   2248                     &Subtable);
   2249                 if (ACPI_FAILURE (Status))
   2250                 {
   2251                     return (Status);
   2252                 }
   2253                 ParentTable = DtPeekSubtable ();
   2254                 DtInsertSubtable (ParentTable, Subtable);
   2255 
   2256                 SecureComponent->SecureComponentOffset =
   2257                     sizeof (ACPI_SDEV_NAMESPACE) + sizeof (ACPI_SDEV_SECURE_COMPONENT);
   2258                 SecureComponent->SecureComponentLength = ComponentLength;
   2259 
   2260 
   2261                 /*
   2262                  * Add the secure component to the subtable to be added for the
   2263                  * the namespace subtable's length
   2264                  */
   2265                 ComponentLength += sizeof (ACPI_SDEV_SECURE_COMPONENT);
   2266             }
   2267 
   2268             /* Append DeviceId namespace string */
   2269 
   2270             Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev0a,
   2271                 &Subtable);
   2272             if (ACPI_FAILURE (Status))
   2273             {
   2274                 return (Status);
   2275             }
   2276 
   2277             if (!Subtable)
   2278             {
   2279                 break;
   2280             }
   2281 
   2282             ParentTable = DtPeekSubtable ();
   2283             DtInsertSubtable (ParentTable, Subtable);
   2284 
   2285             Namesp->DeviceIdOffset += sizeof (ACPI_SDEV_NAMESPACE);
   2286 
   2287             Namesp->DeviceIdLength = (UINT16) Subtable->Length;
   2288 
   2289             /* Append Vendor data */
   2290 
   2291             Namesp->VendorDataLength = 0;
   2292             Namesp->VendorDataOffset = 0;
   2293 
   2294             if (*PFieldList)
   2295             {
   2296                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev1b,
   2297                     &Subtable);
   2298                 if (ACPI_FAILURE (Status))
   2299                 {
   2300                     return (Status);
   2301                 }
   2302 
   2303                 if (Subtable)
   2304                 {
   2305                     ParentTable = DtPeekSubtable ();
   2306                     DtInsertSubtable (ParentTable, Subtable);
   2307 
   2308                     Namesp->VendorDataOffset =
   2309                         Namesp->DeviceIdOffset + Namesp->DeviceIdLength;
   2310                     Namesp->VendorDataLength =
   2311                         (UINT16) Subtable->Length;
   2312 
   2313                     /* Final size of entire namespace structure */
   2314 
   2315                     SdevHeader->Length = (UINT16)(sizeof(ACPI_SDEV_NAMESPACE) +
   2316                         Subtable->Length + Namesp->DeviceIdLength) + ComponentLength;
   2317                 }
   2318             }
   2319 
   2320             break;
   2321 
   2322         case ACPI_SDEV_TYPE_PCIE_ENDPOINT_DEVICE:
   2323 
   2324             /* Append the PCIe path info first */
   2325 
   2326             EntryCount = 0;
   2327             while (*PFieldList && !strcmp ((*PFieldList)->Name, "Device"))
   2328             {
   2329                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev1a,
   2330                     &Subtable);
   2331                 if (ACPI_FAILURE (Status))
   2332                 {
   2333                     return (Status);
   2334                 }
   2335 
   2336                 if (!Subtable)
   2337                 {
   2338                     DtPopSubtable ();
   2339                     break;
   2340                 }
   2341 
   2342                 ParentTable = DtPeekSubtable ();
   2343                 DtInsertSubtable (ParentTable, Subtable);
   2344                 EntryCount++;
   2345             }
   2346 
   2347             /* Path offset will point immediately after the main subtable */
   2348 
   2349             Pcie->PathOffset = sizeof (ACPI_SDEV_PCIE);
   2350             Pcie->PathLength = (UINT16)
   2351                 (EntryCount * sizeof (ACPI_SDEV_PCIE_PATH));
   2352 
   2353             /* Append the Vendor Data last */
   2354 
   2355             Pcie->VendorDataLength = 0;
   2356             Pcie->VendorDataOffset = 0;
   2357 
   2358             if (*PFieldList)
   2359             {
   2360                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev1b,
   2361                     &Subtable);
   2362                 if (ACPI_FAILURE (Status))
   2363                 {
   2364                     return (Status);
   2365                 }
   2366 
   2367                 if (Subtable)
   2368                 {
   2369                     ParentTable = DtPeekSubtable ();
   2370                     DtInsertSubtable (ParentTable, Subtable);
   2371 
   2372                     Pcie->VendorDataOffset =
   2373                         Pcie->PathOffset + Pcie->PathLength;
   2374                     Pcie->VendorDataLength = (UINT16)
   2375                         Subtable->Length;
   2376                 }
   2377             }
   2378 
   2379             SdevHeader->Length =
   2380                 sizeof (ACPI_SDEV_PCIE) +
   2381                 Pcie->PathLength + Pcie->VendorDataLength;
   2382             break;
   2383 
   2384         default:
   2385 
   2386             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "SDEV");
   2387             return (AE_ERROR);
   2388         }
   2389 
   2390         DtPopSubtable ();
   2391     }
   2392 
   2393     return (AE_OK);
   2394 }
   2395 
   2396 
   2397 /******************************************************************************
   2398  *
   2399  * FUNCTION:    DtCompileSlic
   2400  *
   2401  * PARAMETERS:  List                - Current field list pointer
   2402  *
   2403  * RETURN:      Status
   2404  *
   2405  * DESCRIPTION: Compile SLIC.
   2406  *
   2407  *****************************************************************************/
   2408 
   2409 ACPI_STATUS
   2410 DtCompileSlic (
   2411     void                    **List)
   2412 {
   2413     ACPI_STATUS             Status;
   2414     DT_SUBTABLE             *Subtable;
   2415     DT_SUBTABLE             *ParentTable;
   2416     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2417 
   2418 
   2419     while (*PFieldList)
   2420     {
   2421         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSlic,
   2422             &Subtable);
   2423         if (ACPI_FAILURE (Status))
   2424         {
   2425             return (Status);
   2426         }
   2427 
   2428         ParentTable = DtPeekSubtable ();
   2429         DtInsertSubtable (ParentTable, Subtable);
   2430         DtPushSubtable (Subtable);
   2431         DtPopSubtable ();
   2432     }
   2433 
   2434     return (AE_OK);
   2435 }
   2436 
   2437 
   2438 /******************************************************************************
   2439  *
   2440  * FUNCTION:    DtCompileSlit
   2441  *
   2442  * PARAMETERS:  List                - Current field list pointer
   2443  *
   2444  * RETURN:      Status
   2445  *
   2446  * DESCRIPTION: Compile SLIT.
   2447  *
   2448  *****************************************************************************/
   2449 
   2450 ACPI_STATUS
   2451 DtCompileSlit (
   2452     void                    **List)
   2453 {
   2454     ACPI_STATUS             Status;
   2455     DT_SUBTABLE             *Subtable;
   2456     DT_SUBTABLE             *ParentTable;
   2457     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2458     DT_FIELD                *FieldList;
   2459     DT_FIELD                *EndOfFieldList = NULL;
   2460     UINT32                  Localities;
   2461     UINT32                  LocalityListLength;
   2462     UINT8                   *LocalityBuffer;
   2463 
   2464 
   2465     Status = DtCompileTable (PFieldList, AcpiDmTableInfoSlit,
   2466         &Subtable);
   2467     if (ACPI_FAILURE (Status))
   2468     {
   2469         return (Status);
   2470     }
   2471 
   2472     ParentTable = DtPeekSubtable ();
   2473     DtInsertSubtable (ParentTable, Subtable);
   2474 
   2475     Localities = *ACPI_CAST_PTR (UINT32, Subtable->Buffer);
   2476     LocalityBuffer = UtLocalCalloc (Localities);
   2477     LocalityListLength = 0;
   2478 
   2479     /* Compile each locality buffer */
   2480 
   2481     FieldList = *PFieldList;
   2482     while (FieldList)
   2483     {
   2484         DtCompileBuffer (LocalityBuffer,
   2485             FieldList->Value, FieldList, Localities);
   2486 
   2487         LocalityListLength++;
   2488         DtCreateSubtable (LocalityBuffer, Localities, &Subtable);
   2489         DtInsertSubtable (ParentTable, Subtable);
   2490         EndOfFieldList = FieldList;
   2491         FieldList = FieldList->Next;
   2492     }
   2493 
   2494     if (LocalityListLength != Localities)
   2495     {
   2496         sprintf(AslGbl_MsgBuffer,
   2497             "Found %u entries, must match LocalityCount: %u",
   2498             LocalityListLength, Localities);
   2499         DtError (ASL_ERROR, ASL_MSG_ENTRY_LIST, EndOfFieldList, AslGbl_MsgBuffer);
   2500         ACPI_FREE (LocalityBuffer);
   2501         return (AE_LIMIT);
   2502     }
   2503 
   2504     ACPI_FREE (LocalityBuffer);
   2505     return (AE_OK);
   2506 }
   2507 
   2508 
   2509 /******************************************************************************
   2510  *
   2511  * FUNCTION:    DtCompileSrat
   2512  *
   2513  * PARAMETERS:  List                - Current field list pointer
   2514  *
   2515  * RETURN:      Status
   2516  *
   2517  * DESCRIPTION: Compile SRAT.
   2518  *
   2519  *****************************************************************************/
   2520 
   2521 ACPI_STATUS
   2522 DtCompileSrat (
   2523     void                    **List)
   2524 {
   2525     ACPI_STATUS             Status;
   2526     DT_SUBTABLE             *Subtable;
   2527     DT_SUBTABLE             *ParentTable;
   2528     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2529     DT_FIELD                *SubtableStart;
   2530     ACPI_SUBTABLE_HEADER    *SratHeader;
   2531     ACPI_DMTABLE_INFO       *InfoTable;
   2532 
   2533 
   2534     Status = DtCompileTable (PFieldList, AcpiDmTableInfoSrat,
   2535         &Subtable);
   2536     if (ACPI_FAILURE (Status))
   2537     {
   2538         return (Status);
   2539     }
   2540 
   2541     ParentTable = DtPeekSubtable ();
   2542     DtInsertSubtable (ParentTable, Subtable);
   2543 
   2544     while (*PFieldList)
   2545     {
   2546         SubtableStart = *PFieldList;
   2547         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSratHdr,
   2548             &Subtable);
   2549         if (ACPI_FAILURE (Status))
   2550         {
   2551             return (Status);
   2552         }
   2553 
   2554         ParentTable = DtPeekSubtable ();
   2555         DtInsertSubtable (ParentTable, Subtable);
   2556         DtPushSubtable (Subtable);
   2557 
   2558         SratHeader = ACPI_CAST_PTR (ACPI_SUBTABLE_HEADER, Subtable->Buffer);
   2559 
   2560         switch (SratHeader->Type)
   2561         {
   2562         case ACPI_SRAT_TYPE_CPU_AFFINITY:
   2563 
   2564             InfoTable = AcpiDmTableInfoSrat0;
   2565             break;
   2566 
   2567         case ACPI_SRAT_TYPE_MEMORY_AFFINITY:
   2568 
   2569             InfoTable = AcpiDmTableInfoSrat1;
   2570             break;
   2571 
   2572         case ACPI_SRAT_TYPE_X2APIC_CPU_AFFINITY:
   2573 
   2574             InfoTable = AcpiDmTableInfoSrat2;
   2575             break;
   2576 
   2577         case ACPI_SRAT_TYPE_GICC_AFFINITY:
   2578 
   2579             InfoTable = AcpiDmTableInfoSrat3;
   2580             break;
   2581 
   2582         case ACPI_SRAT_TYPE_GIC_ITS_AFFINITY:
   2583 
   2584             InfoTable = AcpiDmTableInfoSrat4;
   2585             break;
   2586 
   2587         case ACPI_SRAT_TYPE_GENERIC_AFFINITY:
   2588 
   2589             InfoTable = AcpiDmTableInfoSrat5;
   2590             break;
   2591 
   2592         case ACPI_SRAT_TYPE_GENERIC_PORT_AFFINITY:
   2593 
   2594             InfoTable = AcpiDmTableInfoSrat6;
   2595             break;
   2596 
   2597         case ACPI_SRAT_TYPE_RINTC_AFFINITY:
   2598 
   2599             InfoTable = AcpiDmTableInfoSrat7;
   2600             break;
   2601 
   2602         default:
   2603 
   2604             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "SRAT");
   2605             return (AE_ERROR);
   2606         }
   2607 
   2608         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   2609         if (ACPI_FAILURE (Status))
   2610         {
   2611             return (Status);
   2612         }
   2613 
   2614         ParentTable = DtPeekSubtable ();
   2615         DtInsertSubtable (ParentTable, Subtable);
   2616         DtPopSubtable ();
   2617     }
   2618 
   2619     return (AE_OK);
   2620 }
   2621 
   2622 
   2623 /******************************************************************************
   2624  *
   2625  * FUNCTION:    DtCompileStao
   2626  *
   2627  * PARAMETERS:  PFieldList          - Current field list pointer
   2628  *
   2629  * RETURN:      Status
   2630  *
   2631  * DESCRIPTION: Compile STAO.
   2632  *
   2633  *****************************************************************************/
   2634 
   2635 ACPI_STATUS
   2636 DtCompileStao (
   2637     void                    **List)
   2638 {
   2639     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2640     DT_SUBTABLE             *Subtable;
   2641     DT_SUBTABLE             *ParentTable;
   2642     ACPI_STATUS             Status;
   2643 
   2644 
   2645     /* Compile the main table */
   2646 
   2647     Status = DtCompileTable (PFieldList, AcpiDmTableInfoStao,
   2648         &Subtable);
   2649     if (ACPI_FAILURE (Status))
   2650     {
   2651         return (Status);
   2652     }
   2653 
   2654     ParentTable = DtPeekSubtable ();
   2655     DtInsertSubtable (ParentTable, Subtable);
   2656 
   2657     /* Compile each ASCII namestring as a subtable */
   2658 
   2659     while (*PFieldList)
   2660     {
   2661         Status = DtCompileTable (PFieldList, AcpiDmTableInfoStaoStr,
   2662             &Subtable);
   2663         if (ACPI_FAILURE (Status))
   2664         {
   2665             return (Status);
   2666         }
   2667 
   2668         ParentTable = DtPeekSubtable ();
   2669         DtInsertSubtable (ParentTable, Subtable);
   2670     }
   2671 
   2672     return (AE_OK);
   2673 }
   2674 
   2675 
   2676 /******************************************************************************
   2677  *
   2678  * FUNCTION:    DtCompileSvkl
   2679  *
   2680  * PARAMETERS:  PFieldList          - Current field list pointer
   2681  *
   2682  * RETURN:      Status
   2683  *
   2684  * DESCRIPTION: Compile SVKL.
   2685  *
   2686  * NOTES: SVKL is essentially a flat table, with a small main table and
   2687  *          a variable number of a single type of subtable.
   2688  *
   2689  *****************************************************************************/
   2690 
   2691 ACPI_STATUS
   2692 DtCompileSvkl (
   2693     void                    **List)
   2694 {
   2695     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2696     DT_SUBTABLE             *Subtable;
   2697     DT_SUBTABLE             *ParentTable;
   2698     ACPI_STATUS             Status;
   2699 
   2700 
   2701     /* Compile the main table */
   2702 
   2703     Status = DtCompileTable (PFieldList, AcpiDmTableInfoSvkl,
   2704         &Subtable);
   2705     if (ACPI_FAILURE (Status))
   2706     {
   2707         return (Status);
   2708     }
   2709 
   2710     ParentTable = DtPeekSubtable ();
   2711     DtInsertSubtable (ParentTable, Subtable);
   2712 
   2713     /* Compile each subtable */
   2714 
   2715     while (*PFieldList)
   2716     {
   2717         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSvkl0,
   2718             &Subtable);
   2719         if (ACPI_FAILURE (Status))
   2720         {
   2721             return (Status);
   2722         }
   2723 
   2724         ParentTable = DtPeekSubtable ();
   2725         DtInsertSubtable (ParentTable, Subtable);
   2726     }
   2727 
   2728     return (AE_OK);
   2729 }
   2730 
   2731 
   2732 /******************************************************************************
   2733  *
   2734  * FUNCTION:    DtCompileSwft
   2735  *
   2736  * PARAMETERS:  PFieldList          - Current field list pointer
   2737  *
   2738  * RETURN:      Status
   2739  *
   2740  * DESCRIPTION: Compile SWFT.
   2741  *
   2742  *****************************************************************************/
   2743 
   2744 ACPI_STATUS
   2745 DtCompileSwft (
   2746     void                    **List)
   2747 {
   2748     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2749     DT_SUBTABLE             *HdrSub;
   2750     DT_SUBTABLE             *DataSub;
   2751     DT_SUBTABLE             *ParentTable;
   2752     ACPI_STATUS             Status;
   2753 
   2754     /* Main SWFT header */
   2755     Status = DtCompileTable (PFieldList, AcpiDmTableInfoSwft, &HdrSub);
   2756     if (ACPI_FAILURE (Status))
   2757     {
   2758         return (Status);
   2759     }
   2760 
   2761     ParentTable = DtPeekSubtable ();
   2762     DtInsertSubtable (ParentTable, HdrSub);
   2763 
   2764     while (*PFieldList)
   2765     {
   2766         /* File header */
   2767         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSwftFileHdr,
   2768                                  &HdrSub);
   2769         if (ACPI_FAILURE (Status))
   2770         {
   2771             return (Status);
   2772         }
   2773 
   2774         DtInsertSubtable (ParentTable, HdrSub);
   2775 
   2776         /* File data */
   2777         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSwftFileData,
   2778                                  &DataSub);
   2779         if (ACPI_FAILURE (Status))
   2780         {
   2781             return (Status);
   2782         }
   2783 
   2784         DtInsertSubtable (ParentTable, DataSub);
   2785     }
   2786 
   2787     return (AE_OK);
   2788 }
   2789 
   2790 /******************************************************************************
   2791  *
   2792  * FUNCTION:    DtCompileTcpa
   2793  *
   2794  * PARAMETERS:  PFieldList          - Current field list pointer
   2795  *
   2796  * RETURN:      Status
   2797  *
   2798  * DESCRIPTION: Compile TCPA.
   2799  *
   2800  *****************************************************************************/
   2801 
   2802 ACPI_STATUS
   2803 DtCompileTcpa (
   2804     void                    **List)
   2805 {
   2806     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2807     DT_SUBTABLE             *Subtable;
   2808     ACPI_TABLE_TCPA_HDR     *TcpaHeader;
   2809     DT_SUBTABLE             *ParentTable;
   2810     ACPI_STATUS             Status;
   2811 
   2812 
   2813     /* Compile the main table */
   2814 
   2815     Status = DtCompileTable (PFieldList, AcpiDmTableInfoTcpaHdr,
   2816         &Subtable);
   2817     if (ACPI_FAILURE (Status))
   2818     {
   2819         return (Status);
   2820     }
   2821 
   2822     ParentTable = DtPeekSubtable ();
   2823     DtInsertSubtable (ParentTable, Subtable);
   2824 
   2825     /*
   2826      * Examine the PlatformClass field to determine the table type.
   2827      * Either a client or server table. Only one.
   2828      */
   2829     TcpaHeader = ACPI_CAST_PTR (ACPI_TABLE_TCPA_HDR, ParentTable->Buffer);
   2830 
   2831     switch (TcpaHeader->PlatformClass)
   2832     {
   2833     case ACPI_TCPA_CLIENT_TABLE:
   2834 
   2835         Status = DtCompileTable (PFieldList, AcpiDmTableInfoTcpaClient,
   2836             &Subtable);
   2837         break;
   2838 
   2839     case ACPI_TCPA_SERVER_TABLE:
   2840 
   2841         Status = DtCompileTable (PFieldList, AcpiDmTableInfoTcpaServer,
   2842             &Subtable);
   2843         break;
   2844 
   2845     default:
   2846 
   2847         AcpiOsPrintf ("\n**** Unknown TCPA Platform Class 0x%X\n",
   2848             TcpaHeader->PlatformClass);
   2849         Status = AE_ERROR;
   2850         break;
   2851     }
   2852 
   2853     ParentTable = DtPeekSubtable ();
   2854     DtInsertSubtable (ParentTable, Subtable);
   2855     return (Status);
   2856 }
   2857 
   2858 
   2859 /******************************************************************************
   2860  *
   2861  * FUNCTION:    DtCompileTpm2Rev3
   2862  *
   2863  * PARAMETERS:  PFieldList          - Current field list pointer
   2864  *
   2865  * RETURN:      Status
   2866  *
   2867  * DESCRIPTION: Compile TPM2 revision 3
   2868  *
   2869  *****************************************************************************/
   2870 static ACPI_STATUS
   2871 DtCompileTpm2Rev3 (
   2872     void                    **List)
   2873 {
   2874     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2875     DT_SUBTABLE             *Subtable;
   2876     ACPI_TABLE_TPM23        *Tpm23Header;
   2877     DT_SUBTABLE             *ParentTable;
   2878     ACPI_STATUS             Status = AE_OK;
   2879 
   2880 
   2881     Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm23,
   2882         &Subtable);
   2883 
   2884     ParentTable = DtPeekSubtable ();
   2885     DtInsertSubtable (ParentTable, Subtable);
   2886     Tpm23Header = ACPI_CAST_PTR (ACPI_TABLE_TPM23, ParentTable->Buffer);
   2887 
   2888     /* Subtable type depends on the StartMethod */
   2889 
   2890     switch (Tpm23Header->StartMethod)
   2891     {
   2892     case ACPI_TPM23_ACPI_START_METHOD:
   2893 
   2894         /* Subtable specific to to ARM_SMC */
   2895 
   2896         Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm23a,
   2897             &Subtable);
   2898         if (ACPI_FAILURE (Status))
   2899         {
   2900             return (Status);
   2901         }
   2902 
   2903         ParentTable = DtPeekSubtable ();
   2904         DtInsertSubtable (ParentTable, Subtable);
   2905         break;
   2906 
   2907     default:
   2908         break;
   2909     }
   2910 
   2911     return (Status);
   2912 }
   2913 
   2914 
   2915 /******************************************************************************
   2916  *
   2917  * FUNCTION:    DtCompileTpm2
   2918  *
   2919  * PARAMETERS:  PFieldList          - Current field list pointer
   2920  *
   2921  * RETURN:      Status
   2922  *
   2923  * DESCRIPTION: Compile TPM2.
   2924  *
   2925  *****************************************************************************/
   2926 
   2927 ACPI_STATUS
   2928 DtCompileTpm2 (
   2929     void                    **List)
   2930 {
   2931     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2932     DT_SUBTABLE             *Subtable;
   2933     ACPI_TABLE_TPM2         *Tpm2Header;
   2934     DT_SUBTABLE             *ParentTable;
   2935     ACPI_STATUS             Status = AE_OK;
   2936     ACPI_TABLE_HEADER       *Header;
   2937 
   2938 
   2939     ParentTable = DtPeekSubtable ();
   2940 
   2941     Header = ACPI_CAST_PTR (ACPI_TABLE_HEADER, ParentTable->Buffer);
   2942 
   2943     if (Header->Revision == 3)
   2944     {
   2945         return (DtCompileTpm2Rev3 (List));
   2946     }
   2947 
   2948     /* Compile the main table */
   2949 
   2950     Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm2,
   2951         &Subtable);
   2952     if (ACPI_FAILURE (Status))
   2953     {
   2954         return (Status);
   2955     }
   2956 
   2957     ParentTable = DtPeekSubtable ();
   2958     DtInsertSubtable (ParentTable, Subtable);
   2959 
   2960     Tpm2Header = ACPI_CAST_PTR (ACPI_TABLE_TPM2, ParentTable->Buffer);
   2961 
   2962     /* Method parameters */
   2963     /* Optional: Log area minimum length */
   2964     /* Optional: Log area start address */
   2965     /* TBD: Optional fields above not fully implemented (not optional at this time) */
   2966 
   2967     Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm2a,
   2968         &Subtable);
   2969     if (ACPI_FAILURE (Status))
   2970     {
   2971         return (Status);
   2972     }
   2973 
   2974     ParentTable = DtPeekSubtable ();
   2975     DtInsertSubtable (ParentTable, Subtable);
   2976 
   2977 
   2978     /* Subtable type depends on the StartMethod */
   2979 
   2980     switch (Tpm2Header->StartMethod)
   2981     {
   2982     case ACPI_TPM2_COMMAND_BUFFER_WITH_ARM_SMC:
   2983 
   2984         /* Subtable specific to to ARM_SMC */
   2985 
   2986         Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm211,
   2987             &Subtable);
   2988         if (ACPI_FAILURE (Status))
   2989         {
   2990             return (Status);
   2991         }
   2992 
   2993         ParentTable = DtPeekSubtable ();
   2994         DtInsertSubtable (ParentTable, Subtable);
   2995         break;
   2996 
   2997     case ACPI_TPM2_START_METHOD:
   2998     case ACPI_TPM2_MEMORY_MAPPED:
   2999     case ACPI_TPM2_COMMAND_BUFFER:
   3000     case ACPI_TPM2_COMMAND_BUFFER_WITH_START_METHOD:
   3001         break;
   3002 
   3003     case ACPI_TPM2_RESERVED1:
   3004     case ACPI_TPM2_RESERVED3:
   3005     case ACPI_TPM2_RESERVED4:
   3006     case ACPI_TPM2_RESERVED5:
   3007     case ACPI_TPM2_RESERVED9:
   3008     case ACPI_TPM2_RESERVED10:
   3009 
   3010         AcpiOsPrintf ("\n**** Reserved TPM2 Start Method type 0x%X\n",
   3011             Tpm2Header->StartMethod);
   3012         Status = AE_ERROR;
   3013         break;
   3014 
   3015     case ACPI_TPM2_NOT_ALLOWED:
   3016     default:
   3017 
   3018         AcpiOsPrintf ("\n**** Unknown TPM2 Start Method type 0x%X\n",
   3019             Tpm2Header->StartMethod);
   3020         Status = AE_ERROR;
   3021         break;
   3022     }
   3023 
   3024     return (Status);
   3025 }
   3026 
   3027 
   3028 /******************************************************************************
   3029  *
   3030  * FUNCTION:    DtGetGenericTableInfo
   3031  *
   3032  * PARAMETERS:  Name                - Generic type name
   3033  *
   3034  * RETURN:      Info entry
   3035  *
   3036  * DESCRIPTION: Obtain table info for a generic name entry
   3037  *
   3038  *****************************************************************************/
   3039 
   3040 ACPI_DMTABLE_INFO *
   3041 DtGetGenericTableInfo (
   3042     char                    *Name)
   3043 {
   3044     ACPI_DMTABLE_INFO       *Info;
   3045     UINT32                  i;
   3046 
   3047 
   3048     if (!Name)
   3049     {
   3050         return (NULL);
   3051     }
   3052 
   3053     /* Search info table for name match */
   3054 
   3055     for (i = 0; ; i++)
   3056     {
   3057         Info = AcpiDmTableInfoGeneric[i];
   3058         if (Info->Opcode == ACPI_DMT_EXIT)
   3059         {
   3060             Info = NULL;
   3061             break;
   3062         }
   3063 
   3064         /* Use caseless compare for generic keywords */
   3065 
   3066         if (!AcpiUtStricmp (Name, Info->Name))
   3067         {
   3068             break;
   3069         }
   3070     }
   3071 
   3072     return (Info);
   3073 }
   3074 
   3075 
   3076 /******************************************************************************
   3077  *
   3078  * FUNCTION:    DtCompileUefi
   3079  *
   3080  * PARAMETERS:  List                - Current field list pointer
   3081  *
   3082  * RETURN:      Status
   3083  *
   3084  * DESCRIPTION: Compile UEFI.
   3085  *
   3086  *****************************************************************************/
   3087 
   3088 ACPI_STATUS
   3089 DtCompileUefi (
   3090     void                    **List)
   3091 {
   3092     ACPI_STATUS             Status;
   3093     DT_SUBTABLE             *Subtable;
   3094     DT_SUBTABLE             *ParentTable;
   3095     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   3096     UINT16                  *DataOffset;
   3097 
   3098 
   3099     /* Compile the predefined portion of the UEFI table */
   3100 
   3101     Status = DtCompileTable (PFieldList, AcpiDmTableInfoUefi,
   3102         &Subtable);
   3103     if (ACPI_FAILURE (Status))
   3104     {
   3105         return (Status);
   3106     }
   3107 
   3108     DataOffset = (UINT16 *) (Subtable->Buffer + 16);
   3109     *DataOffset = sizeof (ACPI_TABLE_UEFI);
   3110 
   3111     ParentTable = DtPeekSubtable ();
   3112     DtInsertSubtable (ParentTable, Subtable);
   3113 
   3114     /*
   3115      * Compile the "generic" portion of the UEFI table. This
   3116      * part of the table is not predefined and any of the generic
   3117      * operators may be used.
   3118      */
   3119     DtCompileGeneric ((void **) PFieldList, NULL, NULL);
   3120     return (AE_OK);
   3121 }
   3122 
   3123 
   3124 /******************************************************************************
   3125  *
   3126  * FUNCTION:    DtCompileViot
   3127  *
   3128  * PARAMETERS:  List                - Current field list pointer
   3129  *
   3130  * RETURN:      Status
   3131  *
   3132  * DESCRIPTION: Compile VIOT.
   3133  *
   3134  *****************************************************************************/
   3135 
   3136 ACPI_STATUS
   3137 DtCompileViot (
   3138     void                    **List)
   3139 {
   3140     ACPI_STATUS             Status;
   3141     DT_SUBTABLE             *Subtable;
   3142     DT_SUBTABLE             *ParentTable;
   3143     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   3144     DT_FIELD                *SubtableStart;
   3145     ACPI_TABLE_VIOT         *Viot;
   3146     ACPI_VIOT_HEADER        *ViotHeader;
   3147     ACPI_DMTABLE_INFO       *InfoTable;
   3148     UINT16                  NodeCount;
   3149 
   3150     ParentTable = DtPeekSubtable ();
   3151 
   3152     Status = DtCompileTable (PFieldList, AcpiDmTableInfoViot, &Subtable);
   3153     if (ACPI_FAILURE (Status))
   3154     {
   3155         return (Status);
   3156     }
   3157     DtInsertSubtable (ParentTable, Subtable);
   3158 
   3159     /*
   3160      * Using ACPI_SUB_PTR, We needn't define a separate structure. Care
   3161      * should be taken to avoid accessing ACPI_TABLE_HEADER fields.
   3162      */
   3163     Viot = ACPI_SUB_PTR (ACPI_TABLE_VIOT, Subtable->Buffer,
   3164         sizeof (ACPI_TABLE_HEADER));
   3165 
   3166     Viot->NodeOffset = sizeof (ACPI_TABLE_VIOT);
   3167 
   3168     NodeCount = 0;
   3169     while (*PFieldList) {
   3170         SubtableStart = *PFieldList;
   3171         Status = DtCompileTable (PFieldList, AcpiDmTableInfoViotHeader,
   3172             &Subtable);
   3173         if (ACPI_FAILURE (Status))
   3174         {
   3175             return (Status);
   3176         }
   3177 
   3178         ParentTable = DtPeekSubtable ();
   3179         DtInsertSubtable (ParentTable, Subtable);
   3180         DtPushSubtable (Subtable);
   3181 
   3182         ViotHeader = ACPI_CAST_PTR (ACPI_VIOT_HEADER, Subtable->Buffer);
   3183 
   3184         switch (ViotHeader->Type)
   3185         {
   3186         case ACPI_VIOT_NODE_PCI_RANGE:
   3187 
   3188             InfoTable = AcpiDmTableInfoViot1;
   3189             break;
   3190 
   3191         case ACPI_VIOT_NODE_MMIO:
   3192 
   3193             InfoTable = AcpiDmTableInfoViot2;
   3194             break;
   3195 
   3196         case ACPI_VIOT_NODE_VIRTIO_IOMMU_PCI:
   3197 
   3198             InfoTable = AcpiDmTableInfoViot3;
   3199             break;
   3200 
   3201         case ACPI_VIOT_NODE_VIRTIO_IOMMU_MMIO:
   3202 
   3203             InfoTable = AcpiDmTableInfoViot4;
   3204             break;
   3205 
   3206         default:
   3207 
   3208             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "VIOT");
   3209             return (AE_ERROR);
   3210         }
   3211 
   3212         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   3213         if (ACPI_FAILURE (Status))
   3214         {
   3215             return (Status);
   3216         }
   3217 
   3218         ParentTable = DtPeekSubtable ();
   3219         DtInsertSubtable (ParentTable, Subtable);
   3220         DtPopSubtable ();
   3221         NodeCount++;
   3222     }
   3223 
   3224     Viot->NodeCount = NodeCount;
   3225     return (AE_OK);
   3226 }
   3227 
   3228 
   3229 /******************************************************************************
   3230  *
   3231  * FUNCTION:    DtCompileWdat
   3232  *
   3233  * PARAMETERS:  List                - Current field list pointer
   3234  *
   3235  * RETURN:      Status
   3236  *
   3237  * DESCRIPTION: Compile WDAT.
   3238  *
   3239  *****************************************************************************/
   3240 
   3241 ACPI_STATUS
   3242 DtCompileWdat (
   3243     void                    **List)
   3244 {
   3245     ACPI_STATUS             Status;
   3246 
   3247 
   3248     Status = DtCompileTwoSubtables (List,
   3249         AcpiDmTableInfoWdat, AcpiDmTableInfoWdat0);
   3250     return (Status);
   3251 }
   3252 
   3253 
   3254 /******************************************************************************
   3255  *
   3256  * FUNCTION:    DtCompileWpbt
   3257  *
   3258  * PARAMETERS:  List                - Current field list pointer
   3259  *
   3260  * RETURN:      Status
   3261  *
   3262  * DESCRIPTION: Compile WPBT.
   3263  *
   3264  *****************************************************************************/
   3265 
   3266 ACPI_STATUS
   3267 DtCompileWpbt (
   3268     void                    **List)
   3269 {
   3270     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   3271     DT_SUBTABLE             *Subtable;
   3272     DT_SUBTABLE             *ParentTable;
   3273     ACPI_TABLE_WPBT         *Table;
   3274     ACPI_STATUS             Status;
   3275 
   3276 
   3277     /* Compile the main table */
   3278 
   3279     Status = DtCompileTable (PFieldList, AcpiDmTableInfoWpbt, &Subtable);
   3280     if (ACPI_FAILURE (Status))
   3281     {
   3282         return (Status);
   3283     }
   3284 
   3285     ParentTable = DtPeekSubtable ();
   3286     DtInsertSubtable (ParentTable, Subtable);
   3287     Table = ACPI_CAST_PTR (ACPI_TABLE_WPBT, ParentTable->Buffer);
   3288 
   3289     /*
   3290      * Exit now if there are no arguments specified. This is indicated by:
   3291      * The "Command-line Arguments" field has not been specified (if specified,
   3292      * it will be the last field in the field list -- after the main table).
   3293      * Set the Argument Length in the main table to zero.
   3294      */
   3295     if (!*PFieldList)
   3296     {
   3297         Table->ArgumentsLength = 0;
   3298         return (AE_OK);
   3299     }
   3300 
   3301     /* Compile the argument list subtable */
   3302 
   3303     Status = DtCompileTable (PFieldList, AcpiDmTableInfoWpbt0, &Subtable);
   3304     if (ACPI_FAILURE (Status))
   3305     {
   3306         return (Status);
   3307     }
   3308 
   3309     /* Extract the length of the Arguments buffer, insert into main table */
   3310 
   3311     Table->ArgumentsLength = (UINT16) Subtable->TotalLength;
   3312     DtInsertSubtable (ParentTable, Subtable);
   3313     return (AE_OK);
   3314 }
   3315 
   3316 
   3317 /******************************************************************************
   3318  *
   3319  * FUNCTION:    DtCompileXsdt
   3320  *
   3321  * PARAMETERS:  List                - Current field list pointer
   3322  *
   3323  * RETURN:      Status
   3324  *
   3325  * DESCRIPTION: Compile XSDT.
   3326  *
   3327  *****************************************************************************/
   3328 
   3329 ACPI_STATUS
   3330 DtCompileXsdt (
   3331     void                    **List)
   3332 {
   3333     DT_SUBTABLE             *Subtable;
   3334     DT_SUBTABLE             *ParentTable;
   3335     DT_FIELD                *FieldList = *(DT_FIELD **) List;
   3336     UINT64                  Address;
   3337 
   3338 
   3339     ParentTable = DtPeekSubtable ();
   3340 
   3341     while (FieldList)
   3342     {
   3343         DtCompileInteger ((UINT8 *) &Address, FieldList, 8, DT_NON_ZERO);
   3344 
   3345         DtCreateSubtable ((UINT8 *) &Address, 8, &Subtable);
   3346         DtInsertSubtable (ParentTable, Subtable);
   3347         FieldList = FieldList->Next;
   3348     }
   3349 
   3350     return (AE_OK);
   3351 }
   3352 
   3353 
   3354 /******************************************************************************
   3355  *
   3356  * FUNCTION:    DtCompileGeneric
   3357  *
   3358  * PARAMETERS:  List                - Current field list pointer
   3359  *              Name                - Field name to end generic compiling
   3360  *              Length              - Compiled table length to return
   3361  *
   3362  * RETURN:      Status
   3363  *
   3364  * DESCRIPTION: Compile generic unknown table.
   3365  *
   3366  *****************************************************************************/
   3367 
   3368 ACPI_STATUS
   3369 DtCompileGeneric (
   3370     void                    **List,
   3371     char                    *Name,
   3372     UINT32                  *Length)
   3373 {
   3374     ACPI_STATUS             Status;
   3375     DT_SUBTABLE             *Subtable;
   3376     DT_SUBTABLE             *ParentTable;
   3377     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   3378     ACPI_DMTABLE_INFO       *Info;
   3379 
   3380 
   3381     ParentTable = DtPeekSubtable ();
   3382 
   3383     /*
   3384      * Compile the "generic" portion of the table. This
   3385      * part of the table is not predefined and any of the generic
   3386      * operators may be used.
   3387      */
   3388 
   3389     /* Find any and all labels in the entire generic portion */
   3390 
   3391     DtDetectAllLabels (*PFieldList);
   3392 
   3393     /* Now we can actually compile the parse tree */
   3394 
   3395     if (Length && *Length)
   3396     {
   3397         *Length = 0;
   3398     }
   3399     while (*PFieldList)
   3400     {
   3401         if (Name && !strcmp ((*PFieldList)->Name, Name))
   3402         {
   3403             break;
   3404         }
   3405 
   3406         Info = DtGetGenericTableInfo ((*PFieldList)->Name);
   3407         if (!Info)
   3408         {
   3409             sprintf (AslGbl_MsgBuffer, "Generic data type \"%s\" not found",
   3410                 (*PFieldList)->Name);
   3411             DtNameError (ASL_ERROR, ASL_MSG_INVALID_FIELD_NAME,
   3412                 (*PFieldList), AslGbl_MsgBuffer);
   3413 
   3414             *PFieldList = (*PFieldList)->Next;
   3415             continue;
   3416         }
   3417 
   3418         Status = DtCompileTable (PFieldList, Info,
   3419             &Subtable);
   3420         if (ACPI_SUCCESS (Status))
   3421         {
   3422             DtInsertSubtable (ParentTable, Subtable);
   3423             if (Length)
   3424             {
   3425                 *Length += Subtable->Length;
   3426             }
   3427         }
   3428         else
   3429         {
   3430             *PFieldList = (*PFieldList)->Next;
   3431 
   3432             if (Status == AE_NOT_FOUND)
   3433             {
   3434                 sprintf (AslGbl_MsgBuffer, "Generic data type \"%s\" not found",
   3435                     (*PFieldList)->Name);
   3436                 DtNameError (ASL_ERROR, ASL_MSG_INVALID_FIELD_NAME,
   3437                     (*PFieldList), AslGbl_MsgBuffer);
   3438             }
   3439         }
   3440     }
   3441 
   3442     return (AE_OK);
   3443 }
   3444