nsxfeval.c revision 151937
1/******************************************************************************* 2 * 3 * Module Name: nsxfeval - Public interfaces to the ACPI subsystem 4 * ACPI Object evaluation interfaces 5 * $Revision: 1.17 $ 6 * 7 ******************************************************************************/ 8 9/****************************************************************************** 10 * 11 * 1. Copyright Notice 12 * 13 * Some or all of this work - Copyright (c) 1999 - 2005, Intel Corp. 14 * All rights reserved. 15 * 16 * 2. License 17 * 18 * 2.1. This is your license from Intel Corp. under its intellectual property 19 * rights. You may have additional license terms from the party that provided 20 * you this software, covering your right to use that party's intellectual 21 * property rights. 22 * 23 * 2.2. Intel grants, free of charge, to any person ("Licensee") obtaining a 24 * copy of the source code appearing in this file ("Covered Code") an 25 * irrevocable, perpetual, worldwide license under Intel's copyrights in the 26 * base code distributed originally by Intel ("Original Intel Code") to copy, 27 * make derivatives, distribute, use and display any portion of the Covered 28 * Code in any form, with the right to sublicense such rights; and 29 * 30 * 2.3. Intel grants Licensee a non-exclusive and non-transferable patent 31 * license (with the right to sublicense), under only those claims of Intel 32 * patents that are infringed by the Original Intel Code, to make, use, sell, 33 * offer to sell, and import the Covered Code and derivative works thereof 34 * solely to the minimum extent necessary to exercise the above copyright 35 * license, and in no event shall the patent license extend to any additions 36 * to or modifications of the Original Intel Code. No other license or right 37 * is granted directly or by implication, estoppel or otherwise; 38 * 39 * The above copyright and patent license is granted only if the following 40 * conditions are met: 41 * 42 * 3. Conditions 43 * 44 * 3.1. Redistribution of Source with Rights to Further Distribute Source. 45 * Redistribution of source code of any substantial portion of the Covered 46 * Code or modification with rights to further distribute source must include 47 * the above Copyright Notice, the above License, this list of Conditions, 48 * and the following Disclaimer and Export Compliance provision. In addition, 49 * Licensee must cause all Covered Code to which Licensee contributes to 50 * contain a file documenting the changes Licensee made to create that Covered 51 * Code and the date of any change. Licensee must include in that file the 52 * documentation of any changes made by any predecessor Licensee. Licensee 53 * must include a prominent statement that the modification is derived, 54 * directly or indirectly, from Original Intel Code. 55 * 56 * 3.2. Redistribution of Source with no Rights to Further Distribute Source. 57 * Redistribution of source code of any substantial portion of the Covered 58 * Code or modification without rights to further distribute source must 59 * include the following Disclaimer and Export Compliance provision in the 60 * documentation and/or other materials provided with distribution. In 61 * addition, Licensee may not authorize further sublicense of source of any 62 * portion of the Covered Code, and must include terms to the effect that the 63 * license from Licensee to its licensee is limited to the intellectual 64 * property embodied in the software Licensee provides to its licensee, and 65 * not to intellectual property embodied in modifications its licensee may 66 * make. 67 * 68 * 3.3. Redistribution of Executable. Redistribution in executable form of any 69 * substantial portion of the Covered Code or modification must reproduce the 70 * above Copyright Notice, and the following Disclaimer and Export Compliance 71 * provision in the documentation and/or other materials provided with the 72 * distribution. 73 * 74 * 3.4. Intel retains all right, title, and interest in and to the Original 75 * Intel Code. 76 * 77 * 3.5. Neither the name Intel nor any other trademark owned or controlled by 78 * Intel shall be used in advertising or otherwise to promote the sale, use or 79 * other dealings in products derived from or relating to the Covered Code 80 * without prior written authorization from Intel. 81 * 82 * 4. Disclaimer and Export Compliance 83 * 84 * 4.1. INTEL MAKES NO WARRANTY OF ANY KIND REGARDING ANY SOFTWARE PROVIDED 85 * HERE. ANY SOFTWARE ORIGINATING FROM INTEL OR DERIVED FROM INTEL SOFTWARE 86 * IS PROVIDED "AS IS," AND INTEL WILL NOT PROVIDE ANY SUPPORT, ASSISTANCE, 87 * INSTALLATION, TRAINING OR OTHER SERVICES. INTEL WILL NOT PROVIDE ANY 88 * UPDATES, ENHANCEMENTS OR EXTENSIONS. INTEL SPECIFICALLY DISCLAIMS ANY 89 * IMPLIED WARRANTIES OF MERCHANTABILITY, NONINFRINGEMENT AND FITNESS FOR A 90 * PARTICULAR PURPOSE. 91 * 92 * 4.2. IN NO EVENT SHALL INTEL HAVE ANY LIABILITY TO LICENSEE, ITS LICENSEES 93 * OR ANY OTHER THIRD PARTY, FOR ANY LOST PROFITS, LOST DATA, LOSS OF USE OR 94 * COSTS OF PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES, OR FOR ANY INDIRECT, 95 * SPECIAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THIS AGREEMENT, UNDER ANY 96 * CAUSE OF ACTION OR THEORY OF LIABILITY, AND IRRESPECTIVE OF WHETHER INTEL 97 * HAS ADVANCE NOTICE OF THE POSSIBILITY OF SUCH DAMAGES. THESE LIMITATIONS 98 * SHALL APPLY NOTWITHSTANDING THE FAILURE OF THE ESSENTIAL PURPOSE OF ANY 99 * LIMITED REMEDY. 100 * 101 * 4.3. Licensee shall not export, either directly or indirectly, any of this 102 * software or system incorporating such software without first obtaining any 103 * required license or other approval from the U. S. Department of Commerce or 104 * any other agency or department of the United States Government. In the 105 * event Licensee exports any such software from the United States or 106 * re-exports any such software from a foreign destination, Licensee shall 107 * ensure that the distribution and export/re-export of the software is in 108 * compliance with all laws, regulations, orders, or other restrictions of the 109 * U.S. Export Administration Regulations. Licensee agrees that neither it nor 110 * any of its subsidiaries will export/re-export any technical data, process, 111 * software, or service, directly or indirectly, to any country for which the 112 * United States government or any agency thereof requires an export license, 113 * other governmental approval, or letter of assurance, without first obtaining 114 * such license, approval or letter. 115 * 116 *****************************************************************************/ 117 118 119#define __NSXFEVAL_C__ 120 121#include <contrib/dev/acpica/acpi.h> 122#include <contrib/dev/acpica/acnamesp.h> 123#include <contrib/dev/acpica/acinterp.h> 124 125 126#define _COMPONENT ACPI_NAMESPACE 127 ACPI_MODULE_NAME ("nsxfeval") 128 129 130/******************************************************************************* 131 * 132 * FUNCTION: AcpiEvaluateObjectTyped 133 * 134 * PARAMETERS: Handle - Object handle (optional) 135 * Pathname - Object pathname (optional) 136 * ExternalParams - List of parameters to pass to method, 137 * terminated by NULL. May be NULL 138 * if no parameters are being passed. 139 * ReturnBuffer - Where to put method's return value (if 140 * any). If NULL, no value is returned. 141 * ReturnType - Expected type of return object 142 * 143 * RETURN: Status 144 * 145 * DESCRIPTION: Find and evaluate the given object, passing the given 146 * parameters if necessary. One of "Handle" or "Pathname" must 147 * be valid (non-null) 148 * 149 ******************************************************************************/ 150 151ACPI_STATUS 152AcpiEvaluateObjectTyped ( 153 ACPI_HANDLE Handle, 154 ACPI_STRING Pathname, 155 ACPI_OBJECT_LIST *ExternalParams, 156 ACPI_BUFFER *ReturnBuffer, 157 ACPI_OBJECT_TYPE ReturnType) 158{ 159 ACPI_STATUS Status; 160 BOOLEAN MustFree = FALSE; 161 162 163 ACPI_FUNCTION_TRACE ("AcpiEvaluateObjectTyped"); 164 165 166 /* Return buffer must be valid */ 167 168 if (!ReturnBuffer) 169 { 170 return_ACPI_STATUS (AE_BAD_PARAMETER); 171 } 172 173 if (ReturnBuffer->Length == ACPI_ALLOCATE_BUFFER) 174 { 175 MustFree = TRUE; 176 } 177 178 /* Evaluate the object */ 179 180 Status = AcpiEvaluateObject (Handle, Pathname, ExternalParams, ReturnBuffer); 181 if (ACPI_FAILURE (Status)) 182 { 183 return_ACPI_STATUS (Status); 184 } 185 186 /* Type ANY means "don't care" */ 187 188 if (ReturnType == ACPI_TYPE_ANY) 189 { 190 return_ACPI_STATUS (AE_OK); 191 } 192 193 if (ReturnBuffer->Length == 0) 194 { 195 /* Error because caller specifically asked for a return value */ 196 197 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, 198 "No return value\n")); 199 200 return_ACPI_STATUS (AE_NULL_OBJECT); 201 } 202 203 /* Examine the object type returned from EvaluateObject */ 204 205 if (((ACPI_OBJECT *) ReturnBuffer->Pointer)->Type == ReturnType) 206 { 207 return_ACPI_STATUS (AE_OK); 208 } 209 210 /* Return object type does not match requested type */ 211 212 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, 213 "Incorrect return type [%s] requested [%s]\n", 214 AcpiUtGetTypeName (((ACPI_OBJECT *) ReturnBuffer->Pointer)->Type), 215 AcpiUtGetTypeName (ReturnType))); 216 217 if (MustFree) 218 { 219 /* Caller used ACPI_ALLOCATE_BUFFER, free the return buffer */ 220 221 AcpiOsFree (ReturnBuffer->Pointer); 222 ReturnBuffer->Pointer = NULL; 223 } 224 225 ReturnBuffer->Length = 0; 226 return_ACPI_STATUS (AE_TYPE); 227} 228 229 230/******************************************************************************* 231 * 232 * FUNCTION: AcpiEvaluateObject 233 * 234 * PARAMETERS: Handle - Object handle (optional) 235 * Pathname - Object pathname (optional) 236 * ExternalParams - List of parameters to pass to method, 237 * terminated by NULL. May be NULL 238 * if no parameters are being passed. 239 * ReturnBuffer - Where to put method's return value (if 240 * any). If NULL, no value is returned. 241 * 242 * RETURN: Status 243 * 244 * DESCRIPTION: Find and evaluate the given object, passing the given 245 * parameters if necessary. One of "Handle" or "Pathname" must 246 * be valid (non-null) 247 * 248 ******************************************************************************/ 249 250ACPI_STATUS 251AcpiEvaluateObject ( 252 ACPI_HANDLE Handle, 253 ACPI_STRING Pathname, 254 ACPI_OBJECT_LIST *ExternalParams, 255 ACPI_BUFFER *ReturnBuffer) 256{ 257 ACPI_STATUS Status; 258 ACPI_STATUS Status2; 259 ACPI_PARAMETER_INFO Info; 260 ACPI_SIZE BufferSpaceNeeded; 261 UINT32 i; 262 263 264 ACPI_FUNCTION_TRACE ("AcpiEvaluateObject"); 265 266 267 Info.Node = Handle; 268 Info.Parameters = NULL; 269 Info.ReturnObject = NULL; 270 Info.ParameterType = ACPI_PARAM_ARGS; 271 272 /* 273 * If there are parameters to be passed to the object 274 * (which must be a control method), the external objects 275 * must be converted to internal objects 276 */ 277 if (ExternalParams && ExternalParams->Count) 278 { 279 /* 280 * Allocate a new parameter block for the internal objects 281 * Add 1 to count to allow for null terminated internal list 282 */ 283 Info.Parameters = ACPI_MEM_CALLOCATE ( 284 ((ACPI_SIZE) ExternalParams->Count + 1) * 285 sizeof (void *)); 286 if (!Info.Parameters) 287 { 288 return_ACPI_STATUS (AE_NO_MEMORY); 289 } 290 291 /* 292 * Convert each external object in the list to an 293 * internal object 294 */ 295 for (i = 0; i < ExternalParams->Count; i++) 296 { 297 Status = AcpiUtCopyEobjectToIobject (&ExternalParams->Pointer[i], 298 &Info.Parameters[i]); 299 if (ACPI_FAILURE (Status)) 300 { 301 AcpiUtDeleteInternalObjectList (Info.Parameters); 302 return_ACPI_STATUS (Status); 303 } 304 } 305 Info.Parameters[ExternalParams->Count] = NULL; 306 } 307 308 309 /* 310 * Three major cases: 311 * 1) Fully qualified pathname 312 * 2) No handle, not fully qualified pathname (error) 313 * 3) Valid handle 314 */ 315 if ((Pathname) && 316 (AcpiNsValidRootPrefix (Pathname[0]))) 317 { 318 /* 319 * The path is fully qualified, just evaluate by name 320 */ 321 Status = AcpiNsEvaluateByName (Pathname, &Info); 322 } 323 else if (!Handle) 324 { 325 /* 326 * A handle is optional iff a fully qualified pathname 327 * is specified. Since we've already handled fully 328 * qualified names above, this is an error 329 */ 330 if (!Pathname) 331 { 332 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, 333 "Both Handle and Pathname are NULL\n")); 334 } 335 else 336 { 337 ACPI_DEBUG_PRINT ((ACPI_DB_ERROR, 338 "Handle is NULL and Pathname is relative\n")); 339 } 340 341 Status = AE_BAD_PARAMETER; 342 } 343 else 344 { 345 /* 346 * We get here if we have a handle -- and if we have a 347 * pathname it is relative. The handle will be validated 348 * in the lower procedures 349 */ 350 if (!Pathname) 351 { 352 /* 353 * The null pathname case means the handle is for 354 * the actual object to be evaluated 355 */ 356 Status = AcpiNsEvaluateByHandle (&Info); 357 } 358 else 359 { 360 /* 361 * Both a Handle and a relative Pathname 362 */ 363 Status = AcpiNsEvaluateRelative (Pathname, &Info); 364 } 365 } 366 367 368 /* 369 * If we are expecting a return value, and all went well above, 370 * copy the return value to an external object. 371 */ 372 if (ReturnBuffer) 373 { 374 if (!Info.ReturnObject) 375 { 376 ReturnBuffer->Length = 0; 377 } 378 else 379 { 380 if (ACPI_GET_DESCRIPTOR_TYPE (Info.ReturnObject) == ACPI_DESC_TYPE_NAMED) 381 { 382 /* 383 * If we received a NS Node as a return object, this means that 384 * the object we are evaluating has nothing interesting to 385 * return (such as a mutex, etc.) We return an error because 386 * these types are essentially unsupported by this interface. 387 * We don't check up front because this makes it easier to add 388 * support for various types at a later date if necessary. 389 */ 390 Status = AE_TYPE; 391 Info.ReturnObject = NULL; /* No need to delete a NS Node */ 392 ReturnBuffer->Length = 0; 393 } 394 395 if (ACPI_SUCCESS (Status)) 396 { 397 /* 398 * Find out how large a buffer is needed 399 * to contain the returned object 400 */ 401 Status = AcpiUtGetObjectSize (Info.ReturnObject, 402 &BufferSpaceNeeded); 403 if (ACPI_SUCCESS (Status)) 404 { 405 /* Validate/Allocate/Clear caller buffer */ 406 407 Status = AcpiUtInitializeBuffer (ReturnBuffer, 408 BufferSpaceNeeded); 409 if (ACPI_FAILURE (Status)) 410 { 411 /* 412 * Caller's buffer is too small or a new one can't be allocated 413 */ 414 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 415 "Needed buffer size %X, %s\n", 416 (UINT32) BufferSpaceNeeded, 417 AcpiFormatException (Status))); 418 } 419 else 420 { 421 /* 422 * We have enough space for the object, build it 423 */ 424 Status = AcpiUtCopyIobjectToEobject (Info.ReturnObject, 425 ReturnBuffer); 426 } 427 } 428 } 429 } 430 } 431 432 if (Info.ReturnObject) 433 { 434 /* 435 * Delete the internal return object. NOTE: Interpreter 436 * must be locked to avoid race condition. 437 */ 438 Status2 = AcpiExEnterInterpreter (); 439 if (ACPI_SUCCESS (Status2)) 440 { 441 /* 442 * Delete the internal return object. (Or at least 443 * decrement the reference count by one) 444 */ 445 AcpiUtRemoveReference (Info.ReturnObject); 446 AcpiExExitInterpreter (); 447 } 448 } 449 450 /* 451 * Free the input parameter list (if we created one), 452 */ 453 if (Info.Parameters) 454 { 455 /* Free the allocated parameter block */ 456 457 AcpiUtDeleteInternalObjectList (Info.Parameters); 458 } 459 460 return_ACPI_STATUS (Status); 461} 462 463 464/******************************************************************************* 465 * 466 * FUNCTION: AcpiWalkNamespace 467 * 468 * PARAMETERS: Type - ACPI_OBJECT_TYPE to search for 469 * StartObject - Handle in namespace where search begins 470 * MaxDepth - Depth to which search is to reach 471 * UserFunction - Called when an object of "Type" is found 472 * Context - Passed to user function 473 * ReturnValue - Location where return value of 474 * UserFunction is put if terminated early 475 * 476 * RETURNS Return value from the UserFunction if terminated early. 477 * Otherwise, returns NULL. 478 * 479 * DESCRIPTION: Performs a modified depth-first walk of the namespace tree, 480 * starting (and ending) at the object specified by StartHandle. 481 * The UserFunction is called whenever an object that matches 482 * the type parameter is found. If the user function returns 483 * a non-zero value, the search is terminated immediately and this 484 * value is returned to the caller. 485 * 486 * The point of this procedure is to provide a generic namespace 487 * walk routine that can be called from multiple places to 488 * provide multiple services; the User Function can be tailored 489 * to each task, whether it is a print function, a compare 490 * function, etc. 491 * 492 ******************************************************************************/ 493 494ACPI_STATUS 495AcpiWalkNamespace ( 496 ACPI_OBJECT_TYPE Type, 497 ACPI_HANDLE StartObject, 498 UINT32 MaxDepth, 499 ACPI_WALK_CALLBACK UserFunction, 500 void *Context, 501 void **ReturnValue) 502{ 503 ACPI_STATUS Status; 504 505 506 ACPI_FUNCTION_TRACE ("AcpiWalkNamespace"); 507 508 509 /* Parameter validation */ 510 511 if ((Type > ACPI_TYPE_EXTERNAL_MAX) || 512 (!MaxDepth) || 513 (!UserFunction)) 514 { 515 return_ACPI_STATUS (AE_BAD_PARAMETER); 516 } 517 518 /* 519 * Lock the namespace around the walk. 520 * The namespace will be unlocked/locked around each call 521 * to the user function - since this function 522 * must be allowed to make Acpi calls itself. 523 */ 524 Status = AcpiUtAcquireMutex (ACPI_MTX_NAMESPACE); 525 if (ACPI_FAILURE (Status)) 526 { 527 return_ACPI_STATUS (Status); 528 } 529 530 Status = AcpiNsWalkNamespace (Type, StartObject, MaxDepth, 531 ACPI_NS_WALK_UNLOCK, 532 UserFunction, Context, ReturnValue); 533 534 (void) AcpiUtReleaseMutex (ACPI_MTX_NAMESPACE); 535 return_ACPI_STATUS (Status); 536} 537 538 539/******************************************************************************* 540 * 541 * FUNCTION: AcpiNsGetDeviceCallback 542 * 543 * PARAMETERS: Callback from AcpiGetDevice 544 * 545 * RETURN: Status 546 * 547 * DESCRIPTION: Takes callbacks from WalkNamespace and filters out all non- 548 * present devices, or if they specified a HID, it filters based 549 * on that. 550 * 551 ******************************************************************************/ 552 553static ACPI_STATUS 554AcpiNsGetDeviceCallback ( 555 ACPI_HANDLE ObjHandle, 556 UINT32 NestingLevel, 557 void *Context, 558 void **ReturnValue) 559{ 560 ACPI_GET_DEVICES_INFO *Info = Context; 561 ACPI_STATUS Status; 562 ACPI_NAMESPACE_NODE *Node; 563 UINT32 Flags; 564 ACPI_DEVICE_ID Hid; 565 ACPI_COMPATIBLE_ID_LIST *Cid; 566 ACPI_NATIVE_UINT i; 567 568 569 Status = AcpiUtAcquireMutex (ACPI_MTX_NAMESPACE); 570 if (ACPI_FAILURE (Status)) 571 { 572 return (Status); 573 } 574 575 Node = AcpiNsMapHandleToNode (ObjHandle); 576 Status = AcpiUtReleaseMutex (ACPI_MTX_NAMESPACE); 577 if (ACPI_FAILURE (Status)) 578 { 579 return (Status); 580 } 581 582 if (!Node) 583 { 584 return (AE_BAD_PARAMETER); 585 } 586 587 /* Run _STA to determine if device is present */ 588 589 Status = AcpiUtExecute_STA (Node, &Flags); 590 if (ACPI_FAILURE (Status)) 591 { 592 return (AE_CTRL_DEPTH); 593 } 594 595 if (!(Flags & 0x01)) 596 { 597 /* Don't return at the device or children of the device if not there */ 598 599 return (AE_CTRL_DEPTH); 600 } 601 602 /* Filter based on device HID & CID */ 603 604 if (Info->Hid != NULL) 605 { 606 Status = AcpiUtExecute_HID (Node, &Hid); 607 if (Status == AE_NOT_FOUND) 608 { 609 return (AE_OK); 610 } 611 else if (ACPI_FAILURE (Status)) 612 { 613 return (AE_CTRL_DEPTH); 614 } 615 616 if (ACPI_STRNCMP (Hid.Value, Info->Hid, sizeof (Hid.Value)) != 0) 617 { 618 /* Get the list of Compatible IDs */ 619 620 Status = AcpiUtExecute_CID (Node, &Cid); 621 if (Status == AE_NOT_FOUND) 622 { 623 return (AE_OK); 624 } 625 else if (ACPI_FAILURE (Status)) 626 { 627 return (AE_CTRL_DEPTH); 628 } 629 630 /* Walk the CID list */ 631 632 for (i = 0; i < Cid->Count; i++) 633 { 634 if (ACPI_STRNCMP (Cid->Id[i].Value, Info->Hid, 635 sizeof (ACPI_COMPATIBLE_ID)) != 0) 636 { 637 ACPI_MEM_FREE (Cid); 638 return (AE_OK); 639 } 640 } 641 ACPI_MEM_FREE (Cid); 642 } 643 } 644 645 Status = Info->UserFunction (ObjHandle, NestingLevel, Info->Context, 646 ReturnValue); 647 return (Status); 648} 649 650 651/******************************************************************************* 652 * 653 * FUNCTION: AcpiGetDevices 654 * 655 * PARAMETERS: HID - HID to search for. Can be NULL. 656 * UserFunction - Called when a matching object is found 657 * Context - Passed to user function 658 * ReturnValue - Location where return value of 659 * UserFunction is put if terminated early 660 * 661 * RETURNS Return value from the UserFunction if terminated early. 662 * Otherwise, returns NULL. 663 * 664 * DESCRIPTION: Performs a modified depth-first walk of the namespace tree, 665 * starting (and ending) at the object specified by StartHandle. 666 * The UserFunction is called whenever an object of type 667 * Device is found. If the user function returns 668 * a non-zero value, the search is terminated immediately and this 669 * value is returned to the caller. 670 * 671 * This is a wrapper for WalkNamespace, but the callback performs 672 * additional filtering. Please see AcpiGetDeviceCallback. 673 * 674 ******************************************************************************/ 675 676ACPI_STATUS 677AcpiGetDevices ( 678 char *HID, 679 ACPI_WALK_CALLBACK UserFunction, 680 void *Context, 681 void **ReturnValue) 682{ 683 ACPI_STATUS Status; 684 ACPI_GET_DEVICES_INFO Info; 685 686 687 ACPI_FUNCTION_TRACE ("AcpiGetDevices"); 688 689 690 /* Parameter validation */ 691 692 if (!UserFunction) 693 { 694 return_ACPI_STATUS (AE_BAD_PARAMETER); 695 } 696 697 /* 698 * We're going to call their callback from OUR callback, so we need 699 * to know what it is, and their context parameter. 700 */ 701 Info.Context = Context; 702 Info.UserFunction = UserFunction; 703 Info.Hid = HID; 704 705 /* 706 * Lock the namespace around the walk. 707 * The namespace will be unlocked/locked around each call 708 * to the user function - since this function 709 * must be allowed to make Acpi calls itself. 710 */ 711 Status = AcpiUtAcquireMutex (ACPI_MTX_NAMESPACE); 712 if (ACPI_FAILURE (Status)) 713 { 714 return_ACPI_STATUS (Status); 715 } 716 717 Status = AcpiNsWalkNamespace (ACPI_TYPE_DEVICE, 718 ACPI_ROOT_OBJECT, ACPI_UINT32_MAX, 719 ACPI_NS_WALK_UNLOCK, 720 AcpiNsGetDeviceCallback, &Info, 721 ReturnValue); 722 723 (void) AcpiUtReleaseMutex (ACPI_MTX_NAMESPACE); 724 return_ACPI_STATUS (Status); 725} 726 727 728/******************************************************************************* 729 * 730 * FUNCTION: AcpiAttachData 731 * 732 * PARAMETERS: ObjHandle - Namespace node 733 * Handler - Handler for this attachment 734 * Data - Pointer to data to be attached 735 * 736 * RETURN: Status 737 * 738 * DESCRIPTION: Attach arbitrary data and handler to a namespace node. 739 * 740 ******************************************************************************/ 741 742ACPI_STATUS 743AcpiAttachData ( 744 ACPI_HANDLE ObjHandle, 745 ACPI_OBJECT_HANDLER Handler, 746 void *Data) 747{ 748 ACPI_NAMESPACE_NODE *Node; 749 ACPI_STATUS Status; 750 751 752 /* Parameter validation */ 753 754 if (!ObjHandle || 755 !Handler || 756 !Data) 757 { 758 return (AE_BAD_PARAMETER); 759 } 760 761 Status = AcpiUtAcquireMutex (ACPI_MTX_NAMESPACE); 762 if (ACPI_FAILURE (Status)) 763 { 764 return (Status); 765 } 766 767 /* Convert and validate the handle */ 768 769 Node = AcpiNsMapHandleToNode (ObjHandle); 770 if (!Node) 771 { 772 Status = AE_BAD_PARAMETER; 773 goto UnlockAndExit; 774 } 775 776 Status = AcpiNsAttachData (Node, Handler, Data); 777 778UnlockAndExit: 779 (void) AcpiUtReleaseMutex (ACPI_MTX_NAMESPACE); 780 return (Status); 781} 782 783 784/******************************************************************************* 785 * 786 * FUNCTION: AcpiDetachData 787 * 788 * PARAMETERS: ObjHandle - Namespace node handle 789 * Handler - Handler used in call to AcpiAttachData 790 * 791 * RETURN: Status 792 * 793 * DESCRIPTION: Remove data that was previously attached to a node. 794 * 795 ******************************************************************************/ 796 797ACPI_STATUS 798AcpiDetachData ( 799 ACPI_HANDLE ObjHandle, 800 ACPI_OBJECT_HANDLER Handler) 801{ 802 ACPI_NAMESPACE_NODE *Node; 803 ACPI_STATUS Status; 804 805 806 /* Parameter validation */ 807 808 if (!ObjHandle || 809 !Handler) 810 { 811 return (AE_BAD_PARAMETER); 812 } 813 814 Status = AcpiUtAcquireMutex (ACPI_MTX_NAMESPACE); 815 if (ACPI_FAILURE (Status)) 816 { 817 return (Status); 818 } 819 820 /* Convert and validate the handle */ 821 822 Node = AcpiNsMapHandleToNode (ObjHandle); 823 if (!Node) 824 { 825 Status = AE_BAD_PARAMETER; 826 goto UnlockAndExit; 827 } 828 829 Status = AcpiNsDetachData (Node, Handler); 830 831UnlockAndExit: 832 (void) AcpiUtReleaseMutex (ACPI_MTX_NAMESPACE); 833 return (Status); 834} 835 836 837/******************************************************************************* 838 * 839 * FUNCTION: AcpiGetData 840 * 841 * PARAMETERS: ObjHandle - Namespace node 842 * Handler - Handler used in call to AttachData 843 * Data - Where the data is returned 844 * 845 * RETURN: Status 846 * 847 * DESCRIPTION: Retrieve data that was previously attached to a namespace node. 848 * 849 ******************************************************************************/ 850 851ACPI_STATUS 852AcpiGetData ( 853 ACPI_HANDLE ObjHandle, 854 ACPI_OBJECT_HANDLER Handler, 855 void **Data) 856{ 857 ACPI_NAMESPACE_NODE *Node; 858 ACPI_STATUS Status; 859 860 861 /* Parameter validation */ 862 863 if (!ObjHandle || 864 !Handler || 865 !Data) 866 { 867 return (AE_BAD_PARAMETER); 868 } 869 870 Status = AcpiUtAcquireMutex (ACPI_MTX_NAMESPACE); 871 if (ACPI_FAILURE (Status)) 872 { 873 return (Status); 874 } 875 876 /* Convert and validate the handle */ 877 878 Node = AcpiNsMapHandleToNode (ObjHandle); 879 if (!Node) 880 { 881 Status = AE_BAD_PARAMETER; 882 goto UnlockAndExit; 883 } 884 885 Status = AcpiNsGetAttachedData (Node, Handler, Data); 886 887UnlockAndExit: 888 (void) AcpiUtReleaseMutex (ACPI_MTX_NAMESPACE); 889 return (Status); 890} 891 892 893