hwsleep.c revision 128212
1112163Sdas 2112163Sdas/****************************************************************************** 3112202Sobrien * 4112202Sobrien * Name: hwsleep.c - ACPI Hardware Sleep/Wake Interface 5112202Sobrien * $Revision: 66 $ 6178140Sdas * 7140279Sdas *****************************************************************************/ 8112163Sdas 9140889Sdas/****************************************************************************** 10112202Sobrien * 11156613Sdeischen * 1. Copyright Notice 12156613Sdeischen * 13112202Sobrien * Some or all of this work - Copyright (c) 1999 - 2004, Intel Corp. 14112202Sobrien * All rights reserved. 15112163Sdas * 16112163Sdas * 2. License 17112163Sdas * 18112163Sdas * 2.1. This is your license from Intel Corp. under its intellectual property 19112163Sdas * rights. You may have additional license terms from the party that provided 20112163Sdas * 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#include "acpi.h" 119 120#define _COMPONENT ACPI_HARDWARE 121 ACPI_MODULE_NAME ("hwsleep") 122 123 124#define METHOD_NAME__BFS "\\_BFS" 125#define METHOD_NAME__GTS "\\_GTS" 126#define METHOD_NAME__PTS "\\_PTS" 127#define METHOD_NAME__SST "\\_SI._SST" 128#define METHOD_NAME__WAK "\\_WAK" 129 130#define ACPI_SST_INDICATOR_OFF 0 131#define ACPI_SST_WORKING 1 132#define ACPI_SST_WAKING 2 133#define ACPI_SST_SLEEPING 3 134#define ACPI_SST_SLEEP_CONTEXT 4 135 136 137/****************************************************************************** 138 * 139 * FUNCTION: AcpiSetFirmwareWakingVector 140 * 141 * PARAMETERS: PhysicalAddress - Physical address of ACPI real mode 142 * entry point. 143 * 144 * RETURN: Status 145 * 146 * DESCRIPTION: Access function for dFirmwareWakingVector field in FACS 147 * 148 ******************************************************************************/ 149 150ACPI_STATUS 151AcpiSetFirmwareWakingVector ( 152 ACPI_PHYSICAL_ADDRESS PhysicalAddress) 153{ 154 155 ACPI_FUNCTION_TRACE ("AcpiSetFirmwareWakingVector"); 156 157 158 /* Set the vector */ 159 160 if (AcpiGbl_CommonFACS.VectorWidth == 32) 161 { 162 *(ACPI_CAST_PTR (UINT32, AcpiGbl_CommonFACS.FirmwareWakingVector)) 163 = (UINT32) PhysicalAddress; 164 } 165 else 166 { 167 *AcpiGbl_CommonFACS.FirmwareWakingVector 168 = PhysicalAddress; 169 } 170 171 return_ACPI_STATUS (AE_OK); 172} 173 174 175/****************************************************************************** 176 * 177 * FUNCTION: AcpiGetFirmwareWakingVector 178 * 179 * PARAMETERS: *PhysicalAddress - Output buffer where contents of 180 * the FirmwareWakingVector field of 181 * the FACS will be stored. 182 * 183 * RETURN: Status 184 * 185 * DESCRIPTION: Access function for FirmwareWakingVector field in FACS 186 * 187 ******************************************************************************/ 188 189ACPI_STATUS 190AcpiGetFirmwareWakingVector ( 191 ACPI_PHYSICAL_ADDRESS *PhysicalAddress) 192{ 193 194 ACPI_FUNCTION_TRACE ("AcpiGetFirmwareWakingVector"); 195 196 197 if (!PhysicalAddress) 198 { 199 return_ACPI_STATUS (AE_BAD_PARAMETER); 200 } 201 202 /* Get the vector */ 203 204 if (AcpiGbl_CommonFACS.VectorWidth == 32) 205 { 206 *PhysicalAddress = (ACPI_PHYSICAL_ADDRESS) 207 *(ACPI_CAST_PTR (UINT32, AcpiGbl_CommonFACS.FirmwareWakingVector)); 208 } 209 else 210 { 211 *PhysicalAddress = 212 *AcpiGbl_CommonFACS.FirmwareWakingVector; 213 } 214 215 return_ACPI_STATUS (AE_OK); 216} 217 218 219/****************************************************************************** 220 * 221 * FUNCTION: AcpiEnterSleepStatePrep 222 * 223 * PARAMETERS: SleepState - Which sleep state to enter 224 * 225 * RETURN: Status 226 * 227 * DESCRIPTION: Prepare to enter a system sleep state (see ACPI 2.0 spec p 231) 228 * This function must execute with interrupts enabled. 229 * We break sleeping into 2 stages so that OSPM can handle 230 * various OS-specific tasks between the two steps. 231 * 232 ******************************************************************************/ 233 234ACPI_STATUS 235AcpiEnterSleepStatePrep ( 236 UINT8 SleepState) 237{ 238 ACPI_STATUS Status; 239 ACPI_OBJECT_LIST ArgList; 240 ACPI_OBJECT Arg; 241 242 243 ACPI_FUNCTION_TRACE ("AcpiEnterSleepStatePrep"); 244 245 246 /* 247 * _PSW methods could be run here to enable wake-on keyboard, LAN, etc. 248 */ 249 Status = AcpiGetSleepTypeData (SleepState, 250 &AcpiGbl_SleepTypeA, &AcpiGbl_SleepTypeB); 251 if (ACPI_FAILURE (Status)) 252 { 253 return_ACPI_STATUS (Status); 254 } 255 256 /* Setup parameter object */ 257 258 ArgList.Count = 1; 259 ArgList.Pointer = &Arg; 260 261 Arg.Type = ACPI_TYPE_INTEGER; 262 Arg.Integer.Value = SleepState; 263 264 /* Run the _PTS and _GTS methods */ 265 266 Status = AcpiEvaluateObject (NULL, METHOD_NAME__PTS, &ArgList, NULL); 267 if (ACPI_FAILURE (Status) && Status != AE_NOT_FOUND) 268 { 269 return_ACPI_STATUS (Status); 270 } 271 272 Status = AcpiEvaluateObject (NULL, METHOD_NAME__GTS, &ArgList, NULL); 273 if (ACPI_FAILURE (Status) && Status != AE_NOT_FOUND) 274 { 275 return_ACPI_STATUS (Status); 276 } 277 278 /* Setup the argument to _SST */ 279 280 switch (SleepState) 281 { 282 case ACPI_STATE_S0: 283 Arg.Integer.Value = ACPI_SST_WORKING; 284 break; 285 286 case ACPI_STATE_S1: 287 case ACPI_STATE_S2: 288 case ACPI_STATE_S3: 289 Arg.Integer.Value = ACPI_SST_SLEEPING; 290 break; 291 292 case ACPI_STATE_S4: 293 Arg.Integer.Value = ACPI_SST_SLEEP_CONTEXT; 294 break; 295 296 default: 297 Arg.Integer.Value = ACPI_SST_INDICATOR_OFF; /* Default is indicator off */ 298 break; 299 } 300 301 /* Set the system indicators to show the desired sleep state. */ 302 303 Status = AcpiEvaluateObject (NULL, METHOD_NAME__SST, &ArgList, NULL); 304 if (ACPI_FAILURE (Status) && Status != AE_NOT_FOUND) 305 { 306 ACPI_REPORT_ERROR (("Method _SST failed, %s\n", AcpiFormatException (Status))); 307 } 308 309 return_ACPI_STATUS (AE_OK); 310} 311 312 313/****************************************************************************** 314 * 315 * FUNCTION: AcpiEnterSleepState 316 * 317 * PARAMETERS: SleepState - Which sleep state to enter 318 * 319 * RETURN: Status 320 * 321 * DESCRIPTION: Enter a system sleep state (see ACPI 2.0 spec p 231) 322 * THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED 323 * 324 ******************************************************************************/ 325 326ACPI_STATUS 327AcpiEnterSleepState ( 328 UINT8 SleepState) 329{ 330 UINT32 PM1AControl; 331 UINT32 PM1BControl; 332 ACPI_BIT_REGISTER_INFO *SleepTypeRegInfo; 333 ACPI_BIT_REGISTER_INFO *SleepEnableRegInfo; 334 UINT32 InValue; 335 ACPI_STATUS Status; 336 337 338 ACPI_FUNCTION_TRACE ("AcpiEnterSleepState"); 339 340 341 if ((AcpiGbl_SleepTypeA > ACPI_SLEEP_TYPE_MAX) || 342 (AcpiGbl_SleepTypeB > ACPI_SLEEP_TYPE_MAX)) 343 { 344 ACPI_REPORT_ERROR (("Sleep values out of range: A=%X B=%X\n", 345 AcpiGbl_SleepTypeA, AcpiGbl_SleepTypeB)); 346 return_ACPI_STATUS (AE_AML_OPERAND_VALUE); 347 } 348 349 SleepTypeRegInfo = AcpiHwGetBitRegisterInfo (ACPI_BITREG_SLEEP_TYPE_A); 350 SleepEnableRegInfo = AcpiHwGetBitRegisterInfo (ACPI_BITREG_SLEEP_ENABLE); 351 352 if (SleepState != ACPI_STATE_S5) 353 { 354 /* Clear wake status */ 355 356 Status = AcpiSetRegister (ACPI_BITREG_WAKE_STATUS, 1, ACPI_MTX_DO_NOT_LOCK); 357 if (ACPI_FAILURE (Status)) 358 { 359 return_ACPI_STATUS (Status); 360 } 361 362 Status = AcpiHwClearAcpiStatus (ACPI_MTX_DO_NOT_LOCK); 363 if (ACPI_FAILURE (Status)) 364 { 365 return_ACPI_STATUS (Status); 366 } 367 368 /* Disable BM arbitration */ 369 370 Status = AcpiSetRegister (ACPI_BITREG_ARB_DISABLE, 1, ACPI_MTX_DO_NOT_LOCK); 371 if (ACPI_FAILURE (Status)) 372 { 373 return_ACPI_STATUS (Status); 374 } 375 } 376 377 /* 378 * 1) Disable all runtime GPEs 379 * 2) Enable all wakeup GPEs 380 */ 381 Status = AcpiHwPrepareGpesForSleep (); 382 if (ACPI_FAILURE (Status)) 383 { 384 return_ACPI_STATUS (Status); 385 } 386 387 /* Get current value of PM1A control */ 388 389 Status = AcpiHwRegisterRead (ACPI_MTX_DO_NOT_LOCK, ACPI_REGISTER_PM1_CONTROL, &PM1AControl); 390 if (ACPI_FAILURE (Status)) 391 { 392 return_ACPI_STATUS (Status); 393 } 394 ACPI_DEBUG_PRINT ((ACPI_DB_INIT, "Entering sleep state [S%d]\n", SleepState)); 395 396 /* Clear SLP_EN and SLP_TYP fields */ 397 398 PM1AControl &= ~(SleepTypeRegInfo->AccessBitMask | SleepEnableRegInfo->AccessBitMask); 399 PM1BControl = PM1AControl; 400 401 /* Insert SLP_TYP bits */ 402 403 PM1AControl |= (AcpiGbl_SleepTypeA << SleepTypeRegInfo->BitPosition); 404 PM1BControl |= (AcpiGbl_SleepTypeB << SleepTypeRegInfo->BitPosition); 405 406 /* 407 * We split the writes of SLP_TYP and SLP_EN to workaround 408 * poorly implemented hardware. 409 */ 410 411 /* Write #1: fill in SLP_TYP data */ 412 413 Status = AcpiHwRegisterWrite (ACPI_MTX_DO_NOT_LOCK, ACPI_REGISTER_PM1A_CONTROL, PM1AControl); 414 if (ACPI_FAILURE (Status)) 415 { 416 return_ACPI_STATUS (Status); 417 } 418 419 Status = AcpiHwRegisterWrite (ACPI_MTX_DO_NOT_LOCK, ACPI_REGISTER_PM1B_CONTROL, PM1BControl); 420 if (ACPI_FAILURE (Status)) 421 { 422 return_ACPI_STATUS (Status); 423 } 424 425 /* Insert SLP_ENABLE bit */ 426 427 PM1AControl |= SleepEnableRegInfo->AccessBitMask; 428 PM1BControl |= SleepEnableRegInfo->AccessBitMask; 429 430 /* Write #2: SLP_TYP + SLP_EN */ 431 432 ACPI_FLUSH_CPU_CACHE (); 433 434 Status = AcpiHwRegisterWrite (ACPI_MTX_DO_NOT_LOCK, ACPI_REGISTER_PM1A_CONTROL, PM1AControl); 435 if (ACPI_FAILURE (Status)) 436 { 437 return_ACPI_STATUS (Status); 438 } 439 440 Status = AcpiHwRegisterWrite (ACPI_MTX_DO_NOT_LOCK, ACPI_REGISTER_PM1B_CONTROL, PM1BControl); 441 if (ACPI_FAILURE (Status)) 442 { 443 return_ACPI_STATUS (Status); 444 } 445 446 if (SleepState > ACPI_STATE_S3) 447 { 448 /* 449 * We wanted to sleep > S3, but it didn't happen (by virtue of the fact that 450 * we are still executing!) 451 * 452 * Wait ten seconds, then try again. This is to get S4/S5 to work on all machines. 453 * 454 * We wait so long to allow chipsets that poll this reg very slowly to 455 * still read the right value. Ideally, this block would go 456 * away entirely. 457 */ 458 AcpiOsStall (10000000); 459 460 Status = AcpiHwRegisterWrite (ACPI_MTX_DO_NOT_LOCK, ACPI_REGISTER_PM1_CONTROL, 461 SleepEnableRegInfo->AccessBitMask); 462 if (ACPI_FAILURE (Status)) 463 { 464 return_ACPI_STATUS (Status); 465 } 466 } 467 468 /* Wait until we enter sleep state */ 469 470 do 471 { 472 Status = AcpiGetRegister (ACPI_BITREG_WAKE_STATUS, &InValue, ACPI_MTX_DO_NOT_LOCK); 473 if (ACPI_FAILURE (Status)) 474 { 475 return_ACPI_STATUS (Status); 476 } 477 478 /* Spin until we wake */ 479 480 } while (!InValue); 481 482 return_ACPI_STATUS (AE_OK); 483} 484 485 486/****************************************************************************** 487 * 488 * FUNCTION: AcpiEnterSleepStateS4bios 489 * 490 * PARAMETERS: None 491 * 492 * RETURN: Status 493 * 494 * DESCRIPTION: Perform a S4 bios request. 495 * THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED 496 * 497 ******************************************************************************/ 498 499ACPI_STATUS 500AcpiEnterSleepStateS4bios ( 501 void) 502{ 503 UINT32 InValue; 504 ACPI_STATUS Status; 505 506 507 ACPI_FUNCTION_TRACE ("AcpiEnterSleepStateS4bios"); 508 509 510 Status = AcpiSetRegister (ACPI_BITREG_WAKE_STATUS, 1, ACPI_MTX_DO_NOT_LOCK); 511 if (ACPI_FAILURE (Status)) 512 { 513 return_ACPI_STATUS (Status); 514 } 515 516 Status = AcpiHwClearAcpiStatus (ACPI_MTX_DO_NOT_LOCK); 517 if (ACPI_FAILURE (Status)) 518 { 519 return_ACPI_STATUS (Status); 520 } 521 522 /* 523 * 1) Disable all runtime GPEs 524 * 2) Enable all wakeup GPEs 525 */ 526 Status = AcpiHwPrepareGpesForSleep (); 527 if (ACPI_FAILURE (Status)) 528 { 529 return_ACPI_STATUS (Status); 530 } 531 532 ACPI_FLUSH_CPU_CACHE (); 533 534 Status = AcpiOsWritePort (AcpiGbl_FADT->SmiCmd, (UINT32) AcpiGbl_FADT->S4BiosReq, 8); 535 536 do { 537 AcpiOsStall(1000); 538 Status = AcpiGetRegister (ACPI_BITREG_WAKE_STATUS, &InValue, ACPI_MTX_DO_NOT_LOCK); 539 if (ACPI_FAILURE (Status)) 540 { 541 return_ACPI_STATUS (Status); 542 } 543 } while (!InValue); 544 545 return_ACPI_STATUS (AE_OK); 546} 547 548 549/****************************************************************************** 550 * 551 * FUNCTION: AcpiLeaveSleepState 552 * 553 * PARAMETERS: SleepState - Which sleep state we just exited 554 * 555 * RETURN: Status 556 * 557 * DESCRIPTION: Perform OS-independent ACPI cleanup after a sleep 558 * 559 ******************************************************************************/ 560 561ACPI_STATUS 562AcpiLeaveSleepState ( 563 UINT8 SleepState) 564{ 565 ACPI_OBJECT_LIST ArgList; 566 ACPI_OBJECT Arg; 567 ACPI_STATUS Status; 568 ACPI_BIT_REGISTER_INFO *SleepTypeRegInfo; 569 ACPI_BIT_REGISTER_INFO *SleepEnableRegInfo; 570 UINT32 PM1AControl; 571 UINT32 PM1BControl; 572 573 574 ACPI_FUNCTION_TRACE ("AcpiLeaveSleepState"); 575 576 577 /* 578 * Set SLP_TYPE and SLP_EN to state S0. 579 * This is unclear from the ACPI Spec, but it is required 580 * by some machines. 581 */ 582 Status = AcpiGetSleepTypeData (ACPI_STATE_S0, 583 &AcpiGbl_SleepTypeA, &AcpiGbl_SleepTypeB); 584 if (ACPI_SUCCESS (Status)) 585 { 586 SleepTypeRegInfo = AcpiHwGetBitRegisterInfo (ACPI_BITREG_SLEEP_TYPE_A); 587 SleepEnableRegInfo = AcpiHwGetBitRegisterInfo (ACPI_BITREG_SLEEP_ENABLE); 588 589 /* Get current value of PM1A control */ 590 591 Status = AcpiHwRegisterRead (ACPI_MTX_DO_NOT_LOCK, 592 ACPI_REGISTER_PM1_CONTROL, &PM1AControl); 593 if (ACPI_SUCCESS (Status)) 594 { 595 /* Clear SLP_EN and SLP_TYP fields */ 596 597 PM1AControl &= ~(SleepTypeRegInfo->AccessBitMask | 598 SleepEnableRegInfo->AccessBitMask); 599 PM1BControl = PM1AControl; 600 601 /* Insert SLP_TYP bits */ 602 603 PM1AControl |= (AcpiGbl_SleepTypeA << SleepTypeRegInfo->BitPosition); 604 PM1BControl |= (AcpiGbl_SleepTypeB << SleepTypeRegInfo->BitPosition); 605 606 /* Just ignore any errors */ 607 608 (void) AcpiHwRegisterWrite (ACPI_MTX_DO_NOT_LOCK, 609 ACPI_REGISTER_PM1A_CONTROL, PM1AControl); 610 (void) AcpiHwRegisterWrite (ACPI_MTX_DO_NOT_LOCK, 611 ACPI_REGISTER_PM1B_CONTROL, PM1BControl); 612 } 613 } 614 615 /* Ensure EnterSleepStatePrep -> EnterSleepState ordering */ 616 617 AcpiGbl_SleepTypeA = ACPI_SLEEP_TYPE_INVALID; 618 619 /* Setup parameter object */ 620 621 ArgList.Count = 1; 622 ArgList.Pointer = &Arg; 623 Arg.Type = ACPI_TYPE_INTEGER; 624 625 /* Ignore any errors from these methods */ 626 627 Arg.Integer.Value = ACPI_SST_WAKING; 628 Status = AcpiEvaluateObject (NULL, METHOD_NAME__SST, &ArgList, NULL); 629 if (ACPI_FAILURE (Status) && Status != AE_NOT_FOUND) 630 { 631 ACPI_REPORT_ERROR (("Method _SST failed, %s\n", AcpiFormatException (Status))); 632 } 633 634 Arg.Integer.Value = SleepState; 635 Status = AcpiEvaluateObject (NULL, METHOD_NAME__BFS, &ArgList, NULL); 636 if (ACPI_FAILURE (Status) && Status != AE_NOT_FOUND) 637 { 638 ACPI_REPORT_ERROR (("Method _BFS failed, %s\n", AcpiFormatException (Status))); 639 } 640 641 Status = AcpiEvaluateObject (NULL, METHOD_NAME__WAK, &ArgList, NULL); 642 if (ACPI_FAILURE (Status) && Status != AE_NOT_FOUND) 643 { 644 ACPI_REPORT_ERROR (("Method _WAK failed, %s\n", AcpiFormatException (Status))); 645 } 646 /* TBD: _WAK "sometimes" returns stuff - do we want to look at it? */ 647 648 /* 649 * Restore the GPEs: 650 * 1) Disable all wakeup GPEs 651 * 2) Enable all runtime GPEs 652 */ 653 Status = AcpiHwRestoreGpesOnWake (); 654 if (ACPI_FAILURE (Status)) 655 { 656 return_ACPI_STATUS (Status); 657 } 658 659 /* Enable power button */ 660 661 AcpiSetRegister(AcpiGbl_FixedEventInfo[ACPI_EVENT_POWER_BUTTON].EnableRegisterId, 662 1, ACPI_MTX_DO_NOT_LOCK); 663 AcpiSetRegister(AcpiGbl_FixedEventInfo[ACPI_EVENT_POWER_BUTTON].StatusRegisterId, 664 1, ACPI_MTX_DO_NOT_LOCK); 665 666 /* Enable BM arbitration */ 667 668 Status = AcpiSetRegister (ACPI_BITREG_ARB_DISABLE, 0, ACPI_MTX_LOCK); 669 if (ACPI_FAILURE (Status)) 670 { 671 return_ACPI_STATUS (Status); 672 } 673 674 Arg.Integer.Value = ACPI_SST_WORKING; 675 Status = AcpiEvaluateObject (NULL, METHOD_NAME__SST, &ArgList, NULL); 676 if (ACPI_FAILURE (Status) && Status != AE_NOT_FOUND) 677 { 678 ACPI_REPORT_ERROR (("Method _SST failed, %s\n", AcpiFormatException (Status))); 679 } 680 681 return_ACPI_STATUS (Status); 682} 683