xref: /freebsd/sys/contrib/dev/acpica/compiler/aslprepkg.c (revision 3fc36ee018bb836bd1796067cf4ef8683f166ebc)
1 /******************************************************************************
2  *
3  * Module Name: aslprepkg - support for ACPI predefined name package objects
4  *
5  *****************************************************************************/
6 
7 /*
8  * Copyright (C) 2000 - 2016, Intel Corp.
9  * All rights reserved.
10  *
11  * Redistribution and use in source and binary forms, with or without
12  * modification, are permitted provided that the following conditions
13  * are met:
14  * 1. Redistributions of source code must retain the above copyright
15  *    notice, this list of conditions, and the following disclaimer,
16  *    without modification.
17  * 2. Redistributions in binary form must reproduce at minimum a disclaimer
18  *    substantially similar to the "NO WARRANTY" disclaimer below
19  *    ("Disclaimer") and any redistribution must be conditioned upon
20  *    including a substantially similar Disclaimer requirement for further
21  *    binary redistribution.
22  * 3. Neither the names of the above-listed copyright holders nor the names
23  *    of any contributors may be used to endorse or promote products derived
24  *    from this software without specific prior written permission.
25  *
26  * Alternatively, this software may be distributed under the terms of the
27  * GNU General Public License ("GPL") version 2 as published by the Free
28  * Software Foundation.
29  *
30  * NO WARRANTY
31  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
32  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
33  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
34  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
35  * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
36  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
37  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
38  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
39  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
40  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
41  * POSSIBILITY OF SUCH DAMAGES.
42  */
43 
44 #include <contrib/dev/acpica/compiler/aslcompiler.h>
45 #include "aslcompiler.y.h"
46 #include <contrib/dev/acpica/include/acpredef.h>
47 
48 
49 #define _COMPONENT          ACPI_COMPILER
50         ACPI_MODULE_NAME    ("aslprepkg")
51 
52 
53 /* Local prototypes */
54 
55 static ACPI_PARSE_OBJECT *
56 ApCheckPackageElements (
57     const char                  *PredefinedName,
58     ACPI_PARSE_OBJECT           *Op,
59     UINT8                       Type1,
60     UINT32                      Count1,
61     UINT8                       Type2,
62     UINT32                      Count2);
63 
64 static void
65 ApCheckPackageList (
66     const char                  *PredefinedName,
67     ACPI_PARSE_OBJECT           *ParentOp,
68     const ACPI_PREDEFINED_INFO  *Package,
69     UINT32                      StartIndex,
70     UINT32                      Count);
71 
72 static void
73 ApPackageTooSmall (
74     const char                  *PredefinedName,
75     ACPI_PARSE_OBJECT           *Op,
76     UINT32                      Count,
77     UINT32                      ExpectedCount);
78 
79 static void
80 ApZeroLengthPackage (
81     const char                  *PredefinedName,
82     ACPI_PARSE_OBJECT           *Op);
83 
84 static void
85 ApPackageTooLarge (
86     const char                  *PredefinedName,
87     ACPI_PARSE_OBJECT           *Op,
88     UINT32                      Count,
89     UINT32                      ExpectedCount);
90 
91 static void
92 ApCustomPackage (
93     ACPI_PARSE_OBJECT           *ParentOp,
94     const ACPI_PREDEFINED_INFO  *Predefined);
95 
96 
97 /*******************************************************************************
98  *
99  * FUNCTION:    ApCheckPackage
100  *
101  * PARAMETERS:  ParentOp            - Parser op for the package
102  *              Predefined          - Pointer to package-specific info for
103  *                                    the method
104  *
105  * RETURN:      None
106  *
107  * DESCRIPTION: Top-level validation for predefined name return package
108  *              objects.
109  *
110  ******************************************************************************/
111 
112 void
113 ApCheckPackage (
114     ACPI_PARSE_OBJECT           *ParentOp,
115     const ACPI_PREDEFINED_INFO  *Predefined)
116 {
117     ACPI_PARSE_OBJECT           *Op;
118     const ACPI_PREDEFINED_INFO  *Package;
119     ACPI_STATUS                 Status;
120     UINT32                      ExpectedCount;
121     UINT32                      Count;
122     UINT32                      i;
123 
124 
125     /* The package info for this name is in the next table entry */
126 
127     Package = Predefined + 1;
128 
129     /* First child is the package length */
130 
131     Op = ParentOp->Asl.Child;
132     Count = (UINT32) Op->Asl.Value.Integer;
133 
134     /*
135      * Many of the variable-length top-level packages are allowed to simply
136      * have zero elements. This allows the BIOS to tell the host that even
137      * though the predefined name/method exists, the feature is not supported.
138      * Other package types require one or more elements. In any case, there
139      * is no need to continue validation.
140      */
141     if (!Count)
142     {
143         switch (Package->RetInfo.Type)
144         {
145         case ACPI_PTYPE1_FIXED:
146         case ACPI_PTYPE1_OPTION:
147         case ACPI_PTYPE2_PKG_COUNT:
148         case ACPI_PTYPE2_REV_FIXED:
149 
150             ApZeroLengthPackage (Predefined->Info.Name, ParentOp);
151             break;
152 
153         case ACPI_PTYPE1_VAR:
154         case ACPI_PTYPE2:
155         case ACPI_PTYPE2_COUNT:
156         case ACPI_PTYPE2_FIXED:
157         case ACPI_PTYPE2_MIN:
158         case ACPI_PTYPE2_FIX_VAR:
159         case ACPI_PTYPE2_VAR_VAR:
160         default:
161 
162             break;
163         }
164 
165         return;
166     }
167 
168     /* Get the first element of the package */
169 
170     Op = Op->Asl.Next;
171 
172     /* Decode the package type */
173 
174     switch (Package->RetInfo.Type)
175     {
176     case ACPI_PTYPE_CUSTOM:
177 
178         ApCustomPackage (ParentOp, Predefined);
179         break;
180 
181     case ACPI_PTYPE1_FIXED:
182         /*
183          * The package count is fixed and there are no subpackages
184          *
185          * If package is too small, exit.
186          * If package is larger than expected, issue warning but continue
187          */
188         ExpectedCount = Package->RetInfo.Count1 + Package->RetInfo.Count2;
189         if (Count < ExpectedCount)
190         {
191             goto PackageTooSmall;
192         }
193         else if (Count > ExpectedCount)
194         {
195             ApPackageTooLarge (Predefined->Info.Name, ParentOp,
196                 Count, ExpectedCount);
197         }
198 
199         /* Validate all elements of the package */
200 
201         ApCheckPackageElements (Predefined->Info.Name, Op,
202             Package->RetInfo.ObjectType1, Package->RetInfo.Count1,
203             Package->RetInfo.ObjectType2, Package->RetInfo.Count2);
204         break;
205 
206     case ACPI_PTYPE1_VAR:
207         /*
208          * The package count is variable, there are no subpackages,
209          * and all elements must be of the same type
210          */
211         for (i = 0; i < Count; i++)
212         {
213             ApCheckObjectType (Predefined->Info.Name, Op,
214                 Package->RetInfo.ObjectType1, i);
215             Op = Op->Asl.Next;
216         }
217         break;
218 
219     case ACPI_PTYPE1_OPTION:
220         /*
221          * The package count is variable, there are no subpackages.
222          * There are a fixed number of required elements, and a variable
223          * number of optional elements.
224          *
225          * Check if package is at least as large as the minimum required
226          */
227         ExpectedCount = Package->RetInfo3.Count;
228         if (Count < ExpectedCount)
229         {
230             goto PackageTooSmall;
231         }
232 
233         /* Variable number of sub-objects */
234 
235         for (i = 0; i < Count; i++)
236         {
237             if (i < Package->RetInfo3.Count)
238             {
239                 /* These are the required package elements (0, 1, or 2) */
240 
241                 ApCheckObjectType (Predefined->Info.Name, Op,
242                     Package->RetInfo3.ObjectType[i], i);
243             }
244             else
245             {
246                 /* These are the optional package elements */
247 
248                 ApCheckObjectType (Predefined->Info.Name, Op,
249                     Package->RetInfo3.TailObjectType, i);
250             }
251 
252             Op = Op->Asl.Next;
253         }
254         break;
255 
256     case ACPI_PTYPE2_REV_FIXED:
257 
258         /* First element is the (Integer) revision */
259 
260         ApCheckObjectType (Predefined->Info.Name, Op,
261             ACPI_RTYPE_INTEGER, 0);
262 
263         Op = Op->Asl.Next;
264         Count--;
265 
266         /* Examine the subpackages */
267 
268         ApCheckPackageList (Predefined->Info.Name, Op,
269             Package, 1, Count);
270         break;
271 
272     case ACPI_PTYPE2_PKG_COUNT:
273 
274         /* First element is the (Integer) count of subpackages to follow */
275 
276         Status = ApCheckObjectType (Predefined->Info.Name, Op,
277             ACPI_RTYPE_INTEGER, 0);
278 
279         /* We must have an integer count from above (otherwise, use Count) */
280 
281         if (ACPI_SUCCESS (Status))
282         {
283             /*
284              * Count cannot be larger than the parent package length, but
285              * allow it to be smaller. The >= accounts for the Integer above.
286              */
287             ExpectedCount = (UINT32) Op->Asl.Value.Integer;
288             if (ExpectedCount >= Count)
289             {
290                 goto PackageTooSmall;
291             }
292 
293             Count = ExpectedCount;
294         }
295 
296         Op = Op->Asl.Next;
297 
298         /* Examine the subpackages */
299 
300         ApCheckPackageList (Predefined->Info.Name, Op,
301             Package, 1, Count);
302         break;
303 
304     case ACPI_PTYPE2_UUID_PAIR:
305 
306         /* The package contains a variable list of UUID Buffer/Package pairs */
307 
308         /* The length of the package must be even */
309 
310         if (Count & 1)
311         {
312             sprintf (MsgBuffer, "%4.4s: Package length, %d, must be even.",
313                 Predefined->Info.Name, Count);
314 
315             AslError (ASL_ERROR, ASL_MSG_RESERVED_PACKAGE_LENGTH,
316                 ParentOp->Asl.Child, MsgBuffer);
317         }
318 
319         /* Validate the alternating types */
320 
321         for (i = 0; i < Count; ++i)
322         {
323             if (i & 1)
324             {
325                 ApCheckObjectType (Predefined->Info.Name, Op,
326                     Package->RetInfo.ObjectType2, i);
327             }
328             else
329             {
330                 ApCheckObjectType (Predefined->Info.Name, Op,
331                     Package->RetInfo.ObjectType1, i);
332             }
333 
334             Op = Op->Asl.Next;
335         }
336 
337         break;
338 
339     case ACPI_PTYPE2_VAR_VAR:
340 
341         /* Check for minimum size (ints at beginning + 1 subpackage) */
342 
343         ExpectedCount = Package->RetInfo4.Count1 + 1;
344         if (Count < ExpectedCount)
345         {
346             goto PackageTooSmall;
347         }
348 
349         /* Check the non-package elements at beginning of main package */
350 
351         for (i = 0; i < Package->RetInfo4.Count1; ++i)
352         {
353             Status = ApCheckObjectType (Predefined->Info.Name, Op,
354                 Package->RetInfo4.ObjectType1, i);
355             Op = Op->Asl.Next;
356         }
357 
358         /* Examine the variable-length list of subpackages */
359 
360         ApCheckPackageList (Predefined->Info.Name, Op,
361             Package, Package->RetInfo4.Count1, Count);
362 
363         break;
364 
365     case ACPI_PTYPE2:
366     case ACPI_PTYPE2_FIXED:
367     case ACPI_PTYPE2_MIN:
368     case ACPI_PTYPE2_COUNT:
369     case ACPI_PTYPE2_FIX_VAR:
370         /*
371          * These types all return a single Package that consists of a
372          * variable number of subpackages.
373          */
374 
375         /* Examine the subpackages */
376 
377         ApCheckPackageList (Predefined->Info.Name, Op,
378             Package, 0, Count);
379         break;
380 
381     default:
382         return;
383     }
384 
385     return;
386 
387 PackageTooSmall:
388     ApPackageTooSmall (Predefined->Info.Name, ParentOp,
389         Count, ExpectedCount);
390 }
391 
392 
393 /*******************************************************************************
394  *
395  * FUNCTION:    ApCustomPackage
396  *
397  * PARAMETERS:  ParentOp            - Parse op for the package
398  *              Predefined          - Pointer to package-specific info for
399  *                                    the method
400  *
401  * RETURN:      None
402  *
403  * DESCRIPTION: Validate packages that don't fit into the standard model and
404  *              require custom code.
405  *
406  * NOTE: Currently used for the _BIX method only. When needed for two or more
407  * methods, probably a detect/dispatch mechanism will be required.
408  *
409  ******************************************************************************/
410 
411 static void
412 ApCustomPackage (
413     ACPI_PARSE_OBJECT           *ParentOp,
414     const ACPI_PREDEFINED_INFO  *Predefined)
415 {
416     ACPI_PARSE_OBJECT           *Op;
417     UINT32                      Count;
418     UINT32                      ExpectedCount;
419     UINT32                      Version;
420 
421 
422     /* First child is the package length */
423 
424     Op = ParentOp->Asl.Child;
425     Count = (UINT32) Op->Asl.Value.Integer;
426 
427     /* Get the version number, must be Integer */
428 
429     Op = Op->Asl.Next;
430     Version = (UINT32) Op->Asl.Value.Integer;
431     if (Op->Asl.ParseOpcode != PARSEOP_INTEGER)
432     {
433         AslError (ASL_ERROR, ASL_MSG_RESERVED_OPERAND_TYPE, Op, MsgBuffer);
434         return;
435     }
436 
437     /* Validate count (# of elements) */
438 
439     ExpectedCount = 21;         /* Version 1 */
440     if (Version == 0)
441     {
442         ExpectedCount = 20;     /* Version 0 */
443     }
444 
445     if (Count < ExpectedCount)
446     {
447         ApPackageTooSmall (Predefined->Info.Name, ParentOp,
448             Count, ExpectedCount);
449         return;
450     }
451     else if (Count > ExpectedCount)
452     {
453         ApPackageTooLarge (Predefined->Info.Name, ParentOp,
454             Count, ExpectedCount);
455     }
456 
457     /* Validate all elements of the package */
458 
459     Op = ApCheckPackageElements (Predefined->Info.Name, Op,
460         ACPI_RTYPE_INTEGER, 16,
461         ACPI_RTYPE_STRING, 4);
462 
463     /* Version 1 has a single trailing integer */
464 
465     if (Version > 0)
466     {
467         ApCheckPackageElements (Predefined->Info.Name, Op,
468             ACPI_RTYPE_INTEGER, 1, 0, 0);
469     }
470 }
471 
472 
473 /*******************************************************************************
474  *
475  * FUNCTION:    ApCheckPackageElements
476  *
477  * PARAMETERS:  PredefinedName      - Name of the predefined object
478  *              Op                  - Parser op for the package
479  *              Type1               - Object type for first group
480  *              Count1              - Count for first group
481  *              Type2               - Object type for second group
482  *              Count2              - Count for second group
483  *
484  * RETURN:      Next Op peer in the parse tree, after all specified elements
485  *              have been validated. Used for multiple validations (calls
486  *              to this function).
487  *
488  * DESCRIPTION: Validate all elements of a package. Works with packages that
489  *              are defined to contain up to two groups of different object
490  *              types.
491  *
492  ******************************************************************************/
493 
494 static ACPI_PARSE_OBJECT *
495 ApCheckPackageElements (
496     const char              *PredefinedName,
497     ACPI_PARSE_OBJECT       *Op,
498     UINT8                   Type1,
499     UINT32                  Count1,
500     UINT8                   Type2,
501     UINT32                  Count2)
502 {
503     UINT32                  i;
504 
505 
506     /*
507      * Up to two groups of package elements are supported by the data
508      * structure. All elements in each group must be of the same type.
509      * The second group can have a count of zero.
510      *
511      * Aborts check upon a NULL package element, as this means (at compile
512      * time) that the remainder of the package elements are also NULL
513      * (This is the only way to create NULL package elements.)
514      */
515     for (i = 0; (i < Count1) && Op; i++)
516     {
517         ApCheckObjectType (PredefinedName, Op, Type1, i);
518         Op = Op->Asl.Next;
519     }
520 
521     for (i = 0; (i < Count2) && Op; i++)
522     {
523         ApCheckObjectType (PredefinedName, Op, Type2, (i + Count1));
524         Op = Op->Asl.Next;
525     }
526 
527     return (Op);
528 }
529 
530 
531 /*******************************************************************************
532  *
533  * FUNCTION:    ApCheckPackageList
534  *
535  * PARAMETERS:  PredefinedName      - Name of the predefined object
536  *              ParentOp            - Parser op of the parent package
537  *              Package             - Package info for this predefined name
538  *              StartIndex          - Index in parent package where list begins
539  *              ParentCount         - Element count of parent package
540  *
541  * RETURN:      None
542  *
543  * DESCRIPTION: Validate the individual package elements for a predefined name.
544  *              Handles the cases where the predefined name is defined as a
545  *              Package of Packages (subpackages). These are the types:
546  *
547  *              ACPI_PTYPE2
548  *              ACPI_PTYPE2_FIXED
549  *              ACPI_PTYPE2_MIN
550  *              ACPI_PTYPE2_COUNT
551  *              ACPI_PTYPE2_FIX_VAR
552  *              ACPI_PTYPE2_VAR_VAR
553  *
554  ******************************************************************************/
555 
556 static void
557 ApCheckPackageList (
558     const char                  *PredefinedName,
559     ACPI_PARSE_OBJECT           *ParentOp,
560     const ACPI_PREDEFINED_INFO  *Package,
561     UINT32                      StartIndex,
562     UINT32                      ParentCount)
563 {
564     ACPI_PARSE_OBJECT           *SubPackageOp = ParentOp;
565     ACPI_PARSE_OBJECT           *Op;
566     ACPI_STATUS                 Status;
567     UINT32                      Count;
568     UINT32                      ExpectedCount;
569     UINT32                      i;
570     UINT32                      j;
571 
572 
573     /*
574      * Validate each subpackage in the parent Package
575      *
576      * Note: We ignore NULL package elements on the assumption that
577      * they will be initialized by the BIOS or other ASL code.
578      */
579     for (i = 0; (i < ParentCount) && SubPackageOp; i++)
580     {
581         /* Each object in the list must be of type Package */
582 
583         Status = ApCheckObjectType (PredefinedName, SubPackageOp,
584             ACPI_RTYPE_PACKAGE, i + StartIndex);
585         if (ACPI_FAILURE (Status))
586         {
587             goto NextSubpackage;
588         }
589 
590         /* Examine the different types of expected subpackages */
591 
592         Op = SubPackageOp->Asl.Child;
593 
594         /* First child is the package length */
595 
596         Count = (UINT32) Op->Asl.Value.Integer;
597         Op = Op->Asl.Next;
598 
599         /*
600          * Most subpackage must have at least one element, with
601          * only rare exceptions. (_RDI)
602          */
603         if (!Count &&
604             (Package->RetInfo.Type != ACPI_PTYPE2_VAR_VAR))
605         {
606             ApZeroLengthPackage (PredefinedName, SubPackageOp);
607             goto NextSubpackage;
608         }
609 
610         /*
611          * Decode the package type.
612          * PTYPE2 indicates that a "package of packages" is expected for
613          * this name. The various flavors of PTYPE2 indicate the number
614          * and format of the subpackages.
615          */
616         switch (Package->RetInfo.Type)
617         {
618         case ACPI_PTYPE2:
619         case ACPI_PTYPE2_PKG_COUNT:
620         case ACPI_PTYPE2_REV_FIXED:
621 
622             /* Each subpackage has a fixed number of elements */
623 
624             ExpectedCount = Package->RetInfo.Count1 + Package->RetInfo.Count2;
625             if (Count < ExpectedCount)
626             {
627                 ApPackageTooSmall (PredefinedName, SubPackageOp,
628                     Count, ExpectedCount);
629                 break;
630             }
631             if (Count > ExpectedCount)
632             {
633                 ApPackageTooLarge (PredefinedName, SubPackageOp,
634                     Count, ExpectedCount);
635                 break;
636             }
637 
638             ApCheckPackageElements (PredefinedName, Op,
639                 Package->RetInfo.ObjectType1, Package->RetInfo.Count1,
640                 Package->RetInfo.ObjectType2, Package->RetInfo.Count2);
641             break;
642 
643         case ACPI_PTYPE2_FIX_VAR:
644             /*
645              * Each subpackage has a fixed number of elements and an
646              * optional element
647              */
648             ExpectedCount = Package->RetInfo.Count1 + Package->RetInfo.Count2;
649             if (Count < ExpectedCount)
650             {
651                 ApPackageTooSmall (PredefinedName, SubPackageOp,
652                     Count, ExpectedCount);
653                 break;
654             }
655 
656             ApCheckPackageElements (PredefinedName, Op,
657                 Package->RetInfo.ObjectType1, Package->RetInfo.Count1,
658                 Package->RetInfo.ObjectType2,
659                 Count - Package->RetInfo.Count1);
660             break;
661 
662         case ACPI_PTYPE2_VAR_VAR:
663             /*
664              * Must have at least the minimum number elements.
665              * A zero PkgCount means the number of elements is variable.
666              */
667             ExpectedCount = Package->RetInfo4.PkgCount;
668             if (ExpectedCount && (Count < ExpectedCount))
669             {
670                 ApPackageTooSmall (PredefinedName, SubPackageOp,
671                     Count, 1);
672                 break;
673             }
674 
675             ApCheckPackageElements (PredefinedName, Op,
676                 Package->RetInfo4.SubObjectTypes,
677                 Package->RetInfo4.PkgCount,
678                 0, 0);
679             break;
680 
681         case ACPI_PTYPE2_FIXED:
682 
683             /* Each subpackage has a fixed length */
684 
685             ExpectedCount = Package->RetInfo2.Count;
686             if (Count < ExpectedCount)
687             {
688                 ApPackageTooSmall (PredefinedName, SubPackageOp,
689                     Count, ExpectedCount);
690                 break;
691             }
692             if (Count > ExpectedCount)
693             {
694                 ApPackageTooLarge (PredefinedName, SubPackageOp,
695                     Count, ExpectedCount);
696                 break;
697             }
698 
699             /* Check each object/type combination */
700 
701             for (j = 0; j < ExpectedCount; j++)
702             {
703                 ApCheckObjectType (PredefinedName, Op,
704                     Package->RetInfo2.ObjectType[j], j);
705 
706                 Op = Op->Asl.Next;
707             }
708             break;
709 
710         case ACPI_PTYPE2_MIN:
711 
712             /* Each subpackage has a variable but minimum length */
713 
714             ExpectedCount = Package->RetInfo.Count1;
715             if (Count < ExpectedCount)
716             {
717                 ApPackageTooSmall (PredefinedName, SubPackageOp,
718                     Count, ExpectedCount);
719                 break;
720             }
721 
722             /* Check the type of each subpackage element */
723 
724             ApCheckPackageElements (PredefinedName, Op,
725                 Package->RetInfo.ObjectType1, Count, 0, 0);
726             break;
727 
728         case ACPI_PTYPE2_COUNT:
729             /*
730              * First element is the (Integer) count of elements, including
731              * the count field (the ACPI name is NumElements)
732              */
733             Status = ApCheckObjectType (PredefinedName, Op,
734                 ACPI_RTYPE_INTEGER, 0);
735 
736             /* We must have an integer count from above (otherwise, use Count) */
737 
738             if (ACPI_SUCCESS (Status))
739             {
740                 /*
741                  * Make sure package is large enough for the Count and is
742                  * is as large as the minimum size
743                  */
744                 ExpectedCount = (UINT32) Op->Asl.Value.Integer;
745 
746                 if (Count < ExpectedCount)
747                 {
748                     ApPackageTooSmall (PredefinedName, SubPackageOp,
749                         Count, ExpectedCount);
750                     break;
751                 }
752                 else if (Count > ExpectedCount)
753                 {
754                     ApPackageTooLarge (PredefinedName, SubPackageOp,
755                         Count, ExpectedCount);
756                 }
757 
758                 /* Some names of this type have a minimum length */
759 
760                 if (Count < Package->RetInfo.Count1)
761                 {
762                     ExpectedCount = Package->RetInfo.Count1;
763                     ApPackageTooSmall (PredefinedName, SubPackageOp,
764                         Count, ExpectedCount);
765                     break;
766                 }
767 
768                 Count = ExpectedCount;
769             }
770 
771             /* Check the type of each subpackage element */
772 
773             Op = Op->Asl.Next;
774             ApCheckPackageElements (PredefinedName, Op,
775                 Package->RetInfo.ObjectType1, (Count - 1), 0, 0);
776             break;
777 
778         default:
779             break;
780         }
781 
782 NextSubpackage:
783         SubPackageOp = SubPackageOp->Asl.Next;
784     }
785 }
786 
787 
788 /*******************************************************************************
789  *
790  * FUNCTION:    ApPackageTooSmall
791  *
792  * PARAMETERS:  PredefinedName      - Name of the predefined object
793  *              Op                  - Current parser op
794  *              Count               - Actual package element count
795  *              ExpectedCount       - Expected package element count
796  *
797  * RETURN:      None
798  *
799  * DESCRIPTION: Issue error message for a package that is smaller than
800  *              required.
801  *
802  ******************************************************************************/
803 
804 static void
805 ApPackageTooSmall (
806     const char                  *PredefinedName,
807     ACPI_PARSE_OBJECT           *Op,
808     UINT32                      Count,
809     UINT32                      ExpectedCount)
810 {
811 
812     sprintf (MsgBuffer, "%s: length %u, required minimum is %u",
813         PredefinedName, Count, ExpectedCount);
814 
815     AslError (ASL_ERROR, ASL_MSG_RESERVED_PACKAGE_LENGTH, Op, MsgBuffer);
816 }
817 
818 
819 /*******************************************************************************
820  *
821  * FUNCTION:    ApZeroLengthPackage
822  *
823  * PARAMETERS:  PredefinedName      - Name of the predefined object
824  *              Op                  - Current parser op
825  *
826  * RETURN:      None
827  *
828  * DESCRIPTION: Issue error message for a zero-length package (a package that
829  *              is required to have a non-zero length). Variable length
830  *              packages seem to be allowed to have zero length, however.
831  *              Even if not allowed, BIOS code does it.
832  *
833  ******************************************************************************/
834 
835 static void
836 ApZeroLengthPackage (
837     const char                  *PredefinedName,
838     ACPI_PARSE_OBJECT           *Op)
839 {
840 
841     sprintf (MsgBuffer, "%s: length is zero", PredefinedName);
842 
843     AslError (ASL_ERROR, ASL_MSG_RESERVED_PACKAGE_LENGTH, Op, MsgBuffer);
844 }
845 
846 
847 /*******************************************************************************
848  *
849  * FUNCTION:    ApPackageTooLarge
850  *
851  * PARAMETERS:  PredefinedName      - Name of the predefined object
852  *              Op                  - Current parser op
853  *              Count               - Actual package element count
854  *              ExpectedCount       - Expected package element count
855  *
856  * RETURN:      None
857  *
858  * DESCRIPTION: Issue a remark for a package that is larger than expected.
859  *
860  ******************************************************************************/
861 
862 static void
863 ApPackageTooLarge (
864     const char                  *PredefinedName,
865     ACPI_PARSE_OBJECT           *Op,
866     UINT32                      Count,
867     UINT32                      ExpectedCount)
868 {
869 
870     sprintf (MsgBuffer, "%s: length is %u, only %u required",
871         PredefinedName, Count, ExpectedCount);
872 
873     AslError (ASL_REMARK, ASL_MSG_RESERVED_PACKAGE_LENGTH, Op, MsgBuffer);
874 }
875