Home | History | Annotate | Line # | Download | only in compiler
dttable2.c revision 1.1.1.12
      1 /******************************************************************************
      2  *
      3  * Module Name: dttable2.c - handling for specific ACPI tables
      4  *
      5  *****************************************************************************/
      6 
      7 /*
      8  * Copyright (C) 2000 - 2021, 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_SUBTABLE_HEADER    *MadtHeader;
    150     ACPI_DMTABLE_INFO       *InfoTable;
    151 
    152 
    153     Status = DtCompileTable (PFieldList, AcpiDmTableInfoMadt,
    154         &Subtable);
    155     if (ACPI_FAILURE (Status))
    156     {
    157         return (Status);
    158     }
    159 
    160     ParentTable = DtPeekSubtable ();
    161     DtInsertSubtable (ParentTable, Subtable);
    162 
    163     while (*PFieldList)
    164     {
    165         SubtableStart = *PFieldList;
    166         Status = DtCompileTable (PFieldList, AcpiDmTableInfoMadtHdr,
    167             &Subtable);
    168         if (ACPI_FAILURE (Status))
    169         {
    170             return (Status);
    171         }
    172 
    173         ParentTable = DtPeekSubtable ();
    174         DtInsertSubtable (ParentTable, Subtable);
    175         DtPushSubtable (Subtable);
    176 
    177         MadtHeader = ACPI_CAST_PTR (ACPI_SUBTABLE_HEADER, Subtable->Buffer);
    178 
    179         switch (MadtHeader->Type)
    180         {
    181         case ACPI_MADT_TYPE_LOCAL_APIC:
    182 
    183             InfoTable = AcpiDmTableInfoMadt0;
    184             break;
    185 
    186         case ACPI_MADT_TYPE_IO_APIC:
    187 
    188             InfoTable = AcpiDmTableInfoMadt1;
    189             break;
    190 
    191         case ACPI_MADT_TYPE_INTERRUPT_OVERRIDE:
    192 
    193             InfoTable = AcpiDmTableInfoMadt2;
    194             break;
    195 
    196         case ACPI_MADT_TYPE_NMI_SOURCE:
    197 
    198             InfoTable = AcpiDmTableInfoMadt3;
    199             break;
    200 
    201         case ACPI_MADT_TYPE_LOCAL_APIC_NMI:
    202 
    203             InfoTable = AcpiDmTableInfoMadt4;
    204             break;
    205 
    206         case ACPI_MADT_TYPE_LOCAL_APIC_OVERRIDE:
    207 
    208             InfoTable = AcpiDmTableInfoMadt5;
    209             break;
    210 
    211         case ACPI_MADT_TYPE_IO_SAPIC:
    212 
    213             InfoTable = AcpiDmTableInfoMadt6;
    214             break;
    215 
    216         case ACPI_MADT_TYPE_LOCAL_SAPIC:
    217 
    218             InfoTable = AcpiDmTableInfoMadt7;
    219             break;
    220 
    221         case ACPI_MADT_TYPE_INTERRUPT_SOURCE:
    222 
    223             InfoTable = AcpiDmTableInfoMadt8;
    224             break;
    225 
    226         case ACPI_MADT_TYPE_LOCAL_X2APIC:
    227 
    228             InfoTable = AcpiDmTableInfoMadt9;
    229             break;
    230 
    231         case ACPI_MADT_TYPE_LOCAL_X2APIC_NMI:
    232 
    233             InfoTable = AcpiDmTableInfoMadt10;
    234             break;
    235 
    236         case ACPI_MADT_TYPE_GENERIC_INTERRUPT:
    237 
    238             InfoTable = AcpiDmTableInfoMadt11;
    239             break;
    240 
    241         case ACPI_MADT_TYPE_GENERIC_DISTRIBUTOR:
    242 
    243             InfoTable = AcpiDmTableInfoMadt12;
    244             break;
    245 
    246         case ACPI_MADT_TYPE_GENERIC_MSI_FRAME:
    247 
    248             InfoTable = AcpiDmTableInfoMadt13;
    249             break;
    250 
    251         case ACPI_MADT_TYPE_GENERIC_REDISTRIBUTOR:
    252 
    253             InfoTable = AcpiDmTableInfoMadt14;
    254             break;
    255 
    256         case ACPI_MADT_TYPE_GENERIC_TRANSLATOR:
    257 
    258             InfoTable = AcpiDmTableInfoMadt15;
    259             break;
    260 
    261         case ACPI_MADT_TYPE_MULTIPROC_WAKEUP:
    262 
    263             InfoTable = AcpiDmTableInfoMadt16;
    264             break;
    265 
    266         default:
    267 
    268             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "MADT");
    269             return (AE_ERROR);
    270         }
    271 
    272         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
    273         if (ACPI_FAILURE (Status))
    274         {
    275             return (Status);
    276         }
    277 
    278         ParentTable = DtPeekSubtable ();
    279         DtInsertSubtable (ParentTable, Subtable);
    280         DtPopSubtable ();
    281     }
    282 
    283     return (AE_OK);
    284 }
    285 
    286 
    287 /******************************************************************************
    288  *
    289  * FUNCTION:    DtCompileMcfg
    290  *
    291  * PARAMETERS:  List                - Current field list pointer
    292  *
    293  * RETURN:      Status
    294  *
    295  * DESCRIPTION: Compile MCFG.
    296  *
    297  *****************************************************************************/
    298 
    299 ACPI_STATUS
    300 DtCompileMcfg (
    301     void                    **List)
    302 {
    303     ACPI_STATUS             Status;
    304 
    305 
    306     Status = DtCompileTwoSubtables (List,
    307         AcpiDmTableInfoMcfg, AcpiDmTableInfoMcfg0);
    308     return (Status);
    309 }
    310 
    311 
    312 /******************************************************************************
    313  *
    314  * FUNCTION:    DtCompileMpst
    315  *
    316  * PARAMETERS:  List                - Current field list pointer
    317  *
    318  * RETURN:      Status
    319  *
    320  * DESCRIPTION: Compile MPST.
    321  *
    322  *****************************************************************************/
    323 
    324 ACPI_STATUS
    325 DtCompileMpst (
    326     void                    **List)
    327 {
    328     ACPI_STATUS             Status;
    329     DT_SUBTABLE             *Subtable;
    330     DT_SUBTABLE             *ParentTable;
    331     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    332     ACPI_MPST_CHANNEL       *MpstChannelInfo;
    333     ACPI_MPST_POWER_NODE    *MpstPowerNode;
    334     ACPI_MPST_DATA_HDR      *MpstDataHeader;
    335     UINT16                  SubtableCount;
    336     UINT32                  PowerStateCount;
    337     UINT32                  ComponentCount;
    338 
    339 
    340     /* Main table */
    341 
    342     Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst, &Subtable);
    343     if (ACPI_FAILURE (Status))
    344     {
    345         return (Status);
    346     }
    347 
    348     ParentTable = DtPeekSubtable ();
    349     DtInsertSubtable (ParentTable, Subtable);
    350     DtPushSubtable (Subtable);
    351 
    352     MpstChannelInfo = ACPI_CAST_PTR (ACPI_MPST_CHANNEL, Subtable->Buffer);
    353     SubtableCount = MpstChannelInfo->PowerNodeCount;
    354 
    355     while (*PFieldList && SubtableCount)
    356     {
    357         /* Subtable: Memory Power Node(s) */
    358 
    359         Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst0,
    360             &Subtable);
    361         if (ACPI_FAILURE (Status))
    362         {
    363             return (Status);
    364         }
    365 
    366         ParentTable = DtPeekSubtable ();
    367         DtInsertSubtable (ParentTable, Subtable);
    368         DtPushSubtable (Subtable);
    369 
    370         MpstPowerNode = ACPI_CAST_PTR (ACPI_MPST_POWER_NODE, Subtable->Buffer);
    371         PowerStateCount = MpstPowerNode->NumPowerStates;
    372         ComponentCount = MpstPowerNode->NumPhysicalComponents;
    373 
    374         ParentTable = DtPeekSubtable ();
    375 
    376         /* Sub-subtables - Memory Power State Structure(s) */
    377 
    378         while (*PFieldList && PowerStateCount)
    379         {
    380             Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst0A,
    381                 &Subtable);
    382             if (ACPI_FAILURE (Status))
    383             {
    384                 return (Status);
    385             }
    386 
    387             DtInsertSubtable (ParentTable, Subtable);
    388             PowerStateCount--;
    389         }
    390 
    391         /* Sub-subtables - Physical Component ID Structure(s) */
    392 
    393         while (*PFieldList && ComponentCount)
    394         {
    395             Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst0B,
    396                 &Subtable);
    397             if (ACPI_FAILURE (Status))
    398             {
    399                 return (Status);
    400             }
    401 
    402             DtInsertSubtable (ParentTable, Subtable);
    403             ComponentCount--;
    404         }
    405 
    406         SubtableCount--;
    407         DtPopSubtable ();
    408     }
    409 
    410     /* Subtable: Count of Memory Power State Characteristic structures */
    411 
    412     DtPopSubtable ();
    413 
    414     Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst1, &Subtable);
    415     if (ACPI_FAILURE (Status))
    416     {
    417         return (Status);
    418     }
    419 
    420     ParentTable = DtPeekSubtable ();
    421     DtInsertSubtable (ParentTable, Subtable);
    422     DtPushSubtable (Subtable);
    423 
    424     MpstDataHeader = ACPI_CAST_PTR (ACPI_MPST_DATA_HDR, Subtable->Buffer);
    425     SubtableCount = MpstDataHeader->CharacteristicsCount;
    426 
    427     ParentTable = DtPeekSubtable ();
    428 
    429     /* Subtable: Memory Power State Characteristics structure(s) */
    430 
    431     while (*PFieldList && SubtableCount)
    432     {
    433         Status = DtCompileTable (PFieldList, AcpiDmTableInfoMpst2,
    434             &Subtable);
    435         if (ACPI_FAILURE (Status))
    436         {
    437             return (Status);
    438         }
    439 
    440         DtInsertSubtable (ParentTable, Subtable);
    441         SubtableCount--;
    442     }
    443 
    444     DtPopSubtable ();
    445     return (AE_OK);
    446 }
    447 
    448 
    449 /******************************************************************************
    450  *
    451  * FUNCTION:    DtCompileMsct
    452  *
    453  * PARAMETERS:  List                - Current field list pointer
    454  *
    455  * RETURN:      Status
    456  *
    457  * DESCRIPTION: Compile MSCT.
    458  *
    459  *****************************************************************************/
    460 
    461 ACPI_STATUS
    462 DtCompileMsct (
    463     void                    **List)
    464 {
    465     ACPI_STATUS             Status;
    466 
    467 
    468     Status = DtCompileTwoSubtables (List,
    469         AcpiDmTableInfoMsct, AcpiDmTableInfoMsct0);
    470     return (Status);
    471 }
    472 
    473 
    474 /******************************************************************************
    475  *
    476  * FUNCTION:    DtCompileNfit
    477  *
    478  * PARAMETERS:  List                - Current field list pointer
    479  *
    480  * RETURN:      Status
    481  *
    482  * DESCRIPTION: Compile NFIT.
    483  *
    484  *****************************************************************************/
    485 
    486 ACPI_STATUS
    487 DtCompileNfit (
    488     void                    **List)
    489 {
    490     ACPI_STATUS             Status;
    491     DT_SUBTABLE             *Subtable;
    492     DT_SUBTABLE             *ParentTable;
    493     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    494     DT_FIELD                *SubtableStart;
    495     ACPI_NFIT_HEADER        *NfitHeader;
    496     ACPI_DMTABLE_INFO       *InfoTable;
    497     UINT32                  Count;
    498     ACPI_NFIT_INTERLEAVE    *Interleave = NULL;
    499     ACPI_NFIT_FLUSH_ADDRESS *Hint = NULL;
    500 
    501 
    502     /* Main table */
    503 
    504     Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfit,
    505         &Subtable);
    506     if (ACPI_FAILURE (Status))
    507     {
    508         return (Status);
    509     }
    510 
    511     ParentTable = DtPeekSubtable ();
    512     DtInsertSubtable (ParentTable, Subtable);
    513     DtPushSubtable (Subtable);
    514 
    515     /* Subtables */
    516 
    517     while (*PFieldList)
    518     {
    519         SubtableStart = *PFieldList;
    520         Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfitHdr,
    521             &Subtable);
    522         if (ACPI_FAILURE (Status))
    523         {
    524             return (Status);
    525         }
    526 
    527         ParentTable = DtPeekSubtable ();
    528         DtInsertSubtable (ParentTable, Subtable);
    529         DtPushSubtable (Subtable);
    530 
    531         NfitHeader = ACPI_CAST_PTR (ACPI_NFIT_HEADER, Subtable->Buffer);
    532 
    533         switch (NfitHeader->Type)
    534         {
    535         case ACPI_NFIT_TYPE_SYSTEM_ADDRESS:
    536 
    537             InfoTable = AcpiDmTableInfoNfit0;
    538             break;
    539 
    540         case ACPI_NFIT_TYPE_MEMORY_MAP:
    541 
    542             InfoTable = AcpiDmTableInfoNfit1;
    543             break;
    544 
    545         case ACPI_NFIT_TYPE_INTERLEAVE:
    546 
    547             Interleave = ACPI_CAST_PTR (ACPI_NFIT_INTERLEAVE, Subtable->Buffer);
    548             InfoTable = AcpiDmTableInfoNfit2;
    549             break;
    550 
    551         case ACPI_NFIT_TYPE_SMBIOS:
    552 
    553             InfoTable = AcpiDmTableInfoNfit3;
    554             break;
    555 
    556         case ACPI_NFIT_TYPE_CONTROL_REGION:
    557 
    558             InfoTable = AcpiDmTableInfoNfit4;
    559             break;
    560 
    561         case ACPI_NFIT_TYPE_DATA_REGION:
    562 
    563             InfoTable = AcpiDmTableInfoNfit5;
    564             break;
    565 
    566         case ACPI_NFIT_TYPE_FLUSH_ADDRESS:
    567 
    568             Hint = ACPI_CAST_PTR (ACPI_NFIT_FLUSH_ADDRESS, Subtable->Buffer);
    569             InfoTable = AcpiDmTableInfoNfit6;
    570             break;
    571 
    572         case ACPI_NFIT_TYPE_CAPABILITIES:
    573 
    574             InfoTable = AcpiDmTableInfoNfit7;
    575             break;
    576 
    577         default:
    578 
    579             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "NFIT");
    580             return (AE_ERROR);
    581         }
    582 
    583         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
    584         if (ACPI_FAILURE (Status))
    585         {
    586             return (Status);
    587         }
    588 
    589         ParentTable = DtPeekSubtable ();
    590         DtInsertSubtable (ParentTable, Subtable);
    591         DtPopSubtable ();
    592 
    593         switch (NfitHeader->Type)
    594         {
    595         case ACPI_NFIT_TYPE_INTERLEAVE:
    596 
    597             Count = 0;
    598             DtPushSubtable (Subtable);
    599             while (*PFieldList)
    600             {
    601                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfit2a,
    602                     &Subtable);
    603                 if (ACPI_FAILURE (Status))
    604                 {
    605                     return (Status);
    606                 }
    607 
    608                 if (!Subtable)
    609                 {
    610                     DtPopSubtable ();
    611                     break;
    612                 }
    613 
    614                 ParentTable = DtPeekSubtable ();
    615                 DtInsertSubtable (ParentTable, Subtable);
    616                 Count++;
    617             }
    618 
    619             Interleave->LineCount = Count;
    620             break;
    621 
    622         case ACPI_NFIT_TYPE_SMBIOS:
    623 
    624             if (*PFieldList)
    625             {
    626                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfit3a,
    627                     &Subtable);
    628                 if (ACPI_FAILURE (Status))
    629                 {
    630                     return (Status);
    631                 }
    632 
    633                 if (Subtable)
    634                 {
    635                     DtInsertSubtable (ParentTable, Subtable);
    636                 }
    637             }
    638             break;
    639 
    640         case ACPI_NFIT_TYPE_FLUSH_ADDRESS:
    641 
    642             Count = 0;
    643             DtPushSubtable (Subtable);
    644             while (*PFieldList)
    645             {
    646                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoNfit6a,
    647                     &Subtable);
    648                 if (ACPI_FAILURE (Status))
    649                 {
    650                     return (Status);
    651                 }
    652 
    653                 if (!Subtable)
    654                 {
    655                     DtPopSubtable ();
    656                     break;
    657                 }
    658 
    659                 ParentTable = DtPeekSubtable ();
    660                 DtInsertSubtable (ParentTable, Subtable);
    661                 Count++;
    662             }
    663 
    664             Hint->HintCount = (UINT16) Count;
    665             break;
    666 
    667         default:
    668             break;
    669         }
    670     }
    671 
    672     return (AE_OK);
    673 }
    674 
    675 
    676 /******************************************************************************
    677  *
    678  * FUNCTION:    DtCompilePcct
    679  *
    680  * PARAMETERS:  List                - Current field list pointer
    681  *
    682  * RETURN:      Status
    683  *
    684  * DESCRIPTION: Compile PCCT.
    685  *
    686  *****************************************************************************/
    687 
    688 ACPI_STATUS
    689 DtCompilePcct (
    690     void                    **List)
    691 {
    692     ACPI_STATUS             Status;
    693     DT_SUBTABLE             *Subtable;
    694     DT_SUBTABLE             *ParentTable;
    695     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    696     DT_FIELD                *SubtableStart;
    697     ACPI_SUBTABLE_HEADER    *PcctHeader;
    698     ACPI_DMTABLE_INFO       *InfoTable;
    699 
    700 
    701     /* Main table */
    702 
    703     Status = DtCompileTable (PFieldList, AcpiDmTableInfoPcct,
    704         &Subtable);
    705     if (ACPI_FAILURE (Status))
    706     {
    707         return (Status);
    708     }
    709 
    710     ParentTable = DtPeekSubtable ();
    711     DtInsertSubtable (ParentTable, Subtable);
    712 
    713     /* Subtables */
    714 
    715     while (*PFieldList)
    716     {
    717         SubtableStart = *PFieldList;
    718         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPcctHdr,
    719             &Subtable);
    720         if (ACPI_FAILURE (Status))
    721         {
    722             return (Status);
    723         }
    724 
    725         ParentTable = DtPeekSubtable ();
    726         DtInsertSubtable (ParentTable, Subtable);
    727         DtPushSubtable (Subtable);
    728 
    729         PcctHeader = ACPI_CAST_PTR (ACPI_SUBTABLE_HEADER, Subtable->Buffer);
    730 
    731         switch (PcctHeader->Type)
    732         {
    733         case ACPI_PCCT_TYPE_GENERIC_SUBSPACE:
    734 
    735             InfoTable = AcpiDmTableInfoPcct0;
    736             break;
    737 
    738         case ACPI_PCCT_TYPE_HW_REDUCED_SUBSPACE:
    739 
    740             InfoTable = AcpiDmTableInfoPcct1;
    741             break;
    742 
    743         case ACPI_PCCT_TYPE_HW_REDUCED_SUBSPACE_TYPE2:
    744 
    745             InfoTable = AcpiDmTableInfoPcct2;
    746             break;
    747 
    748         case ACPI_PCCT_TYPE_EXT_PCC_MASTER_SUBSPACE:
    749 
    750             InfoTable = AcpiDmTableInfoPcct3;
    751             break;
    752 
    753         case ACPI_PCCT_TYPE_EXT_PCC_SLAVE_SUBSPACE:
    754 
    755             InfoTable = AcpiDmTableInfoPcct4;
    756             break;
    757 
    758         case ACPI_PCCT_TYPE_HW_REG_COMM_SUBSPACE:
    759 
    760             InfoTable = AcpiDmTableInfoPcct5;
    761             break;
    762 
    763         default:
    764 
    765             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "PCCT");
    766             return (AE_ERROR);
    767         }
    768 
    769         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
    770         if (ACPI_FAILURE (Status))
    771         {
    772             return (Status);
    773         }
    774 
    775         ParentTable = DtPeekSubtable ();
    776         DtInsertSubtable (ParentTable, Subtable);
    777         DtPopSubtable ();
    778     }
    779 
    780     return (AE_OK);
    781 }
    782 
    783 
    784 /******************************************************************************
    785  *
    786  * FUNCTION:    DtCompilePdtt
    787  *
    788  * PARAMETERS:  List                - Current field list pointer
    789  *
    790  * RETURN:      Status
    791  *
    792  * DESCRIPTION: Compile PDTT.
    793  *
    794  *****************************************************************************/
    795 
    796 ACPI_STATUS
    797 DtCompilePdtt (
    798     void                    **List)
    799 {
    800     ACPI_STATUS             Status;
    801     DT_SUBTABLE             *Subtable;
    802     DT_SUBTABLE             *ParentTable;
    803     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    804     ACPI_TABLE_PDTT         *PdttHeader;
    805     UINT32                  Count = 0;
    806 
    807 
    808     /* Main table */
    809 
    810     Status = DtCompileTable (PFieldList, AcpiDmTableInfoPdtt, &Subtable);
    811     if (ACPI_FAILURE (Status))
    812     {
    813         return (Status);
    814     }
    815 
    816     ParentTable = DtPeekSubtable ();
    817     DtInsertSubtable (ParentTable, Subtable);
    818 
    819     PdttHeader = ACPI_CAST_PTR (ACPI_TABLE_PDTT, ParentTable->Buffer);
    820     PdttHeader->ArrayOffset = sizeof (ACPI_TABLE_PDTT);
    821 
    822     /* There is only one type of subtable at this time, no need to decode */
    823 
    824     while (*PFieldList)
    825     {
    826         /* List of subchannel IDs, each 2 bytes */
    827 
    828         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPdtt0,
    829             &Subtable);
    830         if (ACPI_FAILURE (Status))
    831         {
    832             return (Status);
    833         }
    834 
    835         DtInsertSubtable (ParentTable, Subtable);
    836         Count++;
    837     }
    838 
    839     PdttHeader->TriggerCount = (UINT8) Count;
    840     return (AE_OK);
    841 }
    842 
    843 
    844 /******************************************************************************
    845  *
    846  * FUNCTION:    DtCompilePhat
    847  *
    848  * PARAMETERS:  List                - Current field list pointer
    849  *
    850  * RETURN:      Status
    851  *
    852  * DESCRIPTION: Compile Phat.
    853  *
    854  *****************************************************************************/
    855 
    856 ACPI_STATUS
    857 DtCompilePhat (
    858     void                    **List)
    859 {
    860     ACPI_STATUS             Status = AE_OK;
    861     DT_SUBTABLE             *Subtable;
    862     DT_SUBTABLE             *ParentTable;
    863     DT_FIELD                **PFieldList = (DT_FIELD **) List;
    864     ACPI_PHAT_HEADER        *PhatHeader;
    865     ACPI_DMTABLE_INFO       *Info;
    866     ACPI_PHAT_VERSION_DATA  *VersionData;
    867     UINT32                  RecordCount;
    868 
    869 
    870     /* The table consist of subtables */
    871 
    872     while (*PFieldList)
    873     {
    874         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPhatHdr, &Subtable);
    875         if (ACPI_FAILURE (Status))
    876         {
    877             return (Status);
    878         }
    879 
    880         ParentTable = DtPeekSubtable ();
    881         DtInsertSubtable (ParentTable, Subtable);
    882         DtPushSubtable (Subtable);
    883 
    884         PhatHeader = ACPI_CAST_PTR (ACPI_PHAT_HEADER, Subtable->Buffer);
    885 
    886         switch (PhatHeader->Type)
    887         {
    888         case ACPI_PHAT_TYPE_FW_VERSION_DATA:
    889 
    890             Info = AcpiDmTableInfoPhat0;
    891             PhatHeader->Length = sizeof (ACPI_PHAT_VERSION_DATA);
    892             break;
    893 
    894         case ACPI_PHAT_TYPE_FW_HEALTH_DATA:
    895 
    896             Info = AcpiDmTableInfoPhat1;
    897             PhatHeader->Length = sizeof (ACPI_PHAT_HEALTH_DATA);
    898             break;
    899 
    900         default:
    901 
    902             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, *PFieldList, "PHAT");
    903             return (AE_ERROR);
    904 
    905             break;
    906         }
    907 
    908         Status = DtCompileTable (PFieldList, Info, &Subtable);
    909         if (ACPI_FAILURE (Status))
    910         {
    911             return (Status);
    912         }
    913 
    914         ParentTable = DtPeekSubtable ();
    915         DtInsertSubtable (ParentTable, Subtable);
    916 
    917         switch (PhatHeader->Type)
    918         {
    919         case ACPI_PHAT_TYPE_FW_VERSION_DATA:
    920 
    921             VersionData = ACPI_CAST_PTR (ACPI_PHAT_VERSION_DATA,
    922                 (Subtable->Buffer - sizeof (ACPI_PHAT_HEADER)));
    923             RecordCount = VersionData->ElementCount;
    924 
    925             while (RecordCount)
    926             {
    927                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoPhat0a,
    928                     &Subtable);
    929                 if (ACPI_FAILURE (Status))
    930                 {
    931                     return (Status);
    932                 }
    933                 ParentTable = DtPeekSubtable ();
    934                 DtInsertSubtable (ParentTable, Subtable);
    935 
    936                 RecordCount--;
    937                 PhatHeader->Length += sizeof (ACPI_PHAT_VERSION_ELEMENT);
    938             }
    939             break;
    940 
    941         case ACPI_PHAT_TYPE_FW_HEALTH_DATA:
    942 
    943             /* Compile device path */
    944 
    945             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPhat1a, &Subtable);
    946             if (ACPI_FAILURE (Status))
    947             {
    948                 return (Status);
    949             }
    950             ParentTable = DtPeekSubtable ();
    951             DtInsertSubtable (ParentTable, Subtable);
    952 
    953             PhatHeader->Length += (UINT16) Subtable->Length;
    954 
    955             /* Compile vendor specific data */
    956 
    957             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPhat1b, &Subtable);
    958             if (ACPI_FAILURE (Status))
    959             {
    960                 return (Status);
    961             }
    962             ParentTable = DtPeekSubtable ();
    963             DtInsertSubtable (ParentTable, Subtable);
    964 
    965             PhatHeader->Length += (UINT16) Subtable->Length;
    966 
    967             break;
    968 
    969         default:
    970 
    971             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, *PFieldList, "PHAT");
    972             return (AE_ERROR);
    973         }
    974     }
    975 
    976     return (Status);
    977 }
    978 
    979 
    980 /******************************************************************************
    981  *
    982  * FUNCTION:    DtCompilePmtt
    983  *
    984  * PARAMETERS:  List                - Current field list pointer
    985  *
    986  * RETURN:      Status
    987  *
    988  * DESCRIPTION: Compile PMTT.
    989  *
    990  *****************************************************************************/
    991 
    992 ACPI_STATUS
    993 DtCompilePmtt (
    994     void                    **List)
    995 {
    996     ACPI_STATUS             Status;
    997     DT_SUBTABLE             *Subtable;
    998     DT_SUBTABLE             *ParentTable;
    999     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1000     DT_FIELD                *SubtableStart;
   1001     UINT16                  Type;
   1002 
   1003 
   1004     /* Main table */
   1005 
   1006     Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmtt, &Subtable);
   1007     if (ACPI_FAILURE (Status))
   1008     {
   1009         return (Status);
   1010     }
   1011 
   1012     ParentTable = DtPeekSubtable ();
   1013     DtInsertSubtable (ParentTable, Subtable);
   1014     DtPushSubtable (Subtable);
   1015 
   1016     /* Subtables */
   1017 
   1018     while (*PFieldList)
   1019     {
   1020         SubtableStart = *PFieldList;
   1021         DtCompileInteger ((UINT8 *) &Type, *PFieldList, 2, 0);
   1022 
   1023         switch (Type)
   1024         {
   1025         case ACPI_PMTT_TYPE_SOCKET:
   1026 
   1027             /* Subtable: Socket Structure */
   1028 
   1029             DbgPrint (ASL_DEBUG_OUTPUT, "Compile PMTT_TYPE_SOCKET (0)\n");
   1030 
   1031             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmtt0,
   1032                 &Subtable);
   1033             if (ACPI_FAILURE (Status))
   1034             {
   1035                 return (Status);
   1036             }
   1037 
   1038             break;
   1039 
   1040         case ACPI_PMTT_TYPE_CONTROLLER:
   1041 
   1042             /* Subtable: Memory Controller Structure */
   1043 
   1044             DbgPrint (ASL_DEBUG_OUTPUT, "Compile PMTT_TYPE_CONTROLLER (1)\n");
   1045 
   1046             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmtt1,
   1047                 &Subtable);
   1048             if (ACPI_FAILURE (Status))
   1049             {
   1050                 return (Status);
   1051             }
   1052 
   1053             break;
   1054 
   1055         case ACPI_PMTT_TYPE_DIMM:
   1056 
   1057             /* Subtable: Physical Component (DIMM) Structure */
   1058 
   1059             DbgPrint (ASL_DEBUG_OUTPUT, "Compile PMTT_TYPE_DIMM (2)\n");
   1060             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmtt2,
   1061                 &Subtable);
   1062             if (ACPI_FAILURE (Status))
   1063             {
   1064                 return (Status);
   1065             }
   1066 
   1067             break;
   1068 
   1069         case ACPI_PMTT_TYPE_VENDOR:
   1070 
   1071             /* Subtable: Vendor-specific Structure */
   1072 
   1073             DbgPrint (ASL_DEBUG_OUTPUT, "Compile PMTT_TYPE_VENDOR(FF)\n");
   1074             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPmttVendor,
   1075                 &Subtable);
   1076             if (ACPI_FAILURE (Status))
   1077             {
   1078                 return (Status);
   1079             }
   1080 
   1081             break;
   1082 
   1083         default:
   1084 
   1085             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "PMTT");
   1086             return (AE_ERROR);
   1087         }
   1088 
   1089         DtInsertSubtable (ParentTable, Subtable);
   1090     }
   1091 
   1092     return (Status);
   1093 }
   1094 
   1095 
   1096 /******************************************************************************
   1097  *
   1098  * FUNCTION:    DtCompilePptt
   1099  *
   1100  * PARAMETERS:  List                - Current field list pointer
   1101  *
   1102  * RETURN:      Status
   1103  *
   1104  * DESCRIPTION: Compile PPTT.
   1105  *
   1106  *****************************************************************************/
   1107 
   1108 ACPI_STATUS
   1109 DtCompilePptt (
   1110     void                    **List)
   1111 {
   1112     ACPI_STATUS             Status;
   1113     ACPI_SUBTABLE_HEADER    *PpttHeader;
   1114     ACPI_PPTT_PROCESSOR     *PpttProcessor = NULL;
   1115     DT_SUBTABLE             *Subtable;
   1116     DT_SUBTABLE             *ParentTable;
   1117     ACPI_DMTABLE_INFO       *InfoTable;
   1118     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1119     DT_FIELD                *SubtableStart;
   1120     ACPI_TABLE_HEADER       *PpttAcpiHeader;
   1121 
   1122 
   1123     ParentTable = DtPeekSubtable ();
   1124     while (*PFieldList)
   1125     {
   1126         SubtableStart = *PFieldList;
   1127 
   1128         /* Compile PPTT subtable header */
   1129 
   1130         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPpttHdr,
   1131             &Subtable);
   1132         if (ACPI_FAILURE (Status))
   1133         {
   1134             return (Status);
   1135         }
   1136         DtInsertSubtable (ParentTable, Subtable);
   1137         PpttHeader = ACPI_CAST_PTR (ACPI_SUBTABLE_HEADER, Subtable->Buffer);
   1138         PpttHeader->Length = (UINT8)(Subtable->Length);
   1139 
   1140         switch (PpttHeader->Type)
   1141         {
   1142         case ACPI_PPTT_TYPE_PROCESSOR:
   1143 
   1144             InfoTable = AcpiDmTableInfoPptt0;
   1145             break;
   1146 
   1147         case ACPI_PPTT_TYPE_CACHE:
   1148 
   1149             InfoTable = AcpiDmTableInfoPptt1;
   1150             break;
   1151 
   1152         case ACPI_PPTT_TYPE_ID:
   1153 
   1154             InfoTable = AcpiDmTableInfoPptt2;
   1155             break;
   1156 
   1157         default:
   1158 
   1159             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "PPTT");
   1160             return (AE_ERROR);
   1161         }
   1162 
   1163         /* Compile PPTT subtable body */
   1164 
   1165         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   1166         if (ACPI_FAILURE (Status))
   1167         {
   1168             return (Status);
   1169         }
   1170         DtInsertSubtable (ParentTable, Subtable);
   1171         PpttHeader->Length += (UINT8)(Subtable->Length);
   1172 
   1173         /* Compile PPTT subtable additionals */
   1174 
   1175         switch (PpttHeader->Type)
   1176         {
   1177         case ACPI_PPTT_TYPE_PROCESSOR:
   1178 
   1179             PpttProcessor = ACPI_SUB_PTR (ACPI_PPTT_PROCESSOR,
   1180                 Subtable->Buffer, sizeof (ACPI_SUBTABLE_HEADER));
   1181             if (PpttProcessor)
   1182             {
   1183                 /* Compile initiator proximity domain list */
   1184 
   1185                 PpttProcessor->NumberOfPrivResources = 0;
   1186                 while (*PFieldList)
   1187                 {
   1188                     Status = DtCompileTable (PFieldList,
   1189                         AcpiDmTableInfoPptt0a, &Subtable);
   1190                     if (ACPI_FAILURE (Status))
   1191                     {
   1192                         return (Status);
   1193                     }
   1194                     if (!Subtable)
   1195                     {
   1196                         break;
   1197                     }
   1198 
   1199                     DtInsertSubtable (ParentTable, Subtable);
   1200                     PpttHeader->Length += (UINT8)(Subtable->Length);
   1201                     PpttProcessor->NumberOfPrivResources++;
   1202                 }
   1203             }
   1204             break;
   1205 
   1206         case ACPI_PPTT_TYPE_CACHE:
   1207 
   1208             PpttAcpiHeader = ACPI_CAST_PTR (ACPI_TABLE_HEADER,
   1209                 AslGbl_RootTable->Buffer);
   1210             if (PpttAcpiHeader->Revision < 3)
   1211             {
   1212                 break;
   1213             }
   1214             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPptt1a,
   1215                 &Subtable);
   1216             DtInsertSubtable (ParentTable, Subtable);
   1217             PpttHeader->Length += (UINT8)(Subtable->Length);
   1218             break;
   1219 
   1220         default:
   1221 
   1222             break;
   1223         }
   1224     }
   1225 
   1226     return (AE_OK);
   1227 }
   1228 
   1229 
   1230 /******************************************************************************
   1231  *
   1232  * FUNCTION:    DtCompilePrmt
   1233  *
   1234  * PARAMETERS:  List                - Current field list pointer
   1235  *
   1236  * RETURN:      Status
   1237  *
   1238  * DESCRIPTION: Compile PRMT.
   1239  *
   1240  *****************************************************************************/
   1241 
   1242 ACPI_STATUS
   1243 DtCompilePrmt (
   1244     void                    **List)
   1245 {
   1246     ACPI_STATUS             Status;
   1247     ACPI_TABLE_PRMT_HEADER  *PrmtHeader;
   1248     ACPI_PRMT_MODULE_INFO   *PrmtModuleInfo;
   1249     DT_SUBTABLE             *Subtable;
   1250     DT_SUBTABLE             *ParentTable;
   1251     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1252     UINT32                  i, j;
   1253 
   1254     ParentTable = DtPeekSubtable ();
   1255 
   1256     /* Compile PRMT subtable header */
   1257 
   1258     Status = DtCompileTable (PFieldList, AcpiDmTableInfoPrmtHdr,
   1259         &Subtable);
   1260     if (ACPI_FAILURE (Status))
   1261     {
   1262         return (Status);
   1263     }
   1264     DtInsertSubtable (ParentTable, Subtable);
   1265     PrmtHeader = ACPI_CAST_PTR (ACPI_TABLE_PRMT_HEADER, Subtable->Buffer);
   1266 
   1267     for (i = 0; i < PrmtHeader->ModuleInfoCount; i++)
   1268     {
   1269         Status = DtCompileTable (PFieldList, AcpiDmTableInfoPrmtModule,
   1270             &Subtable);
   1271         if (ACPI_FAILURE (Status))
   1272         {
   1273             return (Status);
   1274         }
   1275         DtInsertSubtable (ParentTable, Subtable);
   1276         PrmtModuleInfo = ACPI_CAST_PTR (ACPI_PRMT_MODULE_INFO, Subtable->Buffer);
   1277 
   1278         for (j = 0; j < PrmtModuleInfo->HandlerInfoCount; j++)
   1279         {
   1280             Status = DtCompileTable (PFieldList, AcpiDmTableInfoPrmtHandler,
   1281                 &Subtable);
   1282             if (ACPI_FAILURE (Status))
   1283             {
   1284                 return (Status);
   1285             }
   1286             DtInsertSubtable (ParentTable, Subtable);
   1287         }
   1288     }
   1289 
   1290     return (AE_OK);
   1291 }
   1292 
   1293 
   1294 /******************************************************************************
   1295  *
   1296  * FUNCTION:    DtCompileRgrt
   1297  *
   1298  * PARAMETERS:  List                - Current field list pointer
   1299  *
   1300  * RETURN:      Status
   1301  *
   1302  * DESCRIPTION: Compile RGRT.
   1303  *
   1304  *****************************************************************************/
   1305 
   1306 ACPI_STATUS
   1307 DtCompileRgrt (
   1308     void                    **List)
   1309 {
   1310     ACPI_STATUS             Status;
   1311     DT_SUBTABLE             *Subtable;
   1312     DT_SUBTABLE             *ParentTable;
   1313     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1314 
   1315 
   1316     /* Compile the main table */
   1317 
   1318     Status = DtCompileTable (PFieldList, AcpiDmTableInfoRgrt,
   1319         &Subtable);
   1320     if (ACPI_FAILURE (Status))
   1321     {
   1322         return (Status);
   1323     }
   1324 
   1325     ParentTable = DtPeekSubtable ();
   1326     DtInsertSubtable (ParentTable, Subtable);
   1327 
   1328     /* Compile the "Subtable" -- actually just the binary (PNG) image */
   1329 
   1330     Status = DtCompileTable (PFieldList, AcpiDmTableInfoRgrt0,
   1331         &Subtable);
   1332     if (ACPI_FAILURE (Status))
   1333     {
   1334         return (Status);
   1335     }
   1336 
   1337     DtInsertSubtable (ParentTable, Subtable);
   1338     return (AE_OK);
   1339 }
   1340 
   1341 
   1342 /******************************************************************************
   1343  *
   1344  * FUNCTION:    DtCompileRsdt
   1345  *
   1346  * PARAMETERS:  List                - Current field list pointer
   1347  *
   1348  * RETURN:      Status
   1349  *
   1350  * DESCRIPTION: Compile RSDT.
   1351  *
   1352  *****************************************************************************/
   1353 
   1354 ACPI_STATUS
   1355 DtCompileRsdt (
   1356     void                    **List)
   1357 {
   1358     DT_SUBTABLE             *Subtable;
   1359     DT_SUBTABLE             *ParentTable;
   1360     DT_FIELD                *FieldList = *(DT_FIELD **) List;
   1361     UINT32                  Address;
   1362 
   1363 
   1364     ParentTable = DtPeekSubtable ();
   1365 
   1366     while (FieldList)
   1367     {
   1368         DtCompileInteger ((UINT8 *) &Address, FieldList, 4, DT_NON_ZERO);
   1369 
   1370         DtCreateSubtable ((UINT8 *) &Address, 4, &Subtable);
   1371         DtInsertSubtable (ParentTable, Subtable);
   1372         FieldList = FieldList->Next;
   1373     }
   1374 
   1375     return (AE_OK);
   1376 }
   1377 
   1378 
   1379 /******************************************************************************
   1380  *
   1381  * FUNCTION:    DtCompileS3pt
   1382  *
   1383  * PARAMETERS:  PFieldList          - Current field list pointer
   1384  *
   1385  * RETURN:      Status
   1386  *
   1387  * DESCRIPTION: Compile S3PT (Pointed to by FPDT)
   1388  *
   1389  *****************************************************************************/
   1390 
   1391 ACPI_STATUS
   1392 DtCompileS3pt (
   1393     DT_FIELD                **PFieldList)
   1394 {
   1395     ACPI_STATUS             Status;
   1396     ACPI_FPDT_HEADER        *S3ptHeader;
   1397     DT_SUBTABLE             *Subtable;
   1398     DT_SUBTABLE             *ParentTable;
   1399     ACPI_DMTABLE_INFO       *InfoTable;
   1400     DT_FIELD                *SubtableStart;
   1401 
   1402 
   1403     Status = DtCompileTable (PFieldList, AcpiDmTableInfoS3pt,
   1404         &AslGbl_RootTable);
   1405     if (ACPI_FAILURE (Status))
   1406     {
   1407         return (Status);
   1408     }
   1409 
   1410     DtPushSubtable (AslGbl_RootTable);
   1411 
   1412     while (*PFieldList)
   1413     {
   1414         SubtableStart = *PFieldList;
   1415         Status = DtCompileTable (PFieldList, AcpiDmTableInfoS3ptHdr,
   1416             &Subtable);
   1417         if (ACPI_FAILURE (Status))
   1418         {
   1419             return (Status);
   1420         }
   1421 
   1422         ParentTable = DtPeekSubtable ();
   1423         DtInsertSubtable (ParentTable, Subtable);
   1424         DtPushSubtable (Subtable);
   1425 
   1426         S3ptHeader = ACPI_CAST_PTR (ACPI_FPDT_HEADER, Subtable->Buffer);
   1427 
   1428         switch (S3ptHeader->Type)
   1429         {
   1430         case ACPI_S3PT_TYPE_RESUME:
   1431 
   1432             InfoTable = AcpiDmTableInfoS3pt0;
   1433             break;
   1434 
   1435         case ACPI_S3PT_TYPE_SUSPEND:
   1436 
   1437             InfoTable = AcpiDmTableInfoS3pt1;
   1438             break;
   1439 
   1440         default:
   1441 
   1442             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "S3PT");
   1443             return (AE_ERROR);
   1444         }
   1445 
   1446         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   1447         if (ACPI_FAILURE (Status))
   1448         {
   1449             return (Status);
   1450         }
   1451 
   1452         ParentTable = DtPeekSubtable ();
   1453         DtInsertSubtable (ParentTable, Subtable);
   1454         DtPopSubtable ();
   1455     }
   1456 
   1457     return (AE_OK);
   1458 }
   1459 
   1460 
   1461 /******************************************************************************
   1462  *
   1463  * FUNCTION:    DtCompileSdev
   1464  *
   1465  * PARAMETERS:  List                - Current field list pointer
   1466  *
   1467  * RETURN:      Status
   1468  *
   1469  * DESCRIPTION: Compile SDEV.
   1470  *
   1471  *****************************************************************************/
   1472 
   1473 ACPI_STATUS
   1474 DtCompileSdev (
   1475     void                    **List)
   1476 {
   1477     ACPI_STATUS                 Status;
   1478     ACPI_SDEV_HEADER            *SdevHeader;
   1479     ACPI_SDEV_HEADER            *SecureComponentHeader;
   1480     DT_SUBTABLE                 *Subtable;
   1481     DT_SUBTABLE                 *ParentTable;
   1482     ACPI_DMTABLE_INFO           *InfoTable;
   1483     ACPI_DMTABLE_INFO           *SecureComponentInfoTable = NULL;
   1484     DT_FIELD                    **PFieldList = (DT_FIELD **) List;
   1485     DT_FIELD                    *SubtableStart;
   1486     ACPI_SDEV_PCIE              *Pcie = NULL;
   1487     ACPI_SDEV_NAMESPACE         *Namesp = NULL;
   1488     UINT32                      EntryCount;
   1489     ACPI_SDEV_SECURE_COMPONENT  *SecureComponent = NULL;
   1490     UINT16                      ComponentLength = 0;
   1491 
   1492 
   1493     /* Subtables */
   1494 
   1495     while (*PFieldList)
   1496     {
   1497         /* Compile common SDEV subtable header */
   1498 
   1499         SubtableStart = *PFieldList;
   1500         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdevHdr,
   1501             &Subtable);
   1502         if (ACPI_FAILURE (Status))
   1503         {
   1504             return (Status);
   1505         }
   1506 
   1507         ParentTable = DtPeekSubtable ();
   1508         DtInsertSubtable (ParentTable, Subtable);
   1509         DtPushSubtable (Subtable);
   1510 
   1511         SdevHeader = ACPI_CAST_PTR (ACPI_SDEV_HEADER, Subtable->Buffer);
   1512         SdevHeader->Length = (UINT8)(sizeof (ACPI_SDEV_HEADER));
   1513 
   1514         switch (SdevHeader->Type)
   1515         {
   1516         case ACPI_SDEV_TYPE_NAMESPACE_DEVICE:
   1517 
   1518             InfoTable = AcpiDmTableInfoSdev0;
   1519             Namesp = ACPI_CAST_PTR (ACPI_SDEV_NAMESPACE, Subtable->Buffer);
   1520             SecureComponent = ACPI_CAST_PTR (ACPI_SDEV_SECURE_COMPONENT,
   1521                 ACPI_ADD_PTR (UINT8, Subtable->Buffer, sizeof(ACPI_SDEV_NAMESPACE)));
   1522             break;
   1523 
   1524         case ACPI_SDEV_TYPE_PCIE_ENDPOINT_DEVICE:
   1525 
   1526             InfoTable = AcpiDmTableInfoSdev1;
   1527             Pcie = ACPI_CAST_PTR (ACPI_SDEV_PCIE, Subtable->Buffer);
   1528             break;
   1529 
   1530         default:
   1531 
   1532             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "SDEV");
   1533             return (AE_ERROR);
   1534         }
   1535 
   1536         /* Compile SDEV subtable body */
   1537 
   1538         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   1539         if (ACPI_FAILURE (Status))
   1540         {
   1541             return (Status);
   1542         }
   1543 
   1544         ParentTable = DtPeekSubtable ();
   1545         DtInsertSubtable (ParentTable, Subtable);
   1546 
   1547         /* Optional data fields are appended to the main subtable body */
   1548 
   1549         switch (SdevHeader->Type)
   1550         {
   1551         case ACPI_SDEV_TYPE_NAMESPACE_DEVICE:
   1552 
   1553             /*
   1554              * Device Id Offset will be be calculated differently depending on
   1555              * the presence of secure access components.
   1556              */
   1557             Namesp->DeviceIdOffset = 0;
   1558             ComponentLength = 0;
   1559 
   1560             /* If the secure access component exists, get the structures */
   1561 
   1562             if (SdevHeader->Flags & ACPI_SDEV_SECURE_COMPONENTS_PRESENT)
   1563             {
   1564                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev0b,
   1565                     &Subtable);
   1566                 if (ACPI_FAILURE (Status))
   1567                 {
   1568                     return (Status);
   1569                 }
   1570                 ParentTable = DtPeekSubtable ();
   1571                 DtInsertSubtable (ParentTable, Subtable);
   1572 
   1573                 Namesp->DeviceIdOffset += sizeof (ACPI_SDEV_SECURE_COMPONENT);
   1574 
   1575                 /* Compile a secure access component header */
   1576 
   1577                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdevSecCompHdr,
   1578                     &Subtable);
   1579                 if (ACPI_FAILURE (Status))
   1580                 {
   1581                     return (Status);
   1582                 }
   1583                 ParentTable = DtPeekSubtable ();
   1584                 DtInsertSubtable (ParentTable, Subtable);
   1585 
   1586                 /* Compile the secure access component */
   1587 
   1588                 SecureComponentHeader = ACPI_CAST_PTR (ACPI_SDEV_HEADER, Subtable->Buffer);
   1589                 switch (SecureComponentHeader->Type)
   1590                 {
   1591                 case ACPI_SDEV_TYPE_ID_COMPONENT:
   1592 
   1593                     SecureComponentInfoTable = AcpiDmTableInfoSdevSecCompId;
   1594                     Namesp->DeviceIdOffset += sizeof (ACPI_SDEV_ID_COMPONENT);
   1595                     ComponentLength = sizeof (ACPI_SDEV_ID_COMPONENT);
   1596                     break;
   1597 
   1598                 case ACPI_SDEV_TYPE_MEM_COMPONENT:
   1599 
   1600                     SecureComponentInfoTable = AcpiDmTableInfoSdevSecCompMem;
   1601                     Namesp->DeviceIdOffset += sizeof (ACPI_SDEV_MEM_COMPONENT);
   1602                     ComponentLength = sizeof (ACPI_SDEV_MEM_COMPONENT);
   1603                     break;
   1604 
   1605                 default:
   1606 
   1607                     /* Any other secure component types are undefined */
   1608 
   1609                     return (AE_ERROR);
   1610                 }
   1611 
   1612                 Status = DtCompileTable (PFieldList, SecureComponentInfoTable,
   1613                     &Subtable);
   1614                 if (ACPI_FAILURE (Status))
   1615                 {
   1616                     return (Status);
   1617                 }
   1618                 ParentTable = DtPeekSubtable ();
   1619                 DtInsertSubtable (ParentTable, Subtable);
   1620 
   1621                 SecureComponent->SecureComponentOffset =
   1622                     sizeof (ACPI_SDEV_NAMESPACE) + sizeof (ACPI_SDEV_SECURE_COMPONENT);
   1623                 SecureComponent->SecureComponentLength = ComponentLength;
   1624 
   1625 
   1626                 /*
   1627                  * Add the secure component to the subtable to be added for the
   1628                  * the namespace subtable's length
   1629                  */
   1630                 ComponentLength += sizeof (ACPI_SDEV_SECURE_COMPONENT);
   1631             }
   1632 
   1633             /* Append DeviceId namespace string */
   1634 
   1635             Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev0a,
   1636                 &Subtable);
   1637             if (ACPI_FAILURE (Status))
   1638             {
   1639                 return (Status);
   1640             }
   1641 
   1642             if (!Subtable)
   1643             {
   1644                 break;
   1645             }
   1646 
   1647             ParentTable = DtPeekSubtable ();
   1648             DtInsertSubtable (ParentTable, Subtable);
   1649 
   1650             Namesp->DeviceIdOffset += sizeof (ACPI_SDEV_NAMESPACE);
   1651 
   1652             Namesp->DeviceIdLength = (UINT16) Subtable->Length;
   1653 
   1654             /* Append Vendor data */
   1655 
   1656             Namesp->VendorDataLength = 0;
   1657             Namesp->VendorDataOffset = 0;
   1658 
   1659             if (*PFieldList)
   1660             {
   1661                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev1b,
   1662                     &Subtable);
   1663                 if (ACPI_FAILURE (Status))
   1664                 {
   1665                     return (Status);
   1666                 }
   1667 
   1668                 if (Subtable)
   1669                 {
   1670                     ParentTable = DtPeekSubtable ();
   1671                     DtInsertSubtable (ParentTable, Subtable);
   1672 
   1673                     Namesp->VendorDataOffset =
   1674                         Namesp->DeviceIdOffset + Namesp->DeviceIdLength;
   1675                     Namesp->VendorDataLength =
   1676                         (UINT16) Subtable->Length;
   1677 
   1678                     /* Final size of entire namespace structure */
   1679 
   1680                     SdevHeader->Length = (UINT16)(sizeof(ACPI_SDEV_NAMESPACE) +
   1681                         Subtable->Length + Namesp->DeviceIdLength) + ComponentLength;
   1682                 }
   1683             }
   1684 
   1685             break;
   1686 
   1687         case ACPI_SDEV_TYPE_PCIE_ENDPOINT_DEVICE:
   1688 
   1689             /* Append the PCIe path info first */
   1690 
   1691             EntryCount = 0;
   1692             while (*PFieldList && !strcmp ((*PFieldList)->Name, "Device"))
   1693             {
   1694                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev1a,
   1695                     &Subtable);
   1696                 if (ACPI_FAILURE (Status))
   1697                 {
   1698                     return (Status);
   1699                 }
   1700 
   1701                 if (!Subtable)
   1702                 {
   1703                     DtPopSubtable ();
   1704                     break;
   1705                 }
   1706 
   1707                 ParentTable = DtPeekSubtable ();
   1708                 DtInsertSubtable (ParentTable, Subtable);
   1709                 EntryCount++;
   1710             }
   1711 
   1712             /* Path offset will point immediately after the main subtable */
   1713 
   1714             Pcie->PathOffset = sizeof (ACPI_SDEV_PCIE);
   1715             Pcie->PathLength = (UINT16)
   1716                 (EntryCount * sizeof (ACPI_SDEV_PCIE_PATH));
   1717 
   1718             /* Append the Vendor Data last */
   1719 
   1720             Pcie->VendorDataLength = 0;
   1721             Pcie->VendorDataOffset = 0;
   1722 
   1723             if (*PFieldList)
   1724             {
   1725                 Status = DtCompileTable (PFieldList, AcpiDmTableInfoSdev1b,
   1726                     &Subtable);
   1727                 if (ACPI_FAILURE (Status))
   1728                 {
   1729                     return (Status);
   1730                 }
   1731 
   1732                 if (Subtable)
   1733                 {
   1734                     ParentTable = DtPeekSubtable ();
   1735                     DtInsertSubtable (ParentTable, Subtable);
   1736 
   1737                     Pcie->VendorDataOffset =
   1738                         Pcie->PathOffset + Pcie->PathLength;
   1739                     Pcie->VendorDataLength = (UINT16)
   1740                         Subtable->Length;
   1741                 }
   1742             }
   1743 
   1744             SdevHeader->Length =
   1745                 sizeof (ACPI_SDEV_PCIE) +
   1746                 Pcie->PathLength + Pcie->VendorDataLength;
   1747             break;
   1748 
   1749         default:
   1750 
   1751             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "SDEV");
   1752             return (AE_ERROR);
   1753         }
   1754 
   1755         DtPopSubtable ();
   1756     }
   1757 
   1758     return (AE_OK);
   1759 }
   1760 
   1761 
   1762 /******************************************************************************
   1763  *
   1764  * FUNCTION:    DtCompileSlic
   1765  *
   1766  * PARAMETERS:  List                - Current field list pointer
   1767  *
   1768  * RETURN:      Status
   1769  *
   1770  * DESCRIPTION: Compile SLIC.
   1771  *
   1772  *****************************************************************************/
   1773 
   1774 ACPI_STATUS
   1775 DtCompileSlic (
   1776     void                    **List)
   1777 {
   1778     ACPI_STATUS             Status;
   1779     DT_SUBTABLE             *Subtable;
   1780     DT_SUBTABLE             *ParentTable;
   1781     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1782 
   1783 
   1784     while (*PFieldList)
   1785     {
   1786         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSlic,
   1787             &Subtable);
   1788         if (ACPI_FAILURE (Status))
   1789         {
   1790             return (Status);
   1791         }
   1792 
   1793         ParentTable = DtPeekSubtable ();
   1794         DtInsertSubtable (ParentTable, Subtable);
   1795         DtPushSubtable (Subtable);
   1796         DtPopSubtable ();
   1797     }
   1798 
   1799     return (AE_OK);
   1800 }
   1801 
   1802 
   1803 /******************************************************************************
   1804  *
   1805  * FUNCTION:    DtCompileSlit
   1806  *
   1807  * PARAMETERS:  List                - Current field list pointer
   1808  *
   1809  * RETURN:      Status
   1810  *
   1811  * DESCRIPTION: Compile SLIT.
   1812  *
   1813  *****************************************************************************/
   1814 
   1815 ACPI_STATUS
   1816 DtCompileSlit (
   1817     void                    **List)
   1818 {
   1819     ACPI_STATUS             Status;
   1820     DT_SUBTABLE             *Subtable;
   1821     DT_SUBTABLE             *ParentTable;
   1822     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1823     DT_FIELD                *FieldList;
   1824     DT_FIELD                *EndOfFieldList = NULL;
   1825     UINT32                  Localities;
   1826     UINT32                  LocalityListLength;
   1827     UINT8                   *LocalityBuffer;
   1828 
   1829 
   1830     Status = DtCompileTable (PFieldList, AcpiDmTableInfoSlit,
   1831         &Subtable);
   1832     if (ACPI_FAILURE (Status))
   1833     {
   1834         return (Status);
   1835     }
   1836 
   1837     ParentTable = DtPeekSubtable ();
   1838     DtInsertSubtable (ParentTable, Subtable);
   1839 
   1840     Localities = *ACPI_CAST_PTR (UINT32, Subtable->Buffer);
   1841     LocalityBuffer = UtLocalCalloc (Localities);
   1842     LocalityListLength = 0;
   1843 
   1844     /* Compile each locality buffer */
   1845 
   1846     FieldList = *PFieldList;
   1847     while (FieldList)
   1848     {
   1849         DtCompileBuffer (LocalityBuffer,
   1850             FieldList->Value, FieldList, Localities);
   1851 
   1852         LocalityListLength++;
   1853         DtCreateSubtable (LocalityBuffer, Localities, &Subtable);
   1854         DtInsertSubtable (ParentTable, Subtable);
   1855         EndOfFieldList = FieldList;
   1856         FieldList = FieldList->Next;
   1857     }
   1858 
   1859     if (LocalityListLength != Localities)
   1860     {
   1861         sprintf(AslGbl_MsgBuffer,
   1862             "Found %u entries, must match LocalityCount: %u",
   1863             LocalityListLength, Localities);
   1864         DtError (ASL_ERROR, ASL_MSG_ENTRY_LIST, EndOfFieldList, AslGbl_MsgBuffer);
   1865         ACPI_FREE (LocalityBuffer);
   1866         return (AE_LIMIT);
   1867     }
   1868 
   1869     ACPI_FREE (LocalityBuffer);
   1870     return (AE_OK);
   1871 }
   1872 
   1873 
   1874 /******************************************************************************
   1875  *
   1876  * FUNCTION:    DtCompileSrat
   1877  *
   1878  * PARAMETERS:  List                - Current field list pointer
   1879  *
   1880  * RETURN:      Status
   1881  *
   1882  * DESCRIPTION: Compile SRAT.
   1883  *
   1884  *****************************************************************************/
   1885 
   1886 ACPI_STATUS
   1887 DtCompileSrat (
   1888     void                    **List)
   1889 {
   1890     ACPI_STATUS             Status;
   1891     DT_SUBTABLE             *Subtable;
   1892     DT_SUBTABLE             *ParentTable;
   1893     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1894     DT_FIELD                *SubtableStart;
   1895     ACPI_SUBTABLE_HEADER    *SratHeader;
   1896     ACPI_DMTABLE_INFO       *InfoTable;
   1897 
   1898 
   1899     Status = DtCompileTable (PFieldList, AcpiDmTableInfoSrat,
   1900         &Subtable);
   1901     if (ACPI_FAILURE (Status))
   1902     {
   1903         return (Status);
   1904     }
   1905 
   1906     ParentTable = DtPeekSubtable ();
   1907     DtInsertSubtable (ParentTable, Subtable);
   1908 
   1909     while (*PFieldList)
   1910     {
   1911         SubtableStart = *PFieldList;
   1912         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSratHdr,
   1913             &Subtable);
   1914         if (ACPI_FAILURE (Status))
   1915         {
   1916             return (Status);
   1917         }
   1918 
   1919         ParentTable = DtPeekSubtable ();
   1920         DtInsertSubtable (ParentTable, Subtable);
   1921         DtPushSubtable (Subtable);
   1922 
   1923         SratHeader = ACPI_CAST_PTR (ACPI_SUBTABLE_HEADER, Subtable->Buffer);
   1924 
   1925         switch (SratHeader->Type)
   1926         {
   1927         case ACPI_SRAT_TYPE_CPU_AFFINITY:
   1928 
   1929             InfoTable = AcpiDmTableInfoSrat0;
   1930             break;
   1931 
   1932         case ACPI_SRAT_TYPE_MEMORY_AFFINITY:
   1933 
   1934             InfoTable = AcpiDmTableInfoSrat1;
   1935             break;
   1936 
   1937         case ACPI_SRAT_TYPE_X2APIC_CPU_AFFINITY:
   1938 
   1939             InfoTable = AcpiDmTableInfoSrat2;
   1940             break;
   1941 
   1942         case ACPI_SRAT_TYPE_GICC_AFFINITY:
   1943 
   1944             InfoTable = AcpiDmTableInfoSrat3;
   1945             break;
   1946 
   1947         case ACPI_SRAT_TYPE_GIC_ITS_AFFINITY:
   1948 
   1949             InfoTable = AcpiDmTableInfoSrat4;
   1950             break;
   1951 
   1952         case ACPI_SRAT_TYPE_GENERIC_AFFINITY:
   1953 
   1954             InfoTable = AcpiDmTableInfoSrat5;
   1955             break;
   1956 
   1957         default:
   1958 
   1959             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "SRAT");
   1960             return (AE_ERROR);
   1961         }
   1962 
   1963         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   1964         if (ACPI_FAILURE (Status))
   1965         {
   1966             return (Status);
   1967         }
   1968 
   1969         ParentTable = DtPeekSubtable ();
   1970         DtInsertSubtable (ParentTable, Subtable);
   1971         DtPopSubtable ();
   1972     }
   1973 
   1974     return (AE_OK);
   1975 }
   1976 
   1977 
   1978 /******************************************************************************
   1979  *
   1980  * FUNCTION:    DtCompileStao
   1981  *
   1982  * PARAMETERS:  PFieldList          - Current field list pointer
   1983  *
   1984  * RETURN:      Status
   1985  *
   1986  * DESCRIPTION: Compile STAO.
   1987  *
   1988  *****************************************************************************/
   1989 
   1990 ACPI_STATUS
   1991 DtCompileStao (
   1992     void                    **List)
   1993 {
   1994     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   1995     DT_SUBTABLE             *Subtable;
   1996     DT_SUBTABLE             *ParentTable;
   1997     ACPI_STATUS             Status;
   1998 
   1999 
   2000     /* Compile the main table */
   2001 
   2002     Status = DtCompileTable (PFieldList, AcpiDmTableInfoStao,
   2003         &Subtable);
   2004     if (ACPI_FAILURE (Status))
   2005     {
   2006         return (Status);
   2007     }
   2008 
   2009     ParentTable = DtPeekSubtable ();
   2010     DtInsertSubtable (ParentTable, Subtable);
   2011 
   2012     /* Compile each ASCII namestring as a subtable */
   2013 
   2014     while (*PFieldList)
   2015     {
   2016         Status = DtCompileTable (PFieldList, AcpiDmTableInfoStaoStr,
   2017             &Subtable);
   2018         if (ACPI_FAILURE (Status))
   2019         {
   2020             return (Status);
   2021         }
   2022 
   2023         ParentTable = DtPeekSubtable ();
   2024         DtInsertSubtable (ParentTable, Subtable);
   2025     }
   2026 
   2027     return (AE_OK);
   2028 }
   2029 
   2030 
   2031 
   2032 /******************************************************************************
   2033  *
   2034  * FUNCTION:    DtCompileSvkl
   2035  *
   2036  * PARAMETERS:  PFieldList          - Current field list pointer
   2037  *
   2038  * RETURN:      Status
   2039  *
   2040  * DESCRIPTION: Compile SVKL.
   2041  *
   2042  * NOTES: SVKL is essentially a flat table, with a small main table and
   2043  *          a variable number of a single type of subtable.
   2044  *
   2045  *****************************************************************************/
   2046 
   2047 ACPI_STATUS
   2048 DtCompileSvkl (
   2049     void                    **List)
   2050 {
   2051     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2052     DT_SUBTABLE             *Subtable;
   2053     DT_SUBTABLE             *ParentTable;
   2054     ACPI_STATUS             Status;
   2055 
   2056 
   2057     /* Compile the main table */
   2058 
   2059     Status = DtCompileTable (PFieldList, AcpiDmTableInfoSvkl,
   2060         &Subtable);
   2061     if (ACPI_FAILURE (Status))
   2062     {
   2063         return (Status);
   2064     }
   2065 
   2066     ParentTable = DtPeekSubtable ();
   2067     DtInsertSubtable (ParentTable, Subtable);
   2068 
   2069     /* Compile each subtable */
   2070 
   2071     while (*PFieldList)
   2072     {
   2073         Status = DtCompileTable (PFieldList, AcpiDmTableInfoSvkl0,
   2074             &Subtable);
   2075         if (ACPI_FAILURE (Status))
   2076         {
   2077             return (Status);
   2078         }
   2079 
   2080         ParentTable = DtPeekSubtable ();
   2081         DtInsertSubtable (ParentTable, Subtable);
   2082     }
   2083 
   2084     return (AE_OK);
   2085 }
   2086 
   2087 
   2088 /******************************************************************************
   2089  *
   2090  * FUNCTION:    DtCompileTcpa
   2091  *
   2092  * PARAMETERS:  PFieldList          - Current field list pointer
   2093  *
   2094  * RETURN:      Status
   2095  *
   2096  * DESCRIPTION: Compile TCPA.
   2097  *
   2098  *****************************************************************************/
   2099 
   2100 ACPI_STATUS
   2101 DtCompileTcpa (
   2102     void                    **List)
   2103 {
   2104     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2105     DT_SUBTABLE             *Subtable;
   2106     ACPI_TABLE_TCPA_HDR     *TcpaHeader;
   2107     DT_SUBTABLE             *ParentTable;
   2108     ACPI_STATUS             Status;
   2109 
   2110 
   2111     /* Compile the main table */
   2112 
   2113     Status = DtCompileTable (PFieldList, AcpiDmTableInfoTcpaHdr,
   2114         &Subtable);
   2115     if (ACPI_FAILURE (Status))
   2116     {
   2117         return (Status);
   2118     }
   2119 
   2120     ParentTable = DtPeekSubtable ();
   2121     DtInsertSubtable (ParentTable, Subtable);
   2122 
   2123     /*
   2124      * Examine the PlatformClass field to determine the table type.
   2125      * Either a client or server table. Only one.
   2126      */
   2127     TcpaHeader = ACPI_CAST_PTR (ACPI_TABLE_TCPA_HDR, ParentTable->Buffer);
   2128 
   2129     switch (TcpaHeader->PlatformClass)
   2130     {
   2131     case ACPI_TCPA_CLIENT_TABLE:
   2132 
   2133         Status = DtCompileTable (PFieldList, AcpiDmTableInfoTcpaClient,
   2134             &Subtable);
   2135         break;
   2136 
   2137     case ACPI_TCPA_SERVER_TABLE:
   2138 
   2139         Status = DtCompileTable (PFieldList, AcpiDmTableInfoTcpaServer,
   2140             &Subtable);
   2141         break;
   2142 
   2143     default:
   2144 
   2145         AcpiOsPrintf ("\n**** Unknown TCPA Platform Class 0x%X\n",
   2146             TcpaHeader->PlatformClass);
   2147         Status = AE_ERROR;
   2148         break;
   2149     }
   2150 
   2151     ParentTable = DtPeekSubtable ();
   2152     DtInsertSubtable (ParentTable, Subtable);
   2153     return (Status);
   2154 }
   2155 
   2156 
   2157 /******************************************************************************
   2158  *
   2159  * FUNCTION:    DtCompileTpm2Rev3
   2160  *
   2161  * PARAMETERS:  PFieldList          - Current field list pointer
   2162  *
   2163  * RETURN:      Status
   2164  *
   2165  * DESCRIPTION: Compile TPM2 revision 3
   2166  *
   2167  *****************************************************************************/
   2168 static ACPI_STATUS
   2169 DtCompileTpm2Rev3 (
   2170     void                    **List)
   2171 {
   2172     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2173     DT_SUBTABLE             *Subtable;
   2174     ACPI_TABLE_TPM23        *Tpm23Header;
   2175     DT_SUBTABLE             *ParentTable;
   2176     ACPI_STATUS             Status = AE_OK;
   2177 
   2178 
   2179     Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm23,
   2180         &Subtable);
   2181 
   2182     ParentTable = DtPeekSubtable ();
   2183     DtInsertSubtable (ParentTable, Subtable);
   2184     Tpm23Header = ACPI_CAST_PTR (ACPI_TABLE_TPM23, ParentTable->Buffer);
   2185 
   2186     /* Subtable type depends on the StartMethod */
   2187 
   2188     switch (Tpm23Header->StartMethod)
   2189     {
   2190     case ACPI_TPM23_ACPI_START_METHOD:
   2191 
   2192         /* Subtable specific to to ARM_SMC */
   2193 
   2194         Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm23a,
   2195             &Subtable);
   2196         if (ACPI_FAILURE (Status))
   2197         {
   2198             return (Status);
   2199         }
   2200 
   2201         ParentTable = DtPeekSubtable ();
   2202         DtInsertSubtable (ParentTable, Subtable);
   2203         break;
   2204 
   2205     default:
   2206         break;
   2207     }
   2208 
   2209     return (Status);
   2210 }
   2211 
   2212 
   2213 /******************************************************************************
   2214  *
   2215  * FUNCTION:    DtCompileTpm2
   2216  *
   2217  * PARAMETERS:  PFieldList          - Current field list pointer
   2218  *
   2219  * RETURN:      Status
   2220  *
   2221  * DESCRIPTION: Compile TPM2.
   2222  *
   2223  *****************************************************************************/
   2224 
   2225 ACPI_STATUS
   2226 DtCompileTpm2 (
   2227     void                    **List)
   2228 {
   2229     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2230     DT_SUBTABLE             *Subtable;
   2231     ACPI_TABLE_TPM2         *Tpm2Header;
   2232     DT_SUBTABLE             *ParentTable;
   2233     ACPI_STATUS             Status = AE_OK;
   2234     ACPI_TABLE_HEADER       *Header;
   2235 
   2236 
   2237     ParentTable = DtPeekSubtable ();
   2238 
   2239     Header = ACPI_CAST_PTR (ACPI_TABLE_HEADER, ParentTable->Buffer);
   2240 
   2241     if (Header->Revision == 3)
   2242     {
   2243         return (DtCompileTpm2Rev3 (List));
   2244     }
   2245 
   2246     /* Compile the main table */
   2247 
   2248     Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm2,
   2249         &Subtable);
   2250     if (ACPI_FAILURE (Status))
   2251     {
   2252         return (Status);
   2253     }
   2254 
   2255     ParentTable = DtPeekSubtable ();
   2256     DtInsertSubtable (ParentTable, Subtable);
   2257 
   2258     Tpm2Header = ACPI_CAST_PTR (ACPI_TABLE_TPM2, ParentTable->Buffer);
   2259 
   2260     /* Method parameters */
   2261     /* Optional: Log area minimum length */
   2262     /* Optional: Log area start address */
   2263     /* TBD: Optional fields above not fully implemented (not optional at this time) */
   2264 
   2265     Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm2a,
   2266         &Subtable);
   2267     if (ACPI_FAILURE (Status))
   2268     {
   2269         return (Status);
   2270     }
   2271 
   2272     ParentTable = DtPeekSubtable ();
   2273     DtInsertSubtable (ParentTable, Subtable);
   2274 
   2275 
   2276     /* Subtable type depends on the StartMethod */
   2277 
   2278     switch (Tpm2Header->StartMethod)
   2279     {
   2280     case ACPI_TPM2_COMMAND_BUFFER_WITH_ARM_SMC:
   2281 
   2282         /* Subtable specific to to ARM_SMC */
   2283 
   2284         Status = DtCompileTable (PFieldList, AcpiDmTableInfoTpm211,
   2285             &Subtable);
   2286         if (ACPI_FAILURE (Status))
   2287         {
   2288             return (Status);
   2289         }
   2290 
   2291         ParentTable = DtPeekSubtable ();
   2292         DtInsertSubtable (ParentTable, Subtable);
   2293         break;
   2294 
   2295     case ACPI_TPM2_START_METHOD:
   2296     case ACPI_TPM2_MEMORY_MAPPED:
   2297     case ACPI_TPM2_COMMAND_BUFFER:
   2298     case ACPI_TPM2_COMMAND_BUFFER_WITH_START_METHOD:
   2299         break;
   2300 
   2301     case ACPI_TPM2_RESERVED1:
   2302     case ACPI_TPM2_RESERVED3:
   2303     case ACPI_TPM2_RESERVED4:
   2304     case ACPI_TPM2_RESERVED5:
   2305     case ACPI_TPM2_RESERVED9:
   2306     case ACPI_TPM2_RESERVED10:
   2307 
   2308         AcpiOsPrintf ("\n**** Reserved TPM2 Start Method type 0x%X\n",
   2309             Tpm2Header->StartMethod);
   2310         Status = AE_ERROR;
   2311         break;
   2312 
   2313     case ACPI_TPM2_NOT_ALLOWED:
   2314     default:
   2315 
   2316         AcpiOsPrintf ("\n**** Unknown TPM2 Start Method type 0x%X\n",
   2317             Tpm2Header->StartMethod);
   2318         Status = AE_ERROR;
   2319         break;
   2320     }
   2321 
   2322     return (Status);
   2323 }
   2324 
   2325 
   2326 /******************************************************************************
   2327  *
   2328  * FUNCTION:    DtGetGenericTableInfo
   2329  *
   2330  * PARAMETERS:  Name                - Generic type name
   2331  *
   2332  * RETURN:      Info entry
   2333  *
   2334  * DESCRIPTION: Obtain table info for a generic name entry
   2335  *
   2336  *****************************************************************************/
   2337 
   2338 ACPI_DMTABLE_INFO *
   2339 DtGetGenericTableInfo (
   2340     char                    *Name)
   2341 {
   2342     ACPI_DMTABLE_INFO       *Info;
   2343     UINT32                  i;
   2344 
   2345 
   2346     if (!Name)
   2347     {
   2348         return (NULL);
   2349     }
   2350 
   2351     /* Search info table for name match */
   2352 
   2353     for (i = 0; ; i++)
   2354     {
   2355         Info = AcpiDmTableInfoGeneric[i];
   2356         if (Info->Opcode == ACPI_DMT_EXIT)
   2357         {
   2358             Info = NULL;
   2359             break;
   2360         }
   2361 
   2362         /* Use caseless compare for generic keywords */
   2363 
   2364         if (!AcpiUtStricmp (Name, Info->Name))
   2365         {
   2366             break;
   2367         }
   2368     }
   2369 
   2370     return (Info);
   2371 }
   2372 
   2373 
   2374 /******************************************************************************
   2375  *
   2376  * FUNCTION:    DtCompileUefi
   2377  *
   2378  * PARAMETERS:  List                - Current field list pointer
   2379  *
   2380  * RETURN:      Status
   2381  *
   2382  * DESCRIPTION: Compile UEFI.
   2383  *
   2384  *****************************************************************************/
   2385 
   2386 ACPI_STATUS
   2387 DtCompileUefi (
   2388     void                    **List)
   2389 {
   2390     ACPI_STATUS             Status;
   2391     DT_SUBTABLE             *Subtable;
   2392     DT_SUBTABLE             *ParentTable;
   2393     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2394     UINT16                  *DataOffset;
   2395 
   2396 
   2397     /* Compile the predefined portion of the UEFI table */
   2398 
   2399     Status = DtCompileTable (PFieldList, AcpiDmTableInfoUefi,
   2400         &Subtable);
   2401     if (ACPI_FAILURE (Status))
   2402     {
   2403         return (Status);
   2404     }
   2405 
   2406     DataOffset = (UINT16 *) (Subtable->Buffer + 16);
   2407     *DataOffset = sizeof (ACPI_TABLE_UEFI);
   2408 
   2409     ParentTable = DtPeekSubtable ();
   2410     DtInsertSubtable (ParentTable, Subtable);
   2411 
   2412     /*
   2413      * Compile the "generic" portion of the UEFI table. This
   2414      * part of the table is not predefined and any of the generic
   2415      * operators may be used.
   2416      */
   2417     DtCompileGeneric ((void **) PFieldList, NULL, NULL);
   2418     return (AE_OK);
   2419 }
   2420 
   2421 
   2422 /******************************************************************************
   2423  *
   2424  * FUNCTION:    DtCompileViot
   2425  *
   2426  * PARAMETERS:  List                - Current field list pointer
   2427  *
   2428  * RETURN:      Status
   2429  *
   2430  * DESCRIPTION: Compile VIOT.
   2431  *
   2432  *****************************************************************************/
   2433 
   2434 ACPI_STATUS
   2435 DtCompileViot (
   2436     void                    **List)
   2437 {
   2438     ACPI_STATUS             Status;
   2439     DT_SUBTABLE             *Subtable;
   2440     DT_SUBTABLE             *ParentTable;
   2441     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2442     DT_FIELD                *SubtableStart;
   2443     ACPI_TABLE_VIOT         *Viot;
   2444     ACPI_VIOT_HEADER        *ViotHeader;
   2445     ACPI_DMTABLE_INFO       *InfoTable;
   2446     UINT16                  NodeCount;
   2447 
   2448     ParentTable = DtPeekSubtable ();
   2449 
   2450     Status = DtCompileTable (PFieldList, AcpiDmTableInfoViot, &Subtable);
   2451     if (ACPI_FAILURE (Status))
   2452     {
   2453         return (Status);
   2454     }
   2455     DtInsertSubtable (ParentTable, Subtable);
   2456 
   2457     /*
   2458      * Using ACPI_SUB_PTR, We needn't define a separate structure. Care
   2459      * should be taken to avoid accessing ACPI_TABLE_HEADER fields.
   2460      */
   2461     Viot = ACPI_SUB_PTR (ACPI_TABLE_VIOT, Subtable->Buffer,
   2462         sizeof (ACPI_TABLE_HEADER));
   2463 
   2464     Viot->NodeOffset = sizeof (ACPI_TABLE_VIOT);
   2465 
   2466     NodeCount = 0;
   2467     while (*PFieldList) {
   2468         SubtableStart = *PFieldList;
   2469         Status = DtCompileTable (PFieldList, AcpiDmTableInfoViotHeader,
   2470             &Subtable);
   2471         if (ACPI_FAILURE (Status))
   2472         {
   2473             return (Status);
   2474         }
   2475 
   2476         ParentTable = DtPeekSubtable ();
   2477         DtInsertSubtable (ParentTable, Subtable);
   2478         DtPushSubtable (Subtable);
   2479 
   2480         ViotHeader = ACPI_CAST_PTR (ACPI_VIOT_HEADER, Subtable->Buffer);
   2481 
   2482         switch (ViotHeader->Type)
   2483         {
   2484         case ACPI_VIOT_NODE_PCI_RANGE:
   2485 
   2486             InfoTable = AcpiDmTableInfoViot1;
   2487             break;
   2488 
   2489         case ACPI_VIOT_NODE_MMIO:
   2490 
   2491             InfoTable = AcpiDmTableInfoViot2;
   2492             break;
   2493 
   2494         case ACPI_VIOT_NODE_VIRTIO_IOMMU_PCI:
   2495 
   2496             InfoTable = AcpiDmTableInfoViot3;
   2497             break;
   2498 
   2499         case ACPI_VIOT_NODE_VIRTIO_IOMMU_MMIO:
   2500 
   2501             InfoTable = AcpiDmTableInfoViot4;
   2502             break;
   2503 
   2504         default:
   2505 
   2506             DtFatal (ASL_MSG_UNKNOWN_SUBTABLE, SubtableStart, "VIOT");
   2507             return (AE_ERROR);
   2508         }
   2509 
   2510         Status = DtCompileTable (PFieldList, InfoTable, &Subtable);
   2511         if (ACPI_FAILURE (Status))
   2512         {
   2513             return (Status);
   2514         }
   2515 
   2516         ParentTable = DtPeekSubtable ();
   2517         DtInsertSubtable (ParentTable, Subtable);
   2518         DtPopSubtable ();
   2519         NodeCount++;
   2520     }
   2521 
   2522     Viot->NodeCount = NodeCount;
   2523     return (AE_OK);
   2524 }
   2525 
   2526 
   2527 /******************************************************************************
   2528  *
   2529  * FUNCTION:    DtCompileWdat
   2530  *
   2531  * PARAMETERS:  List                - Current field list pointer
   2532  *
   2533  * RETURN:      Status
   2534  *
   2535  * DESCRIPTION: Compile WDAT.
   2536  *
   2537  *****************************************************************************/
   2538 
   2539 ACPI_STATUS
   2540 DtCompileWdat (
   2541     void                    **List)
   2542 {
   2543     ACPI_STATUS             Status;
   2544 
   2545 
   2546     Status = DtCompileTwoSubtables (List,
   2547         AcpiDmTableInfoWdat, AcpiDmTableInfoWdat0);
   2548     return (Status);
   2549 }
   2550 
   2551 
   2552 /******************************************************************************
   2553  *
   2554  * FUNCTION:    DtCompileWpbt
   2555  *
   2556  * PARAMETERS:  List                - Current field list pointer
   2557  *
   2558  * RETURN:      Status
   2559  *
   2560  * DESCRIPTION: Compile WPBT.
   2561  *
   2562  *****************************************************************************/
   2563 
   2564 ACPI_STATUS
   2565 DtCompileWpbt (
   2566     void                    **List)
   2567 {
   2568     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2569     DT_SUBTABLE             *Subtable;
   2570     DT_SUBTABLE             *ParentTable;
   2571     ACPI_TABLE_WPBT         *Table;
   2572     ACPI_STATUS             Status;
   2573     UINT16                  Length;
   2574 
   2575 
   2576     /* Compile the main table */
   2577 
   2578     Status = DtCompileTable (PFieldList, AcpiDmTableInfoWpbt,
   2579         &Subtable);
   2580     if (ACPI_FAILURE (Status))
   2581     {
   2582         return (Status);
   2583     }
   2584 
   2585     ParentTable = DtPeekSubtable ();
   2586     DtInsertSubtable (ParentTable, Subtable);
   2587 
   2588     /* Compile the argument list subtable */
   2589 
   2590     Status = DtCompileTable (PFieldList, AcpiDmTableInfoWpbt0,
   2591         &Subtable);
   2592     if (ACPI_FAILURE (Status))
   2593     {
   2594         return (Status);
   2595     }
   2596 
   2597     /* Extract the length of the Arguments buffer, insert into main table */
   2598 
   2599     Length = (UINT16) Subtable->TotalLength;
   2600     Table = ACPI_CAST_PTR (ACPI_TABLE_WPBT, ParentTable->Buffer);
   2601     Table->ArgumentsLength = Length;
   2602 
   2603     ParentTable = DtPeekSubtable ();
   2604     DtInsertSubtable (ParentTable, Subtable);
   2605     return (AE_OK);
   2606 }
   2607 
   2608 
   2609 /******************************************************************************
   2610  *
   2611  * FUNCTION:    DtCompileXsdt
   2612  *
   2613  * PARAMETERS:  List                - Current field list pointer
   2614  *
   2615  * RETURN:      Status
   2616  *
   2617  * DESCRIPTION: Compile XSDT.
   2618  *
   2619  *****************************************************************************/
   2620 
   2621 ACPI_STATUS
   2622 DtCompileXsdt (
   2623     void                    **List)
   2624 {
   2625     DT_SUBTABLE             *Subtable;
   2626     DT_SUBTABLE             *ParentTable;
   2627     DT_FIELD                *FieldList = *(DT_FIELD **) List;
   2628     UINT64                  Address;
   2629 
   2630 
   2631     ParentTable = DtPeekSubtable ();
   2632 
   2633     while (FieldList)
   2634     {
   2635         DtCompileInteger ((UINT8 *) &Address, FieldList, 8, DT_NON_ZERO);
   2636 
   2637         DtCreateSubtable ((UINT8 *) &Address, 8, &Subtable);
   2638         DtInsertSubtable (ParentTable, Subtable);
   2639         FieldList = FieldList->Next;
   2640     }
   2641 
   2642     return (AE_OK);
   2643 }
   2644 
   2645 
   2646 /******************************************************************************
   2647  *
   2648  * FUNCTION:    DtCompileGeneric
   2649  *
   2650  * PARAMETERS:  List                - Current field list pointer
   2651  *              Name                - Field name to end generic compiling
   2652  *              Length              - Compiled table length to return
   2653  *
   2654  * RETURN:      Status
   2655  *
   2656  * DESCRIPTION: Compile generic unknown table.
   2657  *
   2658  *****************************************************************************/
   2659 
   2660 ACPI_STATUS
   2661 DtCompileGeneric (
   2662     void                    **List,
   2663     char                    *Name,
   2664     UINT32                  *Length)
   2665 {
   2666     ACPI_STATUS             Status;
   2667     DT_SUBTABLE             *Subtable;
   2668     DT_SUBTABLE             *ParentTable;
   2669     DT_FIELD                **PFieldList = (DT_FIELD **) List;
   2670     ACPI_DMTABLE_INFO       *Info;
   2671 
   2672 
   2673     ParentTable = DtPeekSubtable ();
   2674 
   2675     /*
   2676      * Compile the "generic" portion of the table. This
   2677      * part of the table is not predefined and any of the generic
   2678      * operators may be used.
   2679      */
   2680 
   2681     /* Find any and all labels in the entire generic portion */
   2682 
   2683     DtDetectAllLabels (*PFieldList);
   2684 
   2685     /* Now we can actually compile the parse tree */
   2686 
   2687     if (Length && *Length)
   2688     {
   2689         *Length = 0;
   2690     }
   2691     while (*PFieldList)
   2692     {
   2693         if (Name && !strcmp ((*PFieldList)->Name, Name))
   2694         {
   2695             break;
   2696         }
   2697 
   2698         Info = DtGetGenericTableInfo ((*PFieldList)->Name);
   2699         if (!Info)
   2700         {
   2701             sprintf (AslGbl_MsgBuffer, "Generic data type \"%s\" not found",
   2702                 (*PFieldList)->Name);
   2703             DtNameError (ASL_ERROR, ASL_MSG_INVALID_FIELD_NAME,
   2704                 (*PFieldList), AslGbl_MsgBuffer);
   2705 
   2706             *PFieldList = (*PFieldList)->Next;
   2707             continue;
   2708         }
   2709 
   2710         Status = DtCompileTable (PFieldList, Info,
   2711             &Subtable);
   2712         if (ACPI_SUCCESS (Status))
   2713         {
   2714             DtInsertSubtable (ParentTable, Subtable);
   2715             if (Length)
   2716             {
   2717                 *Length += Subtable->Length;
   2718             }
   2719         }
   2720         else
   2721         {
   2722             *PFieldList = (*PFieldList)->Next;
   2723 
   2724             if (Status == AE_NOT_FOUND)
   2725             {
   2726                 sprintf (AslGbl_MsgBuffer, "Generic data type \"%s\" not found",
   2727                     (*PFieldList)->Name);
   2728                 DtNameError (ASL_ERROR, ASL_MSG_INVALID_FIELD_NAME,
   2729                     (*PFieldList), AslGbl_MsgBuffer);
   2730             }
   2731         }
   2732     }
   2733 
   2734     return (AE_OK);
   2735 }
   2736