1 /****************************************************************************** 2 * 3 * Module Name: dswload - Dispatcher namespace load callbacks 4 * 5 *****************************************************************************/ 6 7 /****************************************************************************** 8 * 9 * 1. Copyright Notice 10 * 11 * Some or all of this work - Copyright (c) 1999 - 2010, 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 #define __ASLLOAD_C__ 117 118 #include <contrib/dev/acpica/compiler/aslcompiler.h> 119 #include <contrib/dev/acpica/include/amlcode.h> 120 #include <contrib/dev/acpica/include/acdispat.h> 121 #include <contrib/dev/acpica/include/acnamesp.h> 122 123 #include "aslcompiler.y.h" 124 125 #define _COMPONENT ACPI_COMPILER 126 ACPI_MODULE_NAME ("aslload") 127 128 /* Local prototypes */ 129 130 static ACPI_STATUS 131 LdLoadFieldElements ( 132 ACPI_PARSE_OBJECT *Op, 133 ACPI_WALK_STATE *WalkState); 134 135 static ACPI_STATUS 136 LdLoadResourceElements ( 137 ACPI_PARSE_OBJECT *Op, 138 ACPI_WALK_STATE *WalkState); 139 140 static ACPI_STATUS 141 LdNamespace1Begin ( 142 ACPI_PARSE_OBJECT *Op, 143 UINT32 Level, 144 void *Context); 145 146 static ACPI_STATUS 147 LdNamespace2Begin ( 148 ACPI_PARSE_OBJECT *Op, 149 UINT32 Level, 150 void *Context); 151 152 static ACPI_STATUS 153 LdCommonNamespaceEnd ( 154 ACPI_PARSE_OBJECT *Op, 155 UINT32 Level, 156 void *Context); 157 158 159 /******************************************************************************* 160 * 161 * FUNCTION: LdLoadNamespace 162 * 163 * PARAMETERS: RootOp - Root of the parse tree 164 * 165 * RETURN: Status 166 * 167 * DESCRIPTION: Perform a walk of the parse tree that in turn loads all of the 168 * named ASL/AML objects into the namespace. The namespace is 169 * constructed in order to resolve named references and references 170 * to named fields within resource templates/descriptors. 171 * 172 ******************************************************************************/ 173 174 ACPI_STATUS 175 LdLoadNamespace ( 176 ACPI_PARSE_OBJECT *RootOp) 177 { 178 ACPI_WALK_STATE *WalkState; 179 180 181 DbgPrint (ASL_DEBUG_OUTPUT, "\nCreating namespace\n\n"); 182 183 /* Create a new walk state */ 184 185 WalkState = AcpiDsCreateWalkState (0, NULL, NULL, NULL); 186 if (!WalkState) 187 { 188 return AE_NO_MEMORY; 189 } 190 191 /* Walk the entire parse tree, first pass */ 192 193 TrWalkParseTree (RootOp, ASL_WALK_VISIT_TWICE, LdNamespace1Begin, 194 LdCommonNamespaceEnd, WalkState); 195 196 /* Second pass to handle forward references */ 197 198 TrWalkParseTree (RootOp, ASL_WALK_VISIT_TWICE, LdNamespace2Begin, 199 LdCommonNamespaceEnd, WalkState); 200 201 /* Dump the namespace if debug is enabled */ 202 203 AcpiNsDumpTables (ACPI_NS_ALL, ACPI_UINT32_MAX); 204 return AE_OK; 205 } 206 207 208 /******************************************************************************* 209 * 210 * FUNCTION: LdLoadFieldElements 211 * 212 * PARAMETERS: Op - Parent node (Field) 213 * WalkState - Current walk state 214 * 215 * RETURN: Status 216 * 217 * DESCRIPTION: Enter the named elements of the field (children of the parent) 218 * into the namespace. 219 * 220 ******************************************************************************/ 221 222 static ACPI_STATUS 223 LdLoadFieldElements ( 224 ACPI_PARSE_OBJECT *Op, 225 ACPI_WALK_STATE *WalkState) 226 { 227 ACPI_PARSE_OBJECT *Child = NULL; 228 ACPI_NAMESPACE_NODE *Node; 229 ACPI_STATUS Status; 230 231 232 /* Get the first named field element */ 233 234 switch (Op->Asl.AmlOpcode) 235 { 236 case AML_BANK_FIELD_OP: 237 238 Child = UtGetArg (Op, 6); 239 break; 240 241 case AML_INDEX_FIELD_OP: 242 243 Child = UtGetArg (Op, 5); 244 break; 245 246 case AML_FIELD_OP: 247 248 Child = UtGetArg (Op, 4); 249 break; 250 251 default: 252 /* No other opcodes should arrive here */ 253 return (AE_BAD_PARAMETER); 254 } 255 256 /* Enter all elements into the namespace */ 257 258 while (Child) 259 { 260 switch (Child->Asl.AmlOpcode) 261 { 262 case AML_INT_RESERVEDFIELD_OP: 263 case AML_INT_ACCESSFIELD_OP: 264 265 break; 266 267 default: 268 269 Status = AcpiNsLookup (WalkState->ScopeInfo, 270 Child->Asl.Value.String, 271 ACPI_TYPE_LOCAL_REGION_FIELD, 272 ACPI_IMODE_LOAD_PASS1, 273 ACPI_NS_NO_UPSEARCH | ACPI_NS_DONT_OPEN_SCOPE | 274 ACPI_NS_ERROR_IF_FOUND, 275 NULL, &Node); 276 if (ACPI_FAILURE (Status)) 277 { 278 if (Status != AE_ALREADY_EXISTS) 279 { 280 AslError (ASL_ERROR, ASL_MSG_CORE_EXCEPTION, Child, 281 Child->Asl.Value.String); 282 return (Status); 283 } 284 285 /* 286 * The name already exists in this scope 287 * But continue processing the elements 288 */ 289 AslError (ASL_ERROR, ASL_MSG_NAME_EXISTS, Child, 290 Child->Asl.Value.String); 291 } 292 else 293 { 294 Child->Asl.Node = Node; 295 Node->Op = Child; 296 } 297 break; 298 } 299 Child = Child->Asl.Next; 300 } 301 return (AE_OK); 302 } 303 304 305 /******************************************************************************* 306 * 307 * FUNCTION: LdLoadResourceElements 308 * 309 * PARAMETERS: Op - Parent node (Resource Descriptor) 310 * WalkState - Current walk state 311 * 312 * RETURN: Status 313 * 314 * DESCRIPTION: Enter the named elements of the resource descriptor (children 315 * of the parent) into the namespace. 316 * 317 * NOTE: In the real AML namespace, these named elements never exist. But 318 * we simply use the namespace here as a symbol table so we can look 319 * them up as they are referenced. 320 * 321 ******************************************************************************/ 322 323 static ACPI_STATUS 324 LdLoadResourceElements ( 325 ACPI_PARSE_OBJECT *Op, 326 ACPI_WALK_STATE *WalkState) 327 { 328 ACPI_PARSE_OBJECT *InitializerOp = NULL; 329 ACPI_NAMESPACE_NODE *Node; 330 ACPI_STATUS Status; 331 332 333 /* 334 * Enter the resource name into the namespace. Name must not already exist. 335 * This opens a scope, so later field names are guaranteed to be new/unique. 336 */ 337 Status = AcpiNsLookup (WalkState->ScopeInfo, Op->Asl.Namepath, 338 ACPI_TYPE_LOCAL_RESOURCE, ACPI_IMODE_LOAD_PASS1, 339 ACPI_NS_NO_UPSEARCH | ACPI_NS_ERROR_IF_FOUND, 340 WalkState, &Node); 341 if (ACPI_FAILURE (Status)) 342 { 343 if (Status == AE_ALREADY_EXISTS) 344 { 345 /* Actual node causing the error was saved in ParentMethod */ 346 347 AslError (ASL_ERROR, ASL_MSG_NAME_EXISTS, 348 (ACPI_PARSE_OBJECT *) Op->Asl.ParentMethod, Op->Asl.Namepath); 349 return (AE_OK); 350 } 351 return (Status); 352 } 353 354 Node->Value = (UINT32) Op->Asl.Value.Integer; 355 Node->Op = Op; 356 Op->Asl.Node = Node; 357 358 /* 359 * Now enter the predefined fields, for easy lookup when referenced 360 * by the source ASL 361 */ 362 InitializerOp = ASL_GET_CHILD_NODE (Op); 363 while (InitializerOp) 364 { 365 366 if (InitializerOp->Asl.ExternalName) 367 { 368 Status = AcpiNsLookup (WalkState->ScopeInfo, 369 InitializerOp->Asl.ExternalName, 370 ACPI_TYPE_LOCAL_RESOURCE_FIELD, 371 ACPI_IMODE_LOAD_PASS1, 372 ACPI_NS_NO_UPSEARCH | ACPI_NS_DONT_OPEN_SCOPE, 373 NULL, &Node); 374 if (ACPI_FAILURE (Status)) 375 { 376 return (Status); 377 } 378 379 /* 380 * Store the field offset in the namespace node so it 381 * can be used when the field is referenced 382 */ 383 Node->Value = (UINT32) InitializerOp->Asl.Value.Integer; 384 InitializerOp->Asl.Node = Node; 385 Node->Op = InitializerOp; 386 387 /* Pass thru the field type (Bitfield or Bytefield) */ 388 389 if (InitializerOp->Asl.CompileFlags & NODE_IS_BIT_OFFSET) 390 { 391 Node->Flags |= ANOBJ_IS_BIT_OFFSET; 392 } 393 } 394 InitializerOp = ASL_GET_PEER_NODE (InitializerOp); 395 } 396 397 return (AE_OK); 398 } 399 400 401 /******************************************************************************* 402 * 403 * FUNCTION: LdNamespace1Begin 404 * 405 * PARAMETERS: ASL_WALK_CALLBACK 406 * 407 * RETURN: Status 408 * 409 * DESCRIPTION: Descending callback used during the parse tree walk. If this 410 * is a named AML opcode, enter into the namespace 411 * 412 ******************************************************************************/ 413 414 static ACPI_STATUS 415 LdNamespace1Begin ( 416 ACPI_PARSE_OBJECT *Op, 417 UINT32 Level, 418 void *Context) 419 { 420 ACPI_WALK_STATE *WalkState = (ACPI_WALK_STATE *) Context; 421 ACPI_NAMESPACE_NODE *Node; 422 ACPI_STATUS Status; 423 ACPI_OBJECT_TYPE ObjectType; 424 ACPI_OBJECT_TYPE ActualObjectType = ACPI_TYPE_ANY; 425 char *Path; 426 UINT32 Flags = ACPI_NS_NO_UPSEARCH; 427 ACPI_PARSE_OBJECT *Arg; 428 UINT32 i; 429 BOOLEAN ForceNewScope = FALSE; 430 431 432 ACPI_FUNCTION_NAME (LdNamespace1Begin); 433 ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, "Op %p [%s]\n", 434 Op, Op->Asl.ParseOpName)); 435 436 437 /* 438 * We are only interested in opcodes that have an associated name 439 * (or multiple names) 440 */ 441 switch (Op->Asl.AmlOpcode) 442 { 443 case AML_BANK_FIELD_OP: 444 case AML_INDEX_FIELD_OP: 445 case AML_FIELD_OP: 446 447 Status = LdLoadFieldElements (Op, WalkState); 448 return (Status); 449 450 default: 451 452 /* All other opcodes go below */ 453 break; 454 } 455 456 /* Check if this object has already been installed in the namespace */ 457 458 if (Op->Asl.Node) 459 { 460 return (AE_OK); 461 } 462 463 Path = Op->Asl.Namepath; 464 if (!Path) 465 { 466 return (AE_OK); 467 } 468 469 /* Map the raw opcode into an internal object type */ 470 471 switch (Op->Asl.ParseOpcode) 472 { 473 case PARSEOP_NAME: 474 475 Arg = Op->Asl.Child; /* Get the NameSeg/NameString node */ 476 Arg = Arg->Asl.Next; /* First peer is the object to be associated with the name */ 477 478 /* 479 * If this name refers to a ResourceTemplate, we will need to open 480 * a new scope so that the resource subfield names can be entered into 481 * the namespace underneath this name 482 */ 483 if (Op->Asl.CompileFlags & NODE_IS_RESOURCE_DESC) 484 { 485 ForceNewScope = TRUE; 486 } 487 488 /* Get the data type associated with the named object, not the name itself */ 489 490 /* Log2 loop to convert from Btype (binary) to Etype (encoded) */ 491 492 ObjectType = 1; 493 for (i = 1; i < Arg->Asl.AcpiBtype; i *= 2) 494 { 495 ObjectType++; 496 } 497 break; 498 499 500 case PARSEOP_EXTERNAL: 501 502 /* 503 * "External" simply enters a name and type into the namespace. 504 * We must be careful to not open a new scope, however, no matter 505 * what type the external name refers to (e.g., a method) 506 * 507 * first child is name, next child is ObjectType 508 */ 509 ActualObjectType = (UINT8) Op->Asl.Child->Asl.Next->Asl.Value.Integer; 510 ObjectType = ACPI_TYPE_ANY; 511 512 /* 513 * We will mark every new node along the path as "External". This 514 * allows some or all of the nodes to be created later in the ASL 515 * code. Handles cases like this: 516 * 517 * External (\_SB_.PCI0.ABCD, IntObj) 518 * Scope (_SB_) 519 * { 520 * Device (PCI0) 521 * { 522 * } 523 * } 524 * Method (X) 525 * { 526 * Store (\_SB_.PCI0.ABCD, Local0) 527 * } 528 */ 529 Flags |= ACPI_NS_EXTERNAL; 530 break; 531 532 case PARSEOP_DEFAULT_ARG: 533 534 if (Op->Asl.CompileFlags == NODE_IS_RESOURCE_DESC) 535 { 536 Status = LdLoadResourceElements (Op, WalkState); 537 return_ACPI_STATUS (Status); 538 } 539 540 ObjectType = AslMapNamedOpcodeToDataType (Op->Asl.AmlOpcode); 541 break; 542 543 544 case PARSEOP_SCOPE: 545 546 /* 547 * The name referenced by Scope(Name) must already exist at this point. 548 * In other words, forward references for Scope() are not supported. 549 * The only real reason for this is that the MS interpreter cannot 550 * handle this case. Perhaps someday this case can go away. 551 */ 552 Status = AcpiNsLookup (WalkState->ScopeInfo, Path, ACPI_TYPE_ANY, 553 ACPI_IMODE_EXECUTE, ACPI_NS_SEARCH_PARENT, 554 WalkState, &(Node)); 555 if (ACPI_FAILURE (Status)) 556 { 557 if (Status == AE_NOT_FOUND) 558 { 559 /* The name was not found, go ahead and create it */ 560 561 Status = AcpiNsLookup (WalkState->ScopeInfo, Path, 562 ACPI_TYPE_LOCAL_SCOPE, 563 ACPI_IMODE_LOAD_PASS1, Flags, 564 WalkState, &(Node)); 565 566 /* 567 * However, this is an error -- primarily because the MS 568 * interpreter can't handle a forward reference from the 569 * Scope() operator. 570 */ 571 AslError (ASL_ERROR, ASL_MSG_NOT_FOUND, Op, 572 Op->Asl.ExternalName); 573 AslError (ASL_ERROR, ASL_MSG_SCOPE_FWD_REF, Op, 574 Op->Asl.ExternalName); 575 goto FinishNode; 576 } 577 578 AslCoreSubsystemError (Op, Status, 579 "Failure from namespace lookup", FALSE); 580 581 return_ACPI_STATUS (Status); 582 } 583 584 /* We found a node with this name, now check the type */ 585 586 switch (Node->Type) 587 { 588 case ACPI_TYPE_LOCAL_SCOPE: 589 case ACPI_TYPE_DEVICE: 590 case ACPI_TYPE_POWER: 591 case ACPI_TYPE_PROCESSOR: 592 case ACPI_TYPE_THERMAL: 593 594 /* These are acceptable types - they all open a new scope */ 595 break; 596 597 case ACPI_TYPE_INTEGER: 598 case ACPI_TYPE_STRING: 599 case ACPI_TYPE_BUFFER: 600 601 /* 602 * These types we will allow, but we will change the type. 603 * This enables some existing code of the form: 604 * 605 * Name (DEB, 0) 606 * Scope (DEB) { ... } 607 * 608 * Which is used to workaround the fact that the MS interpreter 609 * does not allow Scope() forward references. 610 */ 611 sprintf (MsgBuffer, "%s [%s], changing type to [Scope]", 612 Op->Asl.ExternalName, AcpiUtGetTypeName (Node->Type)); 613 AslError (ASL_REMARK, ASL_MSG_SCOPE_TYPE, Op, MsgBuffer); 614 615 /* Switch the type to scope, open the new scope */ 616 617 Node->Type = ACPI_TYPE_LOCAL_SCOPE; 618 Status = AcpiDsScopeStackPush (Node, ACPI_TYPE_LOCAL_SCOPE, 619 WalkState); 620 if (ACPI_FAILURE (Status)) 621 { 622 return_ACPI_STATUS (Status); 623 } 624 break; 625 626 default: 627 628 /* All other types are an error */ 629 630 sprintf (MsgBuffer, "%s [%s]", Op->Asl.ExternalName, 631 AcpiUtGetTypeName (Node->Type)); 632 AslError (ASL_ERROR, ASL_MSG_SCOPE_TYPE, Op, MsgBuffer); 633 634 /* 635 * However, switch the type to be an actual scope so 636 * that compilation can continue without generating a whole 637 * cascade of additional errors. Open the new scope. 638 */ 639 Node->Type = ACPI_TYPE_LOCAL_SCOPE; 640 Status = AcpiDsScopeStackPush (Node, ACPI_TYPE_LOCAL_SCOPE, 641 WalkState); 642 if (ACPI_FAILURE (Status)) 643 { 644 return_ACPI_STATUS (Status); 645 } 646 break; 647 } 648 649 Status = AE_OK; 650 goto FinishNode; 651 652 653 default: 654 655 ObjectType = AslMapNamedOpcodeToDataType (Op->Asl.AmlOpcode); 656 break; 657 } 658 659 660 ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, "Loading name: %s, (%s)\n", 661 Op->Asl.ExternalName, AcpiUtGetTypeName (ObjectType))); 662 663 /* The name must not already exist */ 664 665 Flags |= ACPI_NS_ERROR_IF_FOUND; 666 667 /* 668 * Enter the named type into the internal namespace. We enter the name 669 * as we go downward in the parse tree. Any necessary subobjects that 670 * involve arguments to the opcode must be created as we go back up the 671 * parse tree later. 672 */ 673 Status = AcpiNsLookup (WalkState->ScopeInfo, Path, ObjectType, 674 ACPI_IMODE_LOAD_PASS1, Flags, WalkState, &Node); 675 if (ACPI_FAILURE (Status)) 676 { 677 if (Status == AE_ALREADY_EXISTS) 678 { 679 /* The name already exists in this scope */ 680 681 if (Node->Type == ACPI_TYPE_LOCAL_SCOPE) 682 { 683 /* Allow multiple references to the same scope */ 684 685 Node->Type = (UINT8) ObjectType; 686 Status = AE_OK; 687 } 688 else if ((Node->Flags & ANOBJ_IS_EXTERNAL) && 689 (Op->Asl.ParseOpcode != PARSEOP_EXTERNAL)) 690 { 691 /* 692 * Allow one create on an object or segment that was 693 * previously declared External 694 */ 695 Node->Flags &= ~ANOBJ_IS_EXTERNAL; 696 Node->Type = (UINT8) ObjectType; 697 698 /* Just retyped a node, probably will need to open a scope */ 699 700 if (AcpiNsOpensScope (ObjectType)) 701 { 702 Status = AcpiDsScopeStackPush (Node, ObjectType, WalkState); 703 if (ACPI_FAILURE (Status)) 704 { 705 return_ACPI_STATUS (Status); 706 } 707 } 708 Status = AE_OK; 709 } 710 else 711 { 712 /* Valid error, object already exists */ 713 714 AslError (ASL_ERROR, ASL_MSG_NAME_EXISTS, Op, 715 Op->Asl.ExternalName); 716 return_ACPI_STATUS (AE_OK); 717 } 718 } 719 else 720 { 721 AslCoreSubsystemError (Op, Status, 722 "Failure from namespace lookup", FALSE); 723 return_ACPI_STATUS (Status); 724 } 725 } 726 727 if (ForceNewScope) 728 { 729 Status = AcpiDsScopeStackPush (Node, ObjectType, WalkState); 730 if (ACPI_FAILURE (Status)) 731 { 732 return_ACPI_STATUS (Status); 733 } 734 } 735 736 FinishNode: 737 /* 738 * Point the parse node to the new namespace node, and point 739 * the Node back to the original Parse node 740 */ 741 Op->Asl.Node = Node; 742 Node->Op = Op; 743 744 /* Set the actual data type if appropriate (EXTERNAL term only) */ 745 746 if (ActualObjectType != ACPI_TYPE_ANY) 747 { 748 Node->Type = (UINT8) ActualObjectType; 749 Node->Value = ASL_EXTERNAL_METHOD; 750 } 751 752 if (Op->Asl.ParseOpcode == PARSEOP_METHOD) 753 { 754 /* 755 * Get the method argument count from "Extra" and save 756 * it in the namespace node 757 */ 758 Node->Value = (UINT32) Op->Asl.Extra; 759 } 760 761 return_ACPI_STATUS (Status); 762 } 763 764 765 /******************************************************************************* 766 * 767 * FUNCTION: LdNamespace2Begin 768 * 769 * PARAMETERS: ASL_WALK_CALLBACK 770 * 771 * RETURN: Status 772 * 773 * DESCRIPTION: Descending callback used during the pass 2 parse tree walk. 774 * Second pass resolves some forward references. 775 * 776 * Notes: 777 * Currently only needs to handle the Alias operator. 778 * Could be used to allow forward references from the Scope() operator, but 779 * the MS interpreter does not allow this, so this compiler does not either. 780 * 781 ******************************************************************************/ 782 783 static ACPI_STATUS 784 LdNamespace2Begin ( 785 ACPI_PARSE_OBJECT *Op, 786 UINT32 Level, 787 void *Context) 788 { 789 ACPI_WALK_STATE *WalkState = (ACPI_WALK_STATE *) Context; 790 ACPI_STATUS Status; 791 ACPI_NAMESPACE_NODE *Node; 792 ACPI_OBJECT_TYPE ObjectType; 793 BOOLEAN ForceNewScope = FALSE; 794 ACPI_PARSE_OBJECT *Arg; 795 char *Path; 796 ACPI_NAMESPACE_NODE *TargetNode; 797 798 799 ACPI_FUNCTION_NAME (LdNamespace2Begin); 800 ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, "Op %p [%s]\n", 801 Op, Op->Asl.ParseOpName)); 802 803 804 /* Ignore Ops with no namespace node */ 805 806 Node = Op->Asl.Node; 807 if (!Node) 808 { 809 return (AE_OK); 810 } 811 812 /* Get the type to determine if we should push the scope */ 813 814 if ((Op->Asl.ParseOpcode == PARSEOP_DEFAULT_ARG) && 815 (Op->Asl.CompileFlags == NODE_IS_RESOURCE_DESC)) 816 { 817 ObjectType = ACPI_TYPE_LOCAL_RESOURCE; 818 } 819 else 820 { 821 ObjectType = AslMapNamedOpcodeToDataType (Op->Asl.AmlOpcode); 822 } 823 824 /* Push scope for Resource Templates */ 825 826 if (Op->Asl.ParseOpcode == PARSEOP_NAME) 827 { 828 if (Op->Asl.CompileFlags & NODE_IS_RESOURCE_DESC) 829 { 830 ForceNewScope = TRUE; 831 } 832 } 833 834 /* Push the scope stack */ 835 836 if (ForceNewScope || AcpiNsOpensScope (ObjectType)) 837 { 838 Status = AcpiDsScopeStackPush (Node, ObjectType, WalkState); 839 if (ACPI_FAILURE (Status)) 840 { 841 return_ACPI_STATUS (Status); 842 } 843 } 844 845 if (Op->Asl.ParseOpcode == PARSEOP_ALIAS) 846 { 847 /* Complete the alias node by getting and saving the target node */ 848 849 /* First child is the alias target */ 850 851 Arg = Op->Asl.Child; 852 853 /* Get the target pathname */ 854 855 Path = Arg->Asl.Namepath; 856 if (!Path) 857 { 858 Status = UtInternalizeName (Arg->Asl.ExternalName, &Path); 859 if (ACPI_FAILURE (Status)) 860 { 861 return (Status); 862 } 863 } 864 865 /* Get the NS node associated with the target. It must exist. */ 866 867 Status = AcpiNsLookup (WalkState->ScopeInfo, Path, ACPI_TYPE_ANY, 868 ACPI_IMODE_EXECUTE, ACPI_NS_SEARCH_PARENT | ACPI_NS_DONT_OPEN_SCOPE, 869 WalkState, &TargetNode); 870 if (ACPI_FAILURE (Status)) 871 { 872 if (Status == AE_NOT_FOUND) 873 { 874 AslError (ASL_ERROR, ASL_MSG_NOT_FOUND, Op, 875 Op->Asl.ExternalName); 876 877 /* 878 * The name was not found, go ahead and create it. 879 * This prevents more errors later. 880 */ 881 Status = AcpiNsLookup (WalkState->ScopeInfo, Path, 882 ACPI_TYPE_ANY, 883 ACPI_IMODE_LOAD_PASS1, ACPI_NS_NO_UPSEARCH, 884 WalkState, &(Node)); 885 return (AE_OK); 886 } 887 888 AslCoreSubsystemError (Op, Status, 889 "Failure from namespace lookup", FALSE); 890 return (AE_OK); 891 } 892 893 /* Save the target node within the alias node */ 894 895 Node->Object = ACPI_CAST_PTR (ACPI_OPERAND_OBJECT, TargetNode); 896 } 897 898 return (AE_OK); 899 } 900 901 902 /******************************************************************************* 903 * 904 * FUNCTION: LdCommonNamespaceEnd 905 * 906 * PARAMETERS: ASL_WALK_CALLBACK 907 * 908 * RETURN: Status 909 * 910 * DESCRIPTION: Ascending callback used during the loading of the namespace, 911 * We only need to worry about managing the scope stack here. 912 * 913 ******************************************************************************/ 914 915 static ACPI_STATUS 916 LdCommonNamespaceEnd ( 917 ACPI_PARSE_OBJECT *Op, 918 UINT32 Level, 919 void *Context) 920 { 921 ACPI_WALK_STATE *WalkState = (ACPI_WALK_STATE *) Context; 922 ACPI_OBJECT_TYPE ObjectType; 923 BOOLEAN ForceNewScope = FALSE; 924 925 926 ACPI_FUNCTION_NAME (LdCommonNamespaceEnd); 927 928 929 /* We are only interested in opcodes that have an associated name */ 930 931 if (!Op->Asl.Namepath) 932 { 933 return (AE_OK); 934 } 935 936 /* Get the type to determine if we should pop the scope */ 937 938 if ((Op->Asl.ParseOpcode == PARSEOP_DEFAULT_ARG) && 939 (Op->Asl.CompileFlags == NODE_IS_RESOURCE_DESC)) 940 { 941 /* TBD: Merge into AcpiDsMapNamedOpcodeToDataType */ 942 943 ObjectType = ACPI_TYPE_LOCAL_RESOURCE; 944 } 945 else 946 { 947 ObjectType = AslMapNamedOpcodeToDataType (Op->Asl.AmlOpcode); 948 } 949 950 /* Pop scope that was pushed for Resource Templates */ 951 952 if (Op->Asl.ParseOpcode == PARSEOP_NAME) 953 { 954 if (Op->Asl.CompileFlags & NODE_IS_RESOURCE_DESC) 955 { 956 ForceNewScope = TRUE; 957 } 958 } 959 960 /* Pop the scope stack */ 961 962 if (ForceNewScope || AcpiNsOpensScope (ObjectType)) 963 { 964 ACPI_DEBUG_PRINT ((ACPI_DB_DISPATCH, 965 "(%s): Popping scope for Op [%s] %p\n", 966 AcpiUtGetTypeName (ObjectType), Op->Asl.ParseOpName, Op)); 967 968 (void) AcpiDsScopeStackPop (WalkState); 969 } 970 971 return (AE_OK); 972 } 973 974 975