1 /******************************************************************************* 2 * 3 * Module Name: utmisc - common utility procedures 4 * 5 ******************************************************************************/ 6 7 /* 8 * Copyright (C) 2000 - 2011, 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 45 #define __UTMISC_C__ 46 47 #include "acpi.h" 48 #include "accommon.h" 49 #include "acnamesp.h" 50 51 52 #define _COMPONENT ACPI_UTILITIES 53 ACPI_MODULE_NAME ("utmisc") 54 55 56 /******************************************************************************* 57 * 58 * FUNCTION: AcpiUtValidateException 59 * 60 * PARAMETERS: Status - The ACPI_STATUS code to be formatted 61 * 62 * RETURN: A string containing the exception text. NULL if exception is 63 * not valid. 64 * 65 * DESCRIPTION: This function validates and translates an ACPI exception into 66 * an ASCII string. 67 * 68 ******************************************************************************/ 69 70 const char * 71 AcpiUtValidateException ( 72 ACPI_STATUS Status) 73 { 74 UINT32 SubStatus; 75 const char *Exception = NULL; 76 77 78 ACPI_FUNCTION_ENTRY (); 79 80 81 /* 82 * Status is composed of two parts, a "type" and an actual code 83 */ 84 SubStatus = (Status & ~AE_CODE_MASK); 85 86 switch (Status & AE_CODE_MASK) 87 { 88 case AE_CODE_ENVIRONMENTAL: 89 90 if (SubStatus <= AE_CODE_ENV_MAX) 91 { 92 Exception = AcpiGbl_ExceptionNames_Env [SubStatus]; 93 } 94 break; 95 96 case AE_CODE_PROGRAMMER: 97 98 if (SubStatus <= AE_CODE_PGM_MAX) 99 { 100 Exception = AcpiGbl_ExceptionNames_Pgm [SubStatus]; 101 } 102 break; 103 104 case AE_CODE_ACPI_TABLES: 105 106 if (SubStatus <= AE_CODE_TBL_MAX) 107 { 108 Exception = AcpiGbl_ExceptionNames_Tbl [SubStatus]; 109 } 110 break; 111 112 case AE_CODE_AML: 113 114 if (SubStatus <= AE_CODE_AML_MAX) 115 { 116 Exception = AcpiGbl_ExceptionNames_Aml [SubStatus]; 117 } 118 break; 119 120 case AE_CODE_CONTROL: 121 122 if (SubStatus <= AE_CODE_CTRL_MAX) 123 { 124 Exception = AcpiGbl_ExceptionNames_Ctrl [SubStatus]; 125 } 126 break; 127 128 default: 129 break; 130 } 131 132 return (ACPI_CAST_PTR (const char, Exception)); 133 } 134 135 136 /******************************************************************************* 137 * 138 * FUNCTION: AcpiUtIsPciRootBridge 139 * 140 * PARAMETERS: Id - The HID/CID in string format 141 * 142 * RETURN: TRUE if the Id is a match for a PCI/PCI-Express Root Bridge 143 * 144 * DESCRIPTION: Determine if the input ID is a PCI Root Bridge ID. 145 * 146 ******************************************************************************/ 147 148 BOOLEAN 149 AcpiUtIsPciRootBridge ( 150 char *Id) 151 { 152 153 /* 154 * Check if this is a PCI root bridge. 155 * ACPI 3.0+: check for a PCI Express root also. 156 */ 157 if (!(ACPI_STRCMP (Id, 158 PCI_ROOT_HID_STRING)) || 159 160 !(ACPI_STRCMP (Id, 161 PCI_EXPRESS_ROOT_HID_STRING))) 162 { 163 return (TRUE); 164 } 165 166 return (FALSE); 167 } 168 169 170 /******************************************************************************* 171 * 172 * FUNCTION: AcpiUtIsAmlTable 173 * 174 * PARAMETERS: Table - An ACPI table 175 * 176 * RETURN: TRUE if table contains executable AML; FALSE otherwise 177 * 178 * DESCRIPTION: Check ACPI Signature for a table that contains AML code. 179 * Currently, these are DSDT,SSDT,PSDT. All other table types are 180 * data tables that do not contain AML code. 181 * 182 ******************************************************************************/ 183 184 BOOLEAN 185 AcpiUtIsAmlTable ( 186 ACPI_TABLE_HEADER *Table) 187 { 188 189 /* These are the only tables that contain executable AML */ 190 191 if (ACPI_COMPARE_NAME (Table->Signature, ACPI_SIG_DSDT) || 192 ACPI_COMPARE_NAME (Table->Signature, ACPI_SIG_PSDT) || 193 ACPI_COMPARE_NAME (Table->Signature, ACPI_SIG_SSDT)) 194 { 195 return (TRUE); 196 } 197 198 return (FALSE); 199 } 200 201 202 /******************************************************************************* 203 * 204 * FUNCTION: AcpiUtAllocateOwnerId 205 * 206 * PARAMETERS: OwnerId - Where the new owner ID is returned 207 * 208 * RETURN: Status 209 * 210 * DESCRIPTION: Allocate a table or method owner ID. The owner ID is used to 211 * track objects created by the table or method, to be deleted 212 * when the method exits or the table is unloaded. 213 * 214 ******************************************************************************/ 215 216 ACPI_STATUS 217 AcpiUtAllocateOwnerId ( 218 ACPI_OWNER_ID *OwnerId) 219 { 220 UINT32 i; 221 UINT32 j; 222 UINT32 k; 223 ACPI_STATUS Status; 224 225 226 ACPI_FUNCTION_TRACE (UtAllocateOwnerId); 227 228 229 /* Guard against multiple allocations of ID to the same location */ 230 231 if (*OwnerId) 232 { 233 ACPI_ERROR ((AE_INFO, "Owner ID [0x%2.2X] already exists", *OwnerId)); 234 return_ACPI_STATUS (AE_ALREADY_EXISTS); 235 } 236 237 /* Mutex for the global ID mask */ 238 239 Status = AcpiUtAcquireMutex (ACPI_MTX_CACHES); 240 if (ACPI_FAILURE (Status)) 241 { 242 return_ACPI_STATUS (Status); 243 } 244 245 /* 246 * Find a free owner ID, cycle through all possible IDs on repeated 247 * allocations. (ACPI_NUM_OWNERID_MASKS + 1) because first index may have 248 * to be scanned twice. 249 */ 250 for (i = 0, j = AcpiGbl_LastOwnerIdIndex; 251 i < (ACPI_NUM_OWNERID_MASKS + 1); 252 i++, j++) 253 { 254 if (j >= ACPI_NUM_OWNERID_MASKS) 255 { 256 j = 0; /* Wraparound to start of mask array */ 257 } 258 259 for (k = AcpiGbl_NextOwnerIdOffset; k < 32; k++) 260 { 261 if (AcpiGbl_OwnerIdMask[j] == ACPI_UINT32_MAX) 262 { 263 /* There are no free IDs in this mask */ 264 265 break; 266 } 267 268 if (!(AcpiGbl_OwnerIdMask[j] & (1 << k))) 269 { 270 /* 271 * Found a free ID. The actual ID is the bit index plus one, 272 * making zero an invalid Owner ID. Save this as the last ID 273 * allocated and update the global ID mask. 274 */ 275 AcpiGbl_OwnerIdMask[j] |= (1 << k); 276 277 AcpiGbl_LastOwnerIdIndex = (UINT8) j; 278 AcpiGbl_NextOwnerIdOffset = (UINT8) (k + 1); 279 280 /* 281 * Construct encoded ID from the index and bit position 282 * 283 * Note: Last [j].k (bit 255) is never used and is marked 284 * permanently allocated (prevents +1 overflow) 285 */ 286 *OwnerId = (ACPI_OWNER_ID) ((k + 1) + ACPI_MUL_32 (j)); 287 288 ACPI_DEBUG_PRINT ((ACPI_DB_VALUES, 289 "Allocated OwnerId: %2.2X\n", (unsigned int) *OwnerId)); 290 goto Exit; 291 } 292 } 293 294 AcpiGbl_NextOwnerIdOffset = 0; 295 } 296 297 /* 298 * All OwnerIds have been allocated. This typically should 299 * not happen since the IDs are reused after deallocation. The IDs are 300 * allocated upon table load (one per table) and method execution, and 301 * they are released when a table is unloaded or a method completes 302 * execution. 303 * 304 * If this error happens, there may be very deep nesting of invoked control 305 * methods, or there may be a bug where the IDs are not released. 306 */ 307 Status = AE_OWNER_ID_LIMIT; 308 ACPI_ERROR ((AE_INFO, 309 "Could not allocate new OwnerId (255 max), AE_OWNER_ID_LIMIT")); 310 311 Exit: 312 (void) AcpiUtReleaseMutex (ACPI_MTX_CACHES); 313 return_ACPI_STATUS (Status); 314 } 315 316 317 /******************************************************************************* 318 * 319 * FUNCTION: AcpiUtReleaseOwnerId 320 * 321 * PARAMETERS: OwnerIdPtr - Pointer to a previously allocated OwnerID 322 * 323 * RETURN: None. No error is returned because we are either exiting a 324 * control method or unloading a table. Either way, we would 325 * ignore any error anyway. 326 * 327 * DESCRIPTION: Release a table or method owner ID. Valid IDs are 1 - 255 328 * 329 ******************************************************************************/ 330 331 void 332 AcpiUtReleaseOwnerId ( 333 ACPI_OWNER_ID *OwnerIdPtr) 334 { 335 ACPI_OWNER_ID OwnerId = *OwnerIdPtr; 336 ACPI_STATUS Status; 337 UINT32 Index; 338 UINT32 Bit; 339 340 341 ACPI_FUNCTION_TRACE_U32 (UtReleaseOwnerId, OwnerId); 342 343 344 /* Always clear the input OwnerId (zero is an invalid ID) */ 345 346 *OwnerIdPtr = 0; 347 348 /* Zero is not a valid OwnerID */ 349 350 if (OwnerId == 0) 351 { 352 ACPI_ERROR ((AE_INFO, "Invalid OwnerId: 0x%2.2X", OwnerId)); 353 return_VOID; 354 } 355 356 /* Mutex for the global ID mask */ 357 358 Status = AcpiUtAcquireMutex (ACPI_MTX_CACHES); 359 if (ACPI_FAILURE (Status)) 360 { 361 return_VOID; 362 } 363 364 /* Normalize the ID to zero */ 365 366 OwnerId--; 367 368 /* Decode ID to index/offset pair */ 369 370 Index = ACPI_DIV_32 (OwnerId); 371 Bit = 1 << ACPI_MOD_32 (OwnerId); 372 373 /* Free the owner ID only if it is valid */ 374 375 if (AcpiGbl_OwnerIdMask[Index] & Bit) 376 { 377 AcpiGbl_OwnerIdMask[Index] ^= Bit; 378 } 379 else 380 { 381 ACPI_ERROR ((AE_INFO, 382 "Release of non-allocated OwnerId: 0x%2.2X", OwnerId + 1)); 383 } 384 385 (void) AcpiUtReleaseMutex (ACPI_MTX_CACHES); 386 return_VOID; 387 } 388 389 390 /******************************************************************************* 391 * 392 * FUNCTION: AcpiUtStrupr (strupr) 393 * 394 * PARAMETERS: SrcString - The source string to convert 395 * 396 * RETURN: None 397 * 398 * DESCRIPTION: Convert string to uppercase 399 * 400 * NOTE: This is not a POSIX function, so it appears here, not in utclib.c 401 * 402 ******************************************************************************/ 403 404 void 405 AcpiUtStrupr ( 406 char *SrcString) 407 { 408 char *String; 409 410 411 ACPI_FUNCTION_ENTRY (); 412 413 414 if (!SrcString) 415 { 416 return; 417 } 418 419 /* Walk entire string, uppercasing the letters */ 420 421 for (String = SrcString; *String; String++) 422 { 423 *String = (char) ACPI_TOUPPER (*String); 424 } 425 426 return; 427 } 428 429 430 #ifdef ACPI_ASL_COMPILER 431 /******************************************************************************* 432 * 433 * FUNCTION: AcpiUtStrlwr (strlwr) 434 * 435 * PARAMETERS: SrcString - The source string to convert 436 * 437 * RETURN: None 438 * 439 * DESCRIPTION: Convert string to lowercase 440 * 441 * NOTE: This is not a POSIX function, so it appears here, not in utclib.c 442 * 443 ******************************************************************************/ 444 445 void 446 AcpiUtStrlwr ( 447 char *SrcString) 448 { 449 char *String; 450 451 452 ACPI_FUNCTION_ENTRY (); 453 454 455 if (!SrcString) 456 { 457 return; 458 } 459 460 /* Walk entire string, lowercasing the letters */ 461 462 for (String = SrcString; *String; String++) 463 { 464 *String = (char) ACPI_TOLOWER (*String); 465 } 466 467 return; 468 } 469 #endif 470 471 472 /******************************************************************************* 473 * 474 * FUNCTION: AcpiUtPrintString 475 * 476 * PARAMETERS: String - Null terminated ASCII string 477 * MaxLength - Maximum output length 478 * 479 * RETURN: None 480 * 481 * DESCRIPTION: Dump an ASCII string with support for ACPI-defined escape 482 * sequences. 483 * 484 ******************************************************************************/ 485 486 void 487 AcpiUtPrintString ( 488 char *String, 489 UINT8 MaxLength) 490 { 491 UINT32 i; 492 493 494 if (!String) 495 { 496 AcpiOsPrintf ("<\"NULL STRING PTR\">"); 497 return; 498 } 499 500 AcpiOsPrintf ("\""); 501 for (i = 0; String[i] && (i < MaxLength); i++) 502 { 503 /* Escape sequences */ 504 505 switch (String[i]) 506 { 507 case 0x07: 508 AcpiOsPrintf ("\\a"); /* BELL */ 509 break; 510 511 case 0x08: 512 AcpiOsPrintf ("\\b"); /* BACKSPACE */ 513 break; 514 515 case 0x0C: 516 AcpiOsPrintf ("\\f"); /* FORMFEED */ 517 break; 518 519 case 0x0A: 520 AcpiOsPrintf ("\\n"); /* LINEFEED */ 521 break; 522 523 case 0x0D: 524 AcpiOsPrintf ("\\r"); /* CARRIAGE RETURN*/ 525 break; 526 527 case 0x09: 528 AcpiOsPrintf ("\\t"); /* HORIZONTAL TAB */ 529 break; 530 531 case 0x0B: 532 AcpiOsPrintf ("\\v"); /* VERTICAL TAB */ 533 break; 534 535 case '\'': /* Single Quote */ 536 case '\"': /* Double Quote */ 537 case '\\': /* Backslash */ 538 AcpiOsPrintf ("\\%c", (int) String[i]); 539 break; 540 541 default: 542 543 /* Check for printable character or hex escape */ 544 545 if (ACPI_IS_PRINT (String[i])) 546 { 547 /* This is a normal character */ 548 549 AcpiOsPrintf ("%c", (int) String[i]); 550 } 551 else 552 { 553 /* All others will be Hex escapes */ 554 555 AcpiOsPrintf ("\\x%2.2X", (INT32) String[i]); 556 } 557 break; 558 } 559 } 560 AcpiOsPrintf ("\""); 561 562 if (i == MaxLength && String[i]) 563 { 564 AcpiOsPrintf ("..."); 565 } 566 } 567 568 569 /******************************************************************************* 570 * 571 * FUNCTION: AcpiUtDwordByteSwap 572 * 573 * PARAMETERS: Value - Value to be converted 574 * 575 * RETURN: UINT32 integer with bytes swapped 576 * 577 * DESCRIPTION: Convert a 32-bit value to big-endian (swap the bytes) 578 * 579 ******************************************************************************/ 580 581 UINT32 582 AcpiUtDwordByteSwap ( 583 UINT32 Value) 584 { 585 union 586 { 587 UINT32 Value; 588 UINT8 Bytes[4]; 589 } Out; 590 union 591 { 592 UINT32 Value; 593 UINT8 Bytes[4]; 594 } In; 595 596 597 ACPI_FUNCTION_ENTRY (); 598 599 600 In.Value = Value; 601 602 Out.Bytes[0] = In.Bytes[3]; 603 Out.Bytes[1] = In.Bytes[2]; 604 Out.Bytes[2] = In.Bytes[1]; 605 Out.Bytes[3] = In.Bytes[0]; 606 607 return (Out.Value); 608 } 609 610 611 /******************************************************************************* 612 * 613 * FUNCTION: AcpiUtSetIntegerWidth 614 * 615 * PARAMETERS: Revision From DSDT header 616 * 617 * RETURN: None 618 * 619 * DESCRIPTION: Set the global integer bit width based upon the revision 620 * of the DSDT. For Revision 1 and 0, Integers are 32 bits. 621 * For Revision 2 and above, Integers are 64 bits. Yes, this 622 * makes a difference. 623 * 624 ******************************************************************************/ 625 626 void 627 AcpiUtSetIntegerWidth ( 628 UINT8 Revision) 629 { 630 631 if (Revision < 2) 632 { 633 /* 32-bit case */ 634 635 AcpiGbl_IntegerBitWidth = 32; 636 AcpiGbl_IntegerNybbleWidth = 8; 637 AcpiGbl_IntegerByteWidth = 4; 638 } 639 else 640 { 641 /* 64-bit case (ACPI 2.0+) */ 642 643 AcpiGbl_IntegerBitWidth = 64; 644 AcpiGbl_IntegerNybbleWidth = 16; 645 AcpiGbl_IntegerByteWidth = 8; 646 } 647 } 648 649 650 #ifdef ACPI_DEBUG_OUTPUT 651 /******************************************************************************* 652 * 653 * FUNCTION: AcpiUtDisplayInitPathname 654 * 655 * PARAMETERS: Type - Object type of the node 656 * ObjHandle - Handle whose pathname will be displayed 657 * Path - Additional path string to be appended. 658 * (NULL if no extra path) 659 * 660 * RETURN: ACPI_STATUS 661 * 662 * DESCRIPTION: Display full pathname of an object, DEBUG ONLY 663 * 664 ******************************************************************************/ 665 666 void 667 AcpiUtDisplayInitPathname ( 668 UINT8 Type, 669 ACPI_NAMESPACE_NODE *ObjHandle, 670 char *Path) 671 { 672 ACPI_STATUS Status; 673 ACPI_BUFFER Buffer; 674 675 676 ACPI_FUNCTION_ENTRY (); 677 678 679 /* Only print the path if the appropriate debug level is enabled */ 680 681 if (!(AcpiDbgLevel & ACPI_LV_INIT_NAMES)) 682 { 683 return; 684 } 685 686 /* Get the full pathname to the node */ 687 688 Buffer.Length = ACPI_ALLOCATE_LOCAL_BUFFER; 689 Status = AcpiNsHandleToPathname (ObjHandle, &Buffer); 690 if (ACPI_FAILURE (Status)) 691 { 692 return; 693 } 694 695 /* Print what we're doing */ 696 697 switch (Type) 698 { 699 case ACPI_TYPE_METHOD: 700 AcpiOsPrintf ("Executing "); 701 break; 702 703 default: 704 AcpiOsPrintf ("Initializing "); 705 break; 706 } 707 708 /* Print the object type and pathname */ 709 710 AcpiOsPrintf ("%-12s %s", 711 AcpiUtGetTypeName (Type), (char *) Buffer.Pointer); 712 713 /* Extra path is used to append names like _STA, _INI, etc. */ 714 715 if (Path) 716 { 717 AcpiOsPrintf (".%s", Path); 718 } 719 AcpiOsPrintf ("\n"); 720 721 ACPI_FREE (Buffer.Pointer); 722 } 723 #endif 724 725 726 /******************************************************************************* 727 * 728 * FUNCTION: AcpiUtValidAcpiChar 729 * 730 * PARAMETERS: Char - The character to be examined 731 * Position - Byte position (0-3) 732 * 733 * RETURN: TRUE if the character is valid, FALSE otherwise 734 * 735 * DESCRIPTION: Check for a valid ACPI character. Must be one of: 736 * 1) Upper case alpha 737 * 2) numeric 738 * 3) underscore 739 * 740 * We allow a '!' as the last character because of the ASF! table 741 * 742 ******************************************************************************/ 743 744 BOOLEAN 745 AcpiUtValidAcpiChar ( 746 char Character, 747 UINT32 Position) 748 { 749 750 if (!((Character >= 'A' && Character <= 'Z') || 751 (Character >= '0' && Character <= '9') || 752 (Character == '_'))) 753 { 754 /* Allow a '!' in the last position */ 755 756 if (Character == '!' && Position == 3) 757 { 758 return (TRUE); 759 } 760 761 return (FALSE); 762 } 763 764 return (TRUE); 765 } 766 767 768 /******************************************************************************* 769 * 770 * FUNCTION: AcpiUtValidAcpiName 771 * 772 * PARAMETERS: Name - The name to be examined 773 * 774 * RETURN: TRUE if the name is valid, FALSE otherwise 775 * 776 * DESCRIPTION: Check for a valid ACPI name. Each character must be one of: 777 * 1) Upper case alpha 778 * 2) numeric 779 * 3) underscore 780 * 781 ******************************************************************************/ 782 783 BOOLEAN 784 AcpiUtValidAcpiName ( 785 UINT32 Name) 786 { 787 UINT32 i; 788 789 790 ACPI_FUNCTION_ENTRY (); 791 792 793 for (i = 0; i < ACPI_NAME_SIZE; i++) 794 { 795 if (!AcpiUtValidAcpiChar ((ACPI_CAST_PTR (char, &Name))[i], i)) 796 { 797 return (FALSE); 798 } 799 } 800 801 return (TRUE); 802 } 803 804 805 /******************************************************************************* 806 * 807 * FUNCTION: AcpiUtRepairName 808 * 809 * PARAMETERS: Name - The ACPI name to be repaired 810 * 811 * RETURN: Repaired version of the name 812 * 813 * DESCRIPTION: Repair an ACPI name: Change invalid characters to '*' and 814 * return the new name. NOTE: the Name parameter must reside in 815 * read/write memory, cannot be a const. 816 * 817 * An ACPI Name must consist of valid ACPI characters. We will repair the name 818 * if necessary because we don't want to abort because of this, but we want 819 * all namespace names to be printable. A warning message is appropriate. 820 * 821 * This issue came up because there are in fact machines that exhibit 822 * this problem, and we want to be able to enable ACPI support for them, 823 * even though there are a few bad names. 824 * 825 ******************************************************************************/ 826 827 void 828 AcpiUtRepairName ( 829 char *Name) 830 { 831 UINT32 i; 832 BOOLEAN FoundBadChar = FALSE; 833 834 835 ACPI_FUNCTION_NAME (UtRepairName); 836 837 838 /* Check each character in the name */ 839 840 for (i = 0; i < ACPI_NAME_SIZE; i++) 841 { 842 if (AcpiUtValidAcpiChar (Name[i], i)) 843 { 844 continue; 845 } 846 847 /* 848 * Replace a bad character with something printable, yet technically 849 * still invalid. This prevents any collisions with existing "good" 850 * names in the namespace. 851 */ 852 Name[i] = '*'; 853 FoundBadChar = TRUE; 854 } 855 856 if (FoundBadChar) 857 { 858 /* Report warning only if in strict mode or debug mode */ 859 860 if (!AcpiGbl_EnableInterpreterSlack) 861 { 862 ACPI_WARNING ((AE_INFO, 863 "Found bad character(s) in name, repaired: [%4.4s]\n", Name)); 864 } 865 else 866 { 867 ACPI_DEBUG_PRINT ((ACPI_DB_INFO, 868 "Found bad character(s) in name, repaired: [%4.4s]\n", Name)); 869 } 870 } 871 } 872 873 874 /******************************************************************************* 875 * 876 * FUNCTION: AcpiUtStrtoul64 877 * 878 * PARAMETERS: String - Null terminated string 879 * Base - Radix of the string: 16 or ACPI_ANY_BASE; 880 * ACPI_ANY_BASE means 'in behalf of ToInteger' 881 * RetInteger - Where the converted integer is returned 882 * 883 * RETURN: Status and Converted value 884 * 885 * DESCRIPTION: Convert a string into an unsigned value. Performs either a 886 * 32-bit or 64-bit conversion, depending on the current mode 887 * of the interpreter. 888 * NOTE: Does not support Octal strings, not needed. 889 * 890 ******************************************************************************/ 891 892 ACPI_STATUS 893 AcpiUtStrtoul64 ( 894 char *String, 895 UINT32 Base, 896 UINT64 *RetInteger) 897 { 898 UINT32 ThisDigit = 0; 899 UINT64 ReturnValue = 0; 900 UINT64 Quotient; 901 UINT64 Dividend; 902 UINT32 ToIntegerOp = (Base == ACPI_ANY_BASE); 903 UINT32 Mode32 = (AcpiGbl_IntegerByteWidth == 4); 904 UINT8 ValidDigits = 0; 905 UINT8 SignOf0x = 0; 906 UINT8 Term = 0; 907 908 909 ACPI_FUNCTION_TRACE_STR (UtStroul64, String); 910 911 912 switch (Base) 913 { 914 case ACPI_ANY_BASE: 915 case 16: 916 break; 917 918 default: 919 /* Invalid Base */ 920 return_ACPI_STATUS (AE_BAD_PARAMETER); 921 } 922 923 if (!String) 924 { 925 goto ErrorExit; 926 } 927 928 /* Skip over any white space in the buffer */ 929 930 while ((*String) && (ACPI_IS_SPACE (*String) || *String == '\t')) 931 { 932 String++; 933 } 934 935 if (ToIntegerOp) 936 { 937 /* 938 * Base equal to ACPI_ANY_BASE means 'ToInteger operation case'. 939 * We need to determine if it is decimal or hexadecimal. 940 */ 941 if ((*String == '0') && (ACPI_TOLOWER (*(String + 1)) == 'x')) 942 { 943 SignOf0x = 1; 944 Base = 16; 945 946 /* Skip over the leading '0x' */ 947 String += 2; 948 } 949 else 950 { 951 Base = 10; 952 } 953 } 954 955 /* Any string left? Check that '0x' is not followed by white space. */ 956 957 if (!(*String) || ACPI_IS_SPACE (*String) || *String == '\t') 958 { 959 if (ToIntegerOp) 960 { 961 goto ErrorExit; 962 } 963 else 964 { 965 goto AllDone; 966 } 967 } 968 969 /* 970 * Perform a 32-bit or 64-bit conversion, depending upon the current 971 * execution mode of the interpreter 972 */ 973 Dividend = (Mode32) ? ACPI_UINT32_MAX : ACPI_UINT64_MAX; 974 975 /* Main loop: convert the string to a 32- or 64-bit integer */ 976 977 while (*String) 978 { 979 if (ACPI_IS_DIGIT (*String)) 980 { 981 /* Convert ASCII 0-9 to Decimal value */ 982 983 ThisDigit = ((UINT8) *String) - '0'; 984 } 985 else if (Base == 10) 986 { 987 /* Digit is out of range; possible in ToInteger case only */ 988 989 Term = 1; 990 } 991 else 992 { 993 ThisDigit = (UINT8) ACPI_TOUPPER (*String); 994 if (ACPI_IS_XDIGIT ((char) ThisDigit)) 995 { 996 /* Convert ASCII Hex char to value */ 997 998 ThisDigit = ThisDigit - 'A' + 10; 999 } 1000 else 1001 { 1002 Term = 1; 1003 } 1004 } 1005 1006 if (Term) 1007 { 1008 if (ToIntegerOp) 1009 { 1010 goto ErrorExit; 1011 } 1012 else 1013 { 1014 break; 1015 } 1016 } 1017 else if ((ValidDigits == 0) && (ThisDigit == 0) && !SignOf0x) 1018 { 1019 /* Skip zeros */ 1020 String++; 1021 continue; 1022 } 1023 1024 ValidDigits++; 1025 1026 if (SignOf0x && ((ValidDigits > 16) || ((ValidDigits > 8) && Mode32))) 1027 { 1028 /* 1029 * This is ToInteger operation case. 1030 * No any restrictions for string-to-integer conversion, 1031 * see ACPI spec. 1032 */ 1033 goto ErrorExit; 1034 } 1035 1036 /* Divide the digit into the correct position */ 1037 1038 (void) AcpiUtShortDivide ((Dividend - (UINT64) ThisDigit), 1039 Base, &Quotient, NULL); 1040 1041 if (ReturnValue > Quotient) 1042 { 1043 if (ToIntegerOp) 1044 { 1045 goto ErrorExit; 1046 } 1047 else 1048 { 1049 break; 1050 } 1051 } 1052 1053 ReturnValue *= Base; 1054 ReturnValue += ThisDigit; 1055 String++; 1056 } 1057 1058 /* All done, normal exit */ 1059 1060 AllDone: 1061 1062 ACPI_DEBUG_PRINT ((ACPI_DB_EXEC, "Converted value: %8.8X%8.8X\n", 1063 ACPI_FORMAT_UINT64 (ReturnValue))); 1064 1065 *RetInteger = ReturnValue; 1066 return_ACPI_STATUS (AE_OK); 1067 1068 1069 ErrorExit: 1070 /* Base was set/validated above */ 1071 1072 if (Base == 10) 1073 { 1074 return_ACPI_STATUS (AE_BAD_DECIMAL_CONSTANT); 1075 } 1076 else 1077 { 1078 return_ACPI_STATUS (AE_BAD_HEX_CONSTANT); 1079 } 1080 } 1081 1082 1083 /******************************************************************************* 1084 * 1085 * FUNCTION: AcpiUtCreateUpdateStateAndPush 1086 * 1087 * PARAMETERS: Object - Object to be added to the new state 1088 * Action - Increment/Decrement 1089 * StateList - List the state will be added to 1090 * 1091 * RETURN: Status 1092 * 1093 * DESCRIPTION: Create a new state and push it 1094 * 1095 ******************************************************************************/ 1096 1097 ACPI_STATUS 1098 AcpiUtCreateUpdateStateAndPush ( 1099 ACPI_OPERAND_OBJECT *Object, 1100 UINT16 Action, 1101 ACPI_GENERIC_STATE **StateList) 1102 { 1103 ACPI_GENERIC_STATE *State; 1104 1105 1106 ACPI_FUNCTION_ENTRY (); 1107 1108 1109 /* Ignore null objects; these are expected */ 1110 1111 if (!Object) 1112 { 1113 return (AE_OK); 1114 } 1115 1116 State = AcpiUtCreateUpdateState (Object, Action); 1117 if (!State) 1118 { 1119 return (AE_NO_MEMORY); 1120 } 1121 1122 AcpiUtPushGenericState (StateList, State); 1123 return (AE_OK); 1124 } 1125 1126 1127 /******************************************************************************* 1128 * 1129 * FUNCTION: AcpiUtWalkPackageTree 1130 * 1131 * PARAMETERS: SourceObject - The package to walk 1132 * TargetObject - Target object (if package is being copied) 1133 * WalkCallback - Called once for each package element 1134 * Context - Passed to the callback function 1135 * 1136 * RETURN: Status 1137 * 1138 * DESCRIPTION: Walk through a package 1139 * 1140 ******************************************************************************/ 1141 1142 ACPI_STATUS 1143 AcpiUtWalkPackageTree ( 1144 ACPI_OPERAND_OBJECT *SourceObject, 1145 void *TargetObject, 1146 ACPI_PKG_CALLBACK WalkCallback, 1147 void *Context) 1148 { 1149 ACPI_STATUS Status = AE_OK; 1150 ACPI_GENERIC_STATE *StateList = NULL; 1151 ACPI_GENERIC_STATE *State; 1152 UINT32 ThisIndex; 1153 ACPI_OPERAND_OBJECT *ThisSourceObj; 1154 1155 1156 ACPI_FUNCTION_TRACE (UtWalkPackageTree); 1157 1158 1159 State = AcpiUtCreatePkgState (SourceObject, TargetObject, 0); 1160 if (!State) 1161 { 1162 return_ACPI_STATUS (AE_NO_MEMORY); 1163 } 1164 1165 while (State) 1166 { 1167 /* Get one element of the package */ 1168 1169 ThisIndex = State->Pkg.Index; 1170 ThisSourceObj = (ACPI_OPERAND_OBJECT *) 1171 State->Pkg.SourceObject->Package.Elements[ThisIndex]; 1172 1173 /* 1174 * Check for: 1175 * 1) An uninitialized package element. It is completely 1176 * legal to declare a package and leave it uninitialized 1177 * 2) Not an internal object - can be a namespace node instead 1178 * 3) Any type other than a package. Packages are handled in else 1179 * case below. 1180 */ 1181 if ((!ThisSourceObj) || 1182 (ACPI_GET_DESCRIPTOR_TYPE (ThisSourceObj) != ACPI_DESC_TYPE_OPERAND) || 1183 (ThisSourceObj->Common.Type != ACPI_TYPE_PACKAGE)) 1184 { 1185 Status = WalkCallback (ACPI_COPY_TYPE_SIMPLE, ThisSourceObj, 1186 State, Context); 1187 if (ACPI_FAILURE (Status)) 1188 { 1189 return_ACPI_STATUS (Status); 1190 } 1191 1192 State->Pkg.Index++; 1193 while (State->Pkg.Index >= State->Pkg.SourceObject->Package.Count) 1194 { 1195 /* 1196 * We've handled all of the objects at this level, This means 1197 * that we have just completed a package. That package may 1198 * have contained one or more packages itself. 1199 * 1200 * Delete this state and pop the previous state (package). 1201 */ 1202 AcpiUtDeleteGenericState (State); 1203 State = AcpiUtPopGenericState (&StateList); 1204 1205 /* Finished when there are no more states */ 1206 1207 if (!State) 1208 { 1209 /* 1210 * We have handled all of the objects in the top level 1211 * package just add the length of the package objects 1212 * and exit 1213 */ 1214 return_ACPI_STATUS (AE_OK); 1215 } 1216 1217 /* 1218 * Go back up a level and move the index past the just 1219 * completed package object. 1220 */ 1221 State->Pkg.Index++; 1222 } 1223 } 1224 else 1225 { 1226 /* This is a subobject of type package */ 1227 1228 Status = WalkCallback (ACPI_COPY_TYPE_PACKAGE, ThisSourceObj, 1229 State, Context); 1230 if (ACPI_FAILURE (Status)) 1231 { 1232 return_ACPI_STATUS (Status); 1233 } 1234 1235 /* 1236 * Push the current state and create a new one 1237 * The callback above returned a new target package object. 1238 */ 1239 AcpiUtPushGenericState (&StateList, State); 1240 State = AcpiUtCreatePkgState (ThisSourceObj, 1241 State->Pkg.ThisTargetObj, 0); 1242 if (!State) 1243 { 1244 /* Free any stacked Update State objects */ 1245 1246 while (StateList) 1247 { 1248 State = AcpiUtPopGenericState (&StateList); 1249 AcpiUtDeleteGenericState (State); 1250 } 1251 return_ACPI_STATUS (AE_NO_MEMORY); 1252 } 1253 } 1254 } 1255 1256 /* We should never get here */ 1257 1258 return_ACPI_STATUS (AE_AML_INTERNAL); 1259 } 1260 1261 1262