1274357Sjkim/******************************************************************************
2274357Sjkim *
3274357Sjkim * Module Name: aslprune - Parse tree prune utility
4274357Sjkim *
5274357Sjkim *****************************************************************************/
6274357Sjkim
7274357Sjkim/*
8306536Sjkim * Copyright (C) 2000 - 2016, Intel Corp.
9274357Sjkim * All rights reserved.
10274357Sjkim *
11274357Sjkim * Redistribution and use in source and binary forms, with or without
12274357Sjkim * modification, are permitted provided that the following conditions
13274357Sjkim * are met:
14274357Sjkim * 1. Redistributions of source code must retain the above copyright
15274357Sjkim *    notice, this list of conditions, and the following disclaimer,
16274357Sjkim *    without modification.
17274357Sjkim * 2. Redistributions in binary form must reproduce at minimum a disclaimer
18274357Sjkim *    substantially similar to the "NO WARRANTY" disclaimer below
19274357Sjkim *    ("Disclaimer") and any redistribution must be conditioned upon
20274357Sjkim *    including a substantially similar Disclaimer requirement for further
21274357Sjkim *    binary redistribution.
22274357Sjkim * 3. Neither the names of the above-listed copyright holders nor the names
23274357Sjkim *    of any contributors may be used to endorse or promote products derived
24274357Sjkim *    from this software without specific prior written permission.
25274357Sjkim *
26274357Sjkim * Alternatively, this software may be distributed under the terms of the
27274357Sjkim * GNU General Public License ("GPL") version 2 as published by the Free
28274357Sjkim * Software Foundation.
29274357Sjkim *
30274357Sjkim * NO WARRANTY
31274357Sjkim * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
32274357Sjkim * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
33274357Sjkim * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
34274357Sjkim * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
35274357Sjkim * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
36274357Sjkim * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
37274357Sjkim * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
38274357Sjkim * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
39274357Sjkim * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
40274357Sjkim * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
41274357Sjkim * POSSIBILITY OF SUCH DAMAGES.
42274357Sjkim */
43274357Sjkim
44278970Sjkim#include <contrib/dev/acpica/compiler/aslcompiler.h>
45274357Sjkim#include "aslcompiler.y.h"
46278970Sjkim#include <contrib/dev/acpica/include/acapps.h>
47274357Sjkim
48274357Sjkim#define _COMPONENT          ACPI_COMPILER
49274357Sjkim        ACPI_MODULE_NAME    ("aslprune")
50274357Sjkim
51274357Sjkim
52274357Sjkim/* Local prototypes */
53274357Sjkim
54274357Sjkimstatic ACPI_STATUS
55274357SjkimPrTreePruneWalk (
56274357Sjkim    ACPI_PARSE_OBJECT       *Op,
57274357Sjkim    UINT32                  Level,
58274357Sjkim    void                    *Context);
59274357Sjkim
60274357Sjkimstatic void
61274357SjkimPrPrintObjectAtLevel (
62274357Sjkim    UINT32                  Level,
63274357Sjkim    const char              *ObjectName);
64274357Sjkim
65274357Sjkim
66306536Sjkim/* Structure used for the pruning parse tree walk */
67306536Sjkim
68274357Sjkimtypedef struct acpi_prune_info
69274357Sjkim{
70274357Sjkim    UINT32                  PruneLevel;
71274357Sjkim    UINT16                  ParseOpcode;
72274357Sjkim    UINT16                  Count;
73274357Sjkim
74274357Sjkim} ACPI_PRUNE_INFO;
75274357Sjkim
76274357Sjkim
77274357Sjkim/*******************************************************************************
78274357Sjkim *
79274357Sjkim * FUNCTION:    AslPruneParseTree
80274357Sjkim *
81274357Sjkim * PARAMETERS:  PruneDepth              - Number of levels to prune
82274357Sjkim *              Type                    - Prune type (Device, Method, etc.)
83274357Sjkim *
84274357Sjkim * RETURN:      None
85274357Sjkim *
86274357Sjkim * DESCRIPTION: Prune off one or more levels of the ASL parse tree
87274357Sjkim *
88274357Sjkim ******************************************************************************/
89274357Sjkim
90274357Sjkimvoid
91274357SjkimAslPruneParseTree (
92274357Sjkim    UINT32                  PruneDepth,
93274357Sjkim    UINT32                  Type)
94274357Sjkim{
95274357Sjkim    ACPI_PRUNE_INFO         PruneObj;
96274357Sjkim
97274357Sjkim
98274357Sjkim    PruneObj.PruneLevel = PruneDepth;
99274357Sjkim    PruneObj.Count = 0;
100274357Sjkim
101274357Sjkim    switch (Type)
102274357Sjkim    {
103274357Sjkim    case 0:
104274357Sjkim        PruneObj.ParseOpcode = (UINT16) PARSEOP_DEVICE;
105274357Sjkim        break;
106274357Sjkim
107274357Sjkim    case 1:
108274357Sjkim        PruneObj.ParseOpcode = (UINT16) PARSEOP_METHOD;
109274357Sjkim        break;
110274357Sjkim
111274357Sjkim    case 2:
112274357Sjkim        PruneObj.ParseOpcode = (UINT16) PARSEOP_IF;
113274357Sjkim        break;
114274357Sjkim
115274357Sjkim    default:
116274357Sjkim        AcpiOsPrintf ("Unsupported type: %u\n", Type);
117274357Sjkim        return;
118274357Sjkim    }
119274357Sjkim
120274357Sjkim    AcpiOsPrintf ("Pruning parse tree, from depth %u\n",
121274357Sjkim        PruneDepth);
122274357Sjkim
123274357Sjkim    AcpiOsPrintf ("\nRemoving Objects:\n");
124274357Sjkim
125306536Sjkim    TrWalkParseTree (Gbl_ParseTreeRoot, ASL_WALK_VISIT_DOWNWARD,
126274357Sjkim        PrTreePruneWalk, NULL, ACPI_CAST_PTR (void, &PruneObj));
127274357Sjkim
128274357Sjkim    AcpiOsPrintf ("\n%u Total Objects Removed\n", PruneObj.Count);
129274357Sjkim}
130274357Sjkim
131274357Sjkim
132274357Sjkim/*******************************************************************************
133274357Sjkim *
134274357Sjkim * FUNCTION:    PrPrintObjectAtLevel
135274357Sjkim *
136274357Sjkim * PARAMETERS:  Level                   - Current nesting level
137274357Sjkim *              ObjectName              - ACPI name for the object
138274357Sjkim *
139274357Sjkim * RETURN:      None
140274357Sjkim *
141274357Sjkim * DESCRIPTION: Print object name with indent
142274357Sjkim *
143274357Sjkim ******************************************************************************/
144274357Sjkim
145274357Sjkimstatic void
146274357SjkimPrPrintObjectAtLevel (
147274357Sjkim    UINT32                  Level,
148274357Sjkim    const char              *ObjectName)
149274357Sjkim{
150274357Sjkim    UINT32                  i;
151274357Sjkim
152274357Sjkim
153274357Sjkim    for (i = 0; i < Level; i++)
154274357Sjkim    {
155274357Sjkim        AcpiOsPrintf ("  ");
156274357Sjkim    }
157274357Sjkim
158274357Sjkim    AcpiOsPrintf ("[%s] at Level [%u]\n", ObjectName, Level);
159274357Sjkim}
160274357Sjkim
161274357Sjkim
162274357Sjkim/*******************************************************************************
163274357Sjkim *
164274357Sjkim * FUNCTION:    PrTreePruneWalk
165274357Sjkim *
166274357Sjkim * PARAMETERS:  Parse tree walk callback
167274357Sjkim *
168274357Sjkim * RETURN:      Status
169274357Sjkim *
170274357Sjkim * DESCRIPTION: Prune off one or more levels of the ASL parse tree
171274357Sjkim *
172274357Sjkim * Current objects that can be pruned are: Devices, Methods, and If/Else
173274357Sjkim * blocks.
174274357Sjkim *
175274357Sjkim ******************************************************************************/
176274357Sjkim
177274357Sjkimstatic ACPI_STATUS
178274357SjkimPrTreePruneWalk (
179274357Sjkim    ACPI_PARSE_OBJECT       *Op,
180274357Sjkim    UINT32                  Level,
181274357Sjkim    void                    *Context)
182274357Sjkim{
183274357Sjkim    ACPI_PRUNE_INFO         *PruneObj = (ACPI_PRUNE_INFO *) Context;
184274357Sjkim
185274357Sjkim
186274357Sjkim    /* We only care about objects below the Prune Level threshold */
187274357Sjkim
188274357Sjkim    if (Level <= PruneObj->PruneLevel)
189274357Sjkim    {
190274357Sjkim        return (AE_OK);
191274357Sjkim    }
192274357Sjkim
193274357Sjkim    if ((Op->Asl.ParseOpcode != PruneObj->ParseOpcode) &&
194274357Sjkim       !(Op->Asl.ParseOpcode == PARSEOP_ELSE &&
195274357Sjkim             PruneObj->ParseOpcode == PARSEOP_IF))
196274357Sjkim    {
197274357Sjkim        return (AE_OK);
198274357Sjkim    }
199274357Sjkim
200274357Sjkim    switch (Op->Asl.ParseOpcode)
201274357Sjkim    {
202274357Sjkim    case PARSEOP_METHOD:
203274357Sjkim
204274357Sjkim        AcpiOsPrintf ("Method");
205274357Sjkim        PrPrintObjectAtLevel (Level, Op->Asl.Child->Asl.Value.Name);
206274357Sjkim        Op->Asl.Child->Asl.Next->Asl.Next->Asl.Next->Asl.Next->Asl.Next->Asl.Next = NULL;
207274357Sjkim        PruneObj->Count++;
208274357Sjkim        break;
209274357Sjkim
210274357Sjkim    case PARSEOP_DEVICE:
211274357Sjkim
212274357Sjkim        AcpiOsPrintf ("Device");
213274357Sjkim        PrPrintObjectAtLevel (Level, Op->Asl.Child->Asl.Value.Name);
214274357Sjkim        Op->Asl.Child->Asl.Next = NULL;
215274357Sjkim        PruneObj->Count++;
216274357Sjkim        break;
217274357Sjkim
218274357Sjkim    case PARSEOP_IF:
219274357Sjkim    case PARSEOP_ELSE:
220274357Sjkim
221274357Sjkim        if (Op->Asl.ParseOpcode == PARSEOP_ELSE)
222274357Sjkim        {
223274357Sjkim            PrPrintObjectAtLevel(Level, "Else");
224274357Sjkim            Op->Asl.Child = NULL;
225274357Sjkim        }
226274357Sjkim        else
227274357Sjkim        {
228274357Sjkim            PrPrintObjectAtLevel(Level, "If");
229274357Sjkim            Op->Asl.Child->Asl.Next = NULL;
230274357Sjkim        }
231274357Sjkim
232274357Sjkim        PruneObj->Count++;
233274357Sjkim        break;
234274357Sjkim
235274357Sjkim    default:
236274357Sjkim
237274357Sjkim        break;
238274357Sjkim    }
239274357Sjkim
240274357Sjkim    return (AE_OK);
241274357Sjkim}
242