Path: blob/main/sys/contrib/dev/acpica/compiler/aslopcodes.c
48371 views
/******************************************************************************1*2* Module Name: aslopcode - AML opcode generation3*4*****************************************************************************/56/******************************************************************************7*8* 1. Copyright Notice9*10* Some or all of this work - Copyright (c) 1999 - 2025, Intel Corp.11* All rights reserved.12*13* 2. License14*15* 2.1. This is your license from Intel Corp. under its intellectual property16* rights. You may have additional license terms from the party that provided17* you this software, covering your right to use that party's intellectual18* property rights.19*20* 2.2. Intel grants, free of charge, to any person ("Licensee") obtaining a21* copy of the source code appearing in this file ("Covered Code") an22* irrevocable, perpetual, worldwide license under Intel's copyrights in the23* base code distributed originally by Intel ("Original Intel Code") to copy,24* make derivatives, distribute, use and display any portion of the Covered25* Code in any form, with the right to sublicense such rights; and26*27* 2.3. Intel grants Licensee a non-exclusive and non-transferable patent28* license (with the right to sublicense), under only those claims of Intel29* patents that are infringed by the Original Intel Code, to make, use, sell,30* offer to sell, and import the Covered Code and derivative works thereof31* solely to the minimum extent necessary to exercise the above copyright32* license, and in no event shall the patent license extend to any additions33* to or modifications of the Original Intel Code. No other license or right34* is granted directly or by implication, estoppel or otherwise;35*36* The above copyright and patent license is granted only if the following37* conditions are met:38*39* 3. Conditions40*41* 3.1. Redistribution of Source with Rights to Further Distribute Source.42* Redistribution of source code of any substantial portion of the Covered43* Code or modification with rights to further distribute source must include44* the above Copyright Notice, the above License, this list of Conditions,45* and the following Disclaimer and Export Compliance provision. In addition,46* Licensee must cause all Covered Code to which Licensee contributes to47* contain a file documenting the changes Licensee made to create that Covered48* Code and the date of any change. Licensee must include in that file the49* documentation of any changes made by any predecessor Licensee. Licensee50* must include a prominent statement that the modification is derived,51* directly or indirectly, from Original Intel Code.52*53* 3.2. Redistribution of Source with no Rights to Further Distribute Source.54* Redistribution of source code of any substantial portion of the Covered55* Code or modification without rights to further distribute source must56* include the following Disclaimer and Export Compliance provision in the57* documentation and/or other materials provided with distribution. In58* addition, Licensee may not authorize further sublicense of source of any59* portion of the Covered Code, and must include terms to the effect that the60* license from Licensee to its licensee is limited to the intellectual61* property embodied in the software Licensee provides to its licensee, and62* not to intellectual property embodied in modifications its licensee may63* make.64*65* 3.3. Redistribution of Executable. Redistribution in executable form of any66* substantial portion of the Covered Code or modification must reproduce the67* above Copyright Notice, and the following Disclaimer and Export Compliance68* provision in the documentation and/or other materials provided with the69* distribution.70*71* 3.4. Intel retains all right, title, and interest in and to the Original72* Intel Code.73*74* 3.5. Neither the name Intel nor any other trademark owned or controlled by75* Intel shall be used in advertising or otherwise to promote the sale, use or76* other dealings in products derived from or relating to the Covered Code77* without prior written authorization from Intel.78*79* 4. Disclaimer and Export Compliance80*81* 4.1. INTEL MAKES NO WARRANTY OF ANY KIND REGARDING ANY SOFTWARE PROVIDED82* HERE. ANY SOFTWARE ORIGINATING FROM INTEL OR DERIVED FROM INTEL SOFTWARE83* IS PROVIDED "AS IS," AND INTEL WILL NOT PROVIDE ANY SUPPORT, ASSISTANCE,84* INSTALLATION, TRAINING OR OTHER SERVICES. INTEL WILL NOT PROVIDE ANY85* UPDATES, ENHANCEMENTS OR EXTENSIONS. INTEL SPECIFICALLY DISCLAIMS ANY86* IMPLIED WARRANTIES OF MERCHANTABILITY, NONINFRINGEMENT AND FITNESS FOR A87* PARTICULAR PURPOSE.88*89* 4.2. IN NO EVENT SHALL INTEL HAVE ANY LIABILITY TO LICENSEE, ITS LICENSEES90* OR ANY OTHER THIRD PARTY, FOR ANY LOST PROFITS, LOST DATA, LOSS OF USE OR91* COSTS OF PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, OR FOR ANY INDIRECT,92* SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THIS AGREEMENT, UNDER ANY93* CAUSE OF ACTION OR THEORY OF LIABILITY, AND IRRESPECTIVE OF WHETHER INTEL94* HAS ADVANCE NOTICE OF THE POSSIBILITY OF SUCH DAMAGES. THESE LIMITATIONS95* SHALL APPLY NOTWITHSTANDING THE FAILURE OF THE ESSENTIAL PURPOSE OF ANY96* LIMITED REMEDY.97*98* 4.3. Licensee shall not export, either directly or indirectly, any of this99* software or system incorporating such software without first obtaining any100* required license or other approval from the U. S. Department of Commerce or101* any other agency or department of the United States Government. In the102* event Licensee exports any such software from the United States or103* re-exports any such software from a foreign destination, Licensee shall104* ensure that the distribution and export/re-export of the software is in105* compliance with all laws, regulations, orders, or other restrictions of the106* U.S. Export Administration Regulations. Licensee agrees that neither it nor107* any of its subsidiaries will export/re-export any technical data, process,108* software, or service, directly or indirectly, to any country for which the109* United States government or any agency thereof requires an export license,110* other governmental approval, or letter of assurance, without first obtaining111* such license, approval or letter.112*113*****************************************************************************114*115* Alternatively, you may choose to be licensed under the terms of the116* following license:117*118* Redistribution and use in source and binary forms, with or without119* modification, are permitted provided that the following conditions120* are met:121* 1. Redistributions of source code must retain the above copyright122* notice, this list of conditions, and the following disclaimer,123* without modification.124* 2. Redistributions in binary form must reproduce at minimum a disclaimer125* substantially similar to the "NO WARRANTY" disclaimer below126* ("Disclaimer") and any redistribution must be conditioned upon127* including a substantially similar Disclaimer requirement for further128* binary redistribution.129* 3. Neither the names of the above-listed copyright holders nor the names130* of any contributors may be used to endorse or promote products derived131* from this software without specific prior written permission.132*133* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS134* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT135* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR136* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT137* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,138* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT139* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,140* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY141* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT142* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE143* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.144*145* Alternatively, you may choose to be licensed under the terms of the146* GNU General Public License ("GPL") version 2 as published by the Free147* Software Foundation.148*149*****************************************************************************/150151#include <contrib/dev/acpica/compiler/aslcompiler.h>152#include "aslcompiler.y.h"153#include <contrib/dev/acpica/include/amlcode.h>154155#define _COMPONENT ACPI_COMPILER156ACPI_MODULE_NAME ("aslopcodes")157158159/* Local prototypes */160161static void162OpcDoAccessAs (163ACPI_PARSE_OBJECT *Op);164165static void166OpcDoConnection (167ACPI_PARSE_OBJECT *Op);168169static void170OpcDoUnicode (171ACPI_PARSE_OBJECT *Op);172173static void174OpcDoEisaId (175ACPI_PARSE_OBJECT *Op);176177static void178OpcDoUuId (179ACPI_PARSE_OBJECT *Op);180181182/*******************************************************************************183*184* FUNCTION: OpcAmlOpcodeUpdateWalk185*186* PARAMETERS: ASL_WALK_CALLBACK187*188* RETURN: Status189*190* DESCRIPTION: Opcode update walk, ascending callback191*192******************************************************************************/193194ACPI_STATUS195OpcAmlOpcodeUpdateWalk (196ACPI_PARSE_OBJECT *Op,197UINT32 Level,198void *Context)199{200201/*202* Handle the Package() case where the actual opcode cannot be determined203* until the PackageLength operand has been folded and minimized.204* (PackageOp versus VarPackageOp)205*206* This is (as of ACPI 3.0) the only case where the AML opcode can change207* based upon the value of a parameter.208*209* The parser always inserts a VarPackage opcode, which can possibly be210* optimized to a Package opcode.211*/212if (Op->Asl.ParseOpcode == PARSEOP_VAR_PACKAGE)213{214OpnDoPackage (Op);215}216217return (AE_OK);218}219220221/*******************************************************************************222*223* FUNCTION: OpcAmlOpcodeWalk224*225* PARAMETERS: ASL_WALK_CALLBACK226*227* RETURN: Status228*229* DESCRIPTION: Parse tree walk to generate both the AML opcodes and the AML230* operands.231*232******************************************************************************/233234ACPI_STATUS235OpcAmlOpcodeWalk (236ACPI_PARSE_OBJECT *Op,237UINT32 Level,238void *Context)239{240241AslGbl_TotalParseNodes++;242243OpcGenerateAmlOpcode (Op);244OpnGenerateAmlOperands (Op);245return (AE_OK);246}247248249/*******************************************************************************250*251* FUNCTION: OpcGetIntegerWidth252*253* PARAMETERS: Op - DEFINITION BLOCK op254*255* RETURN: none256*257* DESCRIPTION: Extract integer width from the table revision258*259******************************************************************************/260261void262OpcGetIntegerWidth (263ACPI_PARSE_OBJECT *Op)264{265ACPI_PARSE_OBJECT *Child;266267268if (!Op)269{270return;271}272273if (AslGbl_RevisionOverride)274{275AcpiUtSetIntegerWidth (AslGbl_RevisionOverride);276}277else278{279Child = Op->Asl.Child;280Child = Child->Asl.Next;281Child = Child->Asl.Next;282283/* Use the revision to set the integer width */284285AcpiUtSetIntegerWidth ((UINT8) Child->Asl.Value.Integer);286}287}288289290/*******************************************************************************291*292* FUNCTION: OpcSetOptimalIntegerSize293*294* PARAMETERS: Op - A parse tree node295*296* RETURN: Integer width, in bytes. Also sets the node AML opcode to the297* optimal integer AML prefix opcode.298*299* DESCRIPTION: Determine the optimal AML encoding of an integer. All leading300* zeros can be truncated to squeeze the integer into the301* minimal number of AML bytes.302*303******************************************************************************/304305UINT32306OpcSetOptimalIntegerSize (307ACPI_PARSE_OBJECT *Op)308{309310#if 0311/*312* TBD: - we don't want to optimize integers in the block header, but the313* code below does not work correctly.314*/315if (Op->Asl.Parent &&316Op->Asl.Parent->Asl.Parent &&317(Op->Asl.Parent->Asl.Parent->Asl.ParseOpcode == PARSEOP_DEFINITION_BLOCK))318{319return (0);320}321#endif322323/*324* Check for the special AML integers first - Zero, One, Ones.325* These are single-byte opcodes that are the smallest possible326* representation of an integer.327*328* This optimization is optional.329*/330if (AslGbl_IntegerOptimizationFlag)331{332switch (Op->Asl.Value.Integer)333{334case 0:335336Op->Asl.AmlOpcode = AML_ZERO_OP;337AslError (ASL_OPTIMIZATION, ASL_MSG_INTEGER_OPTIMIZATION,338Op, "Zero");339return (1);340341case 1:342343Op->Asl.AmlOpcode = AML_ONE_OP;344AslError (ASL_OPTIMIZATION, ASL_MSG_INTEGER_OPTIMIZATION,345Op, "One");346return (1);347348case ACPI_UINT32_MAX:349350/* Check for table integer width (32 or 64) */351352if (AcpiGbl_IntegerByteWidth == 4)353{354Op->Asl.AmlOpcode = AML_ONES_OP;355AslError (ASL_OPTIMIZATION, ASL_MSG_INTEGER_OPTIMIZATION,356Op, "Ones");357return (1);358}359break;360361case ACPI_UINT64_MAX:362363/* Check for table integer width (32 or 64) */364365if (AcpiGbl_IntegerByteWidth == 8)366{367Op->Asl.AmlOpcode = AML_ONES_OP;368AslError (ASL_OPTIMIZATION, ASL_MSG_INTEGER_OPTIMIZATION,369Op, "Ones");370return (1);371}372break;373374default:375376break;377}378}379380/* Find the best fit using the various AML integer prefixes */381382if (Op->Asl.Value.Integer <= ACPI_UINT8_MAX)383{384Op->Asl.AmlOpcode = AML_BYTE_OP;385return (1);386}387388if (Op->Asl.Value.Integer <= ACPI_UINT16_MAX)389{390Op->Asl.AmlOpcode = AML_WORD_OP;391return (2);392}393394if (Op->Asl.Value.Integer <= ACPI_UINT32_MAX)395{396Op->Asl.AmlOpcode = AML_DWORD_OP;397return (4);398}399else /* 64-bit integer */400{401if (AcpiGbl_IntegerByteWidth == 4)402{403AslError (ASL_WARNING, ASL_MSG_INTEGER_LENGTH,404Op, NULL);405406if (!AslGbl_IgnoreErrors)407{408/* Truncate the integer to 32-bit */409410Op->Asl.Value.Integer &= ACPI_UINT32_MAX;411412/* Now set the optimal integer size */413414return (OpcSetOptimalIntegerSize (Op));415}416}417418Op->Asl.AmlOpcode = AML_QWORD_OP;419return (8);420}421}422423424/*******************************************************************************425*426* FUNCTION: OpcDoAccessAs427*428* PARAMETERS: Op - Parse node429*430* RETURN: None431*432* DESCRIPTION: Implement the ACCESS_AS ASL keyword.433*434******************************************************************************/435436static void437OpcDoAccessAs (438ACPI_PARSE_OBJECT *Op)439{440ACPI_PARSE_OBJECT *TypeOp;441ACPI_PARSE_OBJECT *AttribOp;442ACPI_PARSE_OBJECT *LengthOp;443UINT8 Attribute;444445446Op->Asl.AmlOpcodeLength = 1;447TypeOp = Op->Asl.Child;448449/* First child is the access type */450451TypeOp->Asl.AmlOpcode = AML_RAW_DATA_BYTE;452TypeOp->Asl.ParseOpcode = PARSEOP_RAW_DATA;453454/* Second child is the optional access attribute */455456AttribOp = TypeOp->Asl.Next;457if (AttribOp->Asl.ParseOpcode == PARSEOP_DEFAULT_ARG)458{459AttribOp->Asl.Value.Integer = 0;460}461462AttribOp->Asl.AmlOpcode = AML_RAW_DATA_BYTE;463AttribOp->Asl.ParseOpcode = PARSEOP_RAW_DATA;464465/* Only a few AccessAttributes support AccessLength */466467Attribute = (UINT8) AttribOp->Asl.Value.Integer;468if ((Attribute != AML_FIELD_ATTRIB_BYTES) &&469(Attribute != AML_FIELD_ATTRIB_RAW_BYTES) &&470(Attribute != AML_FIELD_ATTRIB_RAW_PROCESS_BYTES))471{472return;473}474475Op->Asl.AmlOpcode = AML_FIELD_EXT_ACCESS_OP;476477/*478* Child of Attributes is the AccessLength (required for Multibyte,479* RawBytes, RawProcess.)480*/481LengthOp = AttribOp->Asl.Child;482if (!LengthOp)483{484return;485}486487/* TBD: probably can remove */488489if (LengthOp->Asl.ParseOpcode == PARSEOP_DEFAULT_ARG)490{491LengthOp->Asl.Value.Integer = 16;492}493494LengthOp->Asl.AmlOpcode = AML_RAW_DATA_BYTE;495LengthOp->Asl.ParseOpcode = PARSEOP_RAW_DATA;496}497498499/*******************************************************************************500*501* FUNCTION: OpcDoConnection502*503* PARAMETERS: Op - Parse node504*505* RETURN: None506*507* DESCRIPTION: Implement the Connection ASL keyword.508*509******************************************************************************/510511static void512OpcDoConnection (513ACPI_PARSE_OBJECT *Op)514{515ASL_RESOURCE_NODE *Rnode;516ACPI_PARSE_OBJECT *BufferOp;517ACPI_PARSE_OBJECT *BufferLengthOp;518ACPI_PARSE_OBJECT *BufferDataOp;519ASL_RESOURCE_INFO Info;520UINT8 State;521522523Op->Asl.AmlOpcodeLength = 1;524525if (Op->Asl.Child->Asl.AmlOpcode == AML_INT_NAMEPATH_OP)526{527return;528}529530BufferOp = Op->Asl.Child;531BufferLengthOp = BufferOp->Asl.Child;532BufferDataOp = BufferLengthOp->Asl.Next;533534Info.DescriptorTypeOp = BufferDataOp->Asl.Next;535Info.CurrentByteOffset = 0;536State = ACPI_RSTATE_NORMAL;537Rnode = RsDoOneResourceDescriptor (&Info, &State);538if (!Rnode)539{540return; /* error */541}542543/*544* Transform the nodes into the following545*546* Op -> AML_BUFFER_OP547* First Child -> BufferLength548* Second Child -> Descriptor Buffer (raw byte data)549*/550BufferOp->Asl.ParseOpcode = PARSEOP_BUFFER;551BufferOp->Asl.AmlOpcode = AML_BUFFER_OP;552BufferOp->Asl.CompileFlags = OP_AML_PACKAGE | OP_IS_RESOURCE_DESC;553UtSetParseOpName (BufferOp);554555BufferLengthOp->Asl.ParseOpcode = PARSEOP_INTEGER;556BufferLengthOp->Asl.Value.Integer = Rnode->BufferLength;557(void) OpcSetOptimalIntegerSize (BufferLengthOp);558UtSetParseOpName (BufferLengthOp);559560BufferDataOp->Asl.ParseOpcode = PARSEOP_RAW_DATA;561BufferDataOp->Asl.AmlOpcode = AML_RAW_DATA_CHAIN;562BufferDataOp->Asl.AmlOpcodeLength = 0;563BufferDataOp->Asl.AmlLength = Rnode->BufferLength;564BufferDataOp->Asl.Value.Buffer = (UINT8 *) Rnode;565UtSetParseOpName (BufferDataOp);566}567568569/*******************************************************************************570*571* FUNCTION: OpcDoUnicode572*573* PARAMETERS: Op - Parse node574*575* RETURN: None576*577* DESCRIPTION: Implement the UNICODE ASL "macro". Convert the input string578* to a unicode buffer. There is no Unicode AML opcode.579*580* Note: The Unicode string is 16 bits per character, no leading signature,581* with a 16-bit terminating NULL.582*583******************************************************************************/584585static void586OpcDoUnicode (587ACPI_PARSE_OBJECT *Op)588{589ACPI_PARSE_OBJECT *InitializerOp;590UINT32 Length;591UINT32 Count;592UINT32 i;593UINT8 *AsciiString;594UINT16 *UnicodeString;595ACPI_PARSE_OBJECT *BufferLengthOp;596597598/* Change op into a buffer object */599600Op->Asl.CompileFlags &= ~OP_COMPILE_TIME_CONST;601Op->Asl.ParseOpcode = PARSEOP_BUFFER;602UtSetParseOpName (Op);603604/* Buffer Length is first, followed by the string */605606BufferLengthOp = Op->Asl.Child;607InitializerOp = BufferLengthOp->Asl.Next;608609AsciiString = (UINT8 *) InitializerOp->Asl.Value.String;610611/* Create a new buffer for the Unicode string */612613Count = strlen (InitializerOp->Asl.Value.String) + 1;614Length = Count * sizeof (UINT16);615UnicodeString = UtLocalCalloc (Length);616617/* Convert to Unicode string (including null terminator) */618619for (i = 0; i < Count; i++)620{621UnicodeString[i] = (UINT16) AsciiString[i];622}623624/*625* Just set the buffer size node to be the buffer length, regardless626* of whether it was previously an integer or a default_arg placeholder627*/628BufferLengthOp->Asl.ParseOpcode = PARSEOP_INTEGER;629BufferLengthOp->Asl.AmlOpcode = AML_DWORD_OP;630BufferLengthOp->Asl.Value.Integer = Length;631UtSetParseOpName (BufferLengthOp);632633(void) OpcSetOptimalIntegerSize (BufferLengthOp);634635/* The Unicode string is a raw data buffer */636637InitializerOp->Asl.Value.Buffer = (UINT8 *) UnicodeString;638InitializerOp->Asl.AmlOpcode = AML_RAW_DATA_BUFFER;639InitializerOp->Asl.AmlLength = Length;640InitializerOp->Asl.ParseOpcode = PARSEOP_RAW_DATA;641InitializerOp->Asl.Child = NULL;642UtSetParseOpName (InitializerOp);643}644645646/*******************************************************************************647*648* FUNCTION: OpcDoEisaId649*650* PARAMETERS: Op - Parse node651*652* RETURN: None653*654* DESCRIPTION: Convert a string EISA ID to numeric representation. See the655* Pnp BIOS Specification for details. Here is an excerpt:656*657* A seven character ASCII representation of the product658* identifier compressed into a 32-bit identifier. The seven659* character ID consists of a three character manufacturer code,660* a three character hexadecimal product identifier, and a one661* character hexadecimal revision number. The manufacturer code662* is a 3 uppercase character code that is compressed into 3 5-bit663* values as follows:664* 1) Find hex ASCII value for each letter665* 2) Subtract 40h from each ASCII value666* 3) Retain 5 least significant bits for each letter by667* discarding upper 3 bits because they are always 0.668* 4) Compressed code = concatenate 0 and the 3 5-bit values669*670* The format of the compressed product identifier is as follows:671* Byte 0: Bit 7 - Reserved (0)672* Bits 6-2: - 1st character of compressed mfg code673* Bits 1-0 - Upper 2 bits of 2nd character of mfg code674* Byte 1: Bits 7-5 - Lower 3 bits of 2nd character of mfg code675* Bits 4-0 - 3rd character of mfg code676* Byte 2: Bits 7-4 - 1st hex digit of product number677* Bits 3-0 - 2nd hex digit of product number678* Byte 3: Bits 7-4 - 3rd hex digit of product number679* Bits 3-0 - Hex digit of the revision number680*681******************************************************************************/682683static void684OpcDoEisaId (685ACPI_PARSE_OBJECT *Op)686{687UINT32 EisaId = 0;688UINT32 BigEndianId;689char *InString;690ACPI_STATUS Status = AE_OK;691UINT32 i;692693694InString = (char *) Op->Asl.Value.String;695696/*697* The EISAID string must be exactly 7 characters and of the form698* "UUUXXXX" -- 3 uppercase letters and 4 hex digits (e.g., "PNP0001")699*/700if (strlen (InString) != 7)701{702Status = AE_BAD_PARAMETER;703}704else705{706/* Check all 7 characters for correct format */707708for (i = 0; i < 7; i++)709{710/* First 3 characters must be uppercase letters */711712if (i < 3)713{714if (!isupper ((int) InString[i]))715{716Status = AE_BAD_PARAMETER;717}718}719720/* Last 4 characters must be hex digits */721722else if (!isxdigit ((int) InString[i]))723{724Status = AE_BAD_PARAMETER;725}726}727}728729if (ACPI_FAILURE (Status))730{731AslError (ASL_ERROR, ASL_MSG_INVALID_EISAID, Op, Op->Asl.Value.String);732}733else734{735/* Create ID big-endian first (bits are contiguous) */736737BigEndianId =738(UINT32) ((UINT8) (InString[0] - 0x40)) << 26 |739(UINT32) ((UINT8) (InString[1] - 0x40)) << 21 |740(UINT32) ((UINT8) (InString[2] - 0x40)) << 16 |741742(AcpiUtAsciiCharToHex (InString[3])) << 12 |743(AcpiUtAsciiCharToHex (InString[4])) << 8 |744(AcpiUtAsciiCharToHex (InString[5])) << 4 |745AcpiUtAsciiCharToHex (InString[6]);746747/* Swap to little-endian to get final ID (see function header) */748749EisaId = AcpiUtDwordByteSwap (BigEndianId);750}751752/*753* Morph the Op into an integer, regardless of whether there754* was an error in the EISAID string755*/756Op->Asl.Value.Integer = EisaId;757758Op->Asl.CompileFlags &= ~OP_COMPILE_TIME_CONST;759Op->Asl.ParseOpcode = PARSEOP_INTEGER;760(void) OpcSetOptimalIntegerSize (Op);761762/* Op is now an integer */763764UtSetParseOpName (Op);765}766767768/*******************************************************************************769*770* FUNCTION: OpcDoUuId771*772* PARAMETERS: Op - Parse node773*774* RETURN: None775*776* DESCRIPTION: Convert UUID string to 16-byte buffer777*778******************************************************************************/779780static void781OpcDoUuId (782ACPI_PARSE_OBJECT *Op)783{784char *InString;785UINT8 *Buffer;786ACPI_STATUS Status = AE_OK;787ACPI_PARSE_OBJECT *NewOp;788789790InString = ACPI_CAST_PTR (char, Op->Asl.Value.String);791Buffer = UtLocalCalloc (16);792793Status = AuValidateUuid (InString);794if (ACPI_FAILURE (Status))795{796AslError (ASL_ERROR, ASL_MSG_INVALID_UUID, Op, Op->Asl.Value.String);797}798else799{800/* Convert UUID string to a buffer, check for a known UUID */801802AcpiUtConvertStringToUuid (InString, Buffer);803if (!AcpiAhMatchUuid (Buffer))804{805AslError (ASL_REMARK, ASL_MSG_UUID_NOT_FOUND, Op, NULL);806}807}808809/* Change Op to a Buffer */810811Op->Asl.ParseOpcode = PARSEOP_BUFFER;812Op->Common.AmlOpcode = AML_BUFFER_OP;813814/* Disable further optimization */815816Op->Asl.CompileFlags &= ~OP_COMPILE_TIME_CONST;817UtSetParseOpName (Op);818819/* Child node is the buffer length */820821NewOp = TrAllocateOp (PARSEOP_INTEGER);822823NewOp->Asl.AmlOpcode = AML_BYTE_OP;824NewOp->Asl.Value.Integer = 16;825NewOp->Asl.Parent = Op;826827Op->Asl.Child = NewOp;828Op = NewOp;829830/* Peer to the child is the raw buffer data */831832NewOp = TrAllocateOp (PARSEOP_RAW_DATA);833NewOp->Asl.AmlOpcode = AML_RAW_DATA_BUFFER;834NewOp->Asl.AmlLength = 16;835NewOp->Asl.Value.String = ACPI_CAST_PTR (char, Buffer);836NewOp->Asl.Parent = Op->Asl.Parent;837838Op->Asl.Next = NewOp;839}840841842/*******************************************************************************843*844* FUNCTION: OpcGenerateAmlOpcode845*846* PARAMETERS: Op - Parse node847*848* RETURN: None849*850* DESCRIPTION: Generate the AML opcode associated with the node and its851* parse (lex/flex) keyword opcode. Essentially implements852* a mapping between the parse opcodes and the actual AML opcodes.853*854******************************************************************************/855856void857OpcGenerateAmlOpcode (858ACPI_PARSE_OBJECT *Op)859{860UINT16 Index;861862863Index = (UINT16) (Op->Asl.ParseOpcode - ASL_PARSE_OPCODE_BASE);864865Op->Asl.AmlOpcode = AslKeywordMapping[Index].AmlOpcode;866Op->Asl.AcpiBtype = AslKeywordMapping[Index].AcpiBtype;867Op->Asl.CompileFlags |= AslKeywordMapping[Index].Flags;868869if (!Op->Asl.Value.Integer)870{871Op->Asl.Value.Integer = AslKeywordMapping[Index].Value;872}873874/* Special handling for some opcodes */875876switch (Op->Asl.ParseOpcode)877{878case PARSEOP_INTEGER:879/*880* Set the opcode based on the size of the integer881*/882(void) OpcSetOptimalIntegerSize (Op);883break;884885case PARSEOP_OFFSET:886887Op->Asl.AmlOpcodeLength = 1;888break;889890case PARSEOP_ACCESSAS:891892OpcDoAccessAs (Op);893break;894895case PARSEOP_CONNECTION:896897OpcDoConnection (Op);898break;899900case PARSEOP_EISAID:901902OpcDoEisaId (Op);903break;904905case PARSEOP_PRINTF:906907OpcDoPrintf (Op);908break;909910case PARSEOP_FPRINTF:911912OpcDoFprintf (Op);913break;914915case PARSEOP_TOPLD:916917OpcDoPld (Op);918break;919920case PARSEOP_TOUUID:921922OpcDoUuId (Op);923break;924925case PARSEOP_UNICODE:926927OpcDoUnicode (Op);928break;929930case PARSEOP_INCLUDE:931932AslGbl_HasIncludeFiles = TRUE;933break;934935case PARSEOP_TIMER:936937if (AcpiGbl_IntegerBitWidth == 32)938{939AslError (ASL_REMARK, ASL_MSG_TRUNCATION, Op, NULL);940}941break;942943default:944945/* Nothing to do for other opcodes */946947break;948}949950return;951}952953954