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