Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge branch 'release' of git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux-acpi-2.6

* 'release' of git://git.kernel.org/pub/scm/linux/kernel/git/lenb/linux-acpi-2.6:
ACPI: Eliminate us to pm ticks conversion in common path
ACPI: Fix the incorrect calculation about C-state idle time
ACPI: update feature-removal.txt to reflect deleted acpi=ht option
ACPI / EC / PM: Fix names of functions that block/unblock EC transactions
ACPI / EC / PM: Fix race between EC transactions and system suspend

+55 -55
-9
Documentation/feature-removal-schedule.txt
··· 578 578 579 579 ---------------------------- 580 580 581 - What: "acpi=ht" boot option 582 - When: 2.6.35 583 - Why: Useful in 2003, implementation is a hack. 584 - Generally invoked by accident today. 585 - Seen as doing more harm than good. 586 - Who: Len Brown <len.brown@intel.com> 587 - 588 - ---------------------------- 589 - 590 581 What: iwlwifi 50XX module parameters 591 582 When: 2.6.40 592 583 Why: The "..50" modules parameters were used to configure 5000 series and
+16 -6
drivers/acpi/ec.c
··· 79 79 EC_FLAGS_GPE_STORM, /* GPE storm detected */ 80 80 EC_FLAGS_HANDLERS_INSTALLED, /* Handlers for GPE and 81 81 * OpReg are installed */ 82 - EC_FLAGS_FROZEN, /* Transactions are suspended */ 82 + EC_FLAGS_BLOCKED, /* Transactions are blocked */ 83 83 }; 84 84 85 85 /* If we find an EC via the ECDT, we need to keep a ptr to its context */ ··· 293 293 if (t->rdata) 294 294 memset(t->rdata, 0, t->rlen); 295 295 mutex_lock(&ec->lock); 296 - if (test_bit(EC_FLAGS_FROZEN, &ec->flags)) { 296 + if (test_bit(EC_FLAGS_BLOCKED, &ec->flags)) { 297 297 status = -EINVAL; 298 298 goto unlock; 299 299 } ··· 459 459 460 460 EXPORT_SYMBOL(ec_transaction); 461 461 462 - void acpi_ec_suspend_transactions(void) 462 + void acpi_ec_block_transactions(void) 463 463 { 464 464 struct acpi_ec *ec = first_ec; 465 465 ··· 468 468 469 469 mutex_lock(&ec->lock); 470 470 /* Prevent transactions from being carried out */ 471 - set_bit(EC_FLAGS_FROZEN, &ec->flags); 471 + set_bit(EC_FLAGS_BLOCKED, &ec->flags); 472 472 mutex_unlock(&ec->lock); 473 473 } 474 474 475 - void acpi_ec_resume_transactions(void) 475 + void acpi_ec_unblock_transactions(void) 476 476 { 477 477 struct acpi_ec *ec = first_ec; 478 478 ··· 481 481 482 482 mutex_lock(&ec->lock); 483 483 /* Allow transactions to be carried out again */ 484 - clear_bit(EC_FLAGS_FROZEN, &ec->flags); 484 + clear_bit(EC_FLAGS_BLOCKED, &ec->flags); 485 485 mutex_unlock(&ec->lock); 486 + } 487 + 488 + void acpi_ec_unblock_transactions_early(void) 489 + { 490 + /* 491 + * Allow transactions to happen again (this function is called from 492 + * atomic context during wakeup, so we don't need to acquire the mutex). 493 + */ 494 + if (first_ec) 495 + clear_bit(EC_FLAGS_BLOCKED, &first_ec->flags); 486 496 } 487 497 488 498 static int acpi_ec_query_unlocked(struct acpi_ec *ec, u8 * data)
+3 -2
drivers/acpi/internal.h
··· 49 49 int acpi_ec_init(void); 50 50 int acpi_ec_ecdt_probe(void); 51 51 int acpi_boot_ec_enable(void); 52 - void acpi_ec_suspend_transactions(void); 53 - void acpi_ec_resume_transactions(void); 52 + void acpi_ec_block_transactions(void); 53 + void acpi_ec_unblock_transactions(void); 54 + void acpi_ec_unblock_transactions_early(void); 54 55 55 56 /*-------------------------------------------------------------------------- 56 57 Suspend/Resume
+6 -11
drivers/acpi/processor_idle.c
··· 80 80 static unsigned int latency_factor __read_mostly = 2; 81 81 module_param(latency_factor, uint, 0644); 82 82 83 - static s64 us_to_pm_timer_ticks(s64 t) 83 + static u64 us_to_pm_timer_ticks(s64 t) 84 84 { 85 85 return div64_u64(t * PM_TIMER_FREQUENCY, 1000000); 86 86 } ··· 731 731 732 732 seq_puts(seq, "demotion[--] "); 733 733 734 - seq_printf(seq, "latency[%03d] usage[%08d] duration[%020llu]\n", 734 + seq_printf(seq, "latency[%03d] usage[%08d] duration[%020Lu]\n", 735 735 pr->power.states[i].latency, 736 736 pr->power.states[i].usage, 737 - (unsigned long long)pr->power.states[i].time); 737 + us_to_pm_timer_ticks(pr->power.states[i].time)); 738 738 } 739 739 740 740 end: ··· 861 861 ktime_t kt1, kt2; 862 862 s64 idle_time_ns; 863 863 s64 idle_time; 864 - s64 sleep_ticks = 0; 865 864 866 865 pr = __get_cpu_var(processors); 867 866 ··· 905 906 idle_time = idle_time_ns; 906 907 do_div(idle_time, NSEC_PER_USEC); 907 908 908 - sleep_ticks = us_to_pm_timer_ticks(idle_time); 909 - 910 909 /* Tell the scheduler how much we idled: */ 911 910 sched_clock_idle_wakeup_event(idle_time_ns); 912 911 ··· 915 918 cx->usage++; 916 919 917 920 lapic_timer_state_broadcast(pr, cx, 0); 918 - cx->time += sleep_ticks; 921 + cx->time += idle_time; 919 922 return idle_time; 920 923 } 921 924 ··· 937 940 ktime_t kt1, kt2; 938 941 s64 idle_time_ns; 939 942 s64 idle_time; 940 - s64 sleep_ticks = 0; 941 943 942 944 943 945 pr = __get_cpu_var(processors); ··· 1018 1022 spin_unlock(&c3_lock); 1019 1023 } 1020 1024 kt2 = ktime_get_real(); 1021 - idle_time_ns = ktime_to_us(ktime_sub(kt2, kt1)); 1025 + idle_time_ns = ktime_to_ns(ktime_sub(kt2, kt1)); 1022 1026 idle_time = idle_time_ns; 1023 1027 do_div(idle_time, NSEC_PER_USEC); 1024 1028 1025 - sleep_ticks = us_to_pm_timer_ticks(idle_time); 1026 1029 /* Tell the scheduler how much we idled: */ 1027 1030 sched_clock_idle_wakeup_event(idle_time_ns); 1028 1031 ··· 1032 1037 cx->usage++; 1033 1038 1034 1039 lapic_timer_state_broadcast(pr, cx, 0); 1035 - cx->time += sleep_ticks; 1040 + cx->time += idle_time; 1036 1041 return idle_time; 1037 1042 } 1038 1043
+30 -27
drivers/acpi/sleep.c
··· 94 94 } 95 95 96 96 /** 97 - * acpi_pm_disable_gpes - Disable the GPEs. 97 + * acpi_pm_freeze - Disable the GPEs and suspend EC transactions. 98 98 */ 99 - static int acpi_pm_disable_gpes(void) 99 + static int acpi_pm_freeze(void) 100 100 { 101 101 acpi_disable_all_gpes(); 102 + acpi_os_wait_events_complete(NULL); 103 + acpi_ec_block_transactions(); 102 104 return 0; 103 105 } 104 106 ··· 128 126 int error = __acpi_pm_prepare(); 129 127 130 128 if (!error) 131 - acpi_disable_all_gpes(); 129 + acpi_pm_freeze(); 130 + 132 131 return error; 133 132 } 134 133 ··· 259 256 * acpi_leave_sleep_state will reenable specific GPEs later 260 257 */ 261 258 acpi_disable_all_gpes(); 259 + /* Allow EC transactions to happen. */ 260 + acpi_ec_unblock_transactions_early(); 262 261 263 262 local_irq_restore(flags); 264 263 printk(KERN_DEBUG "Back to C!\n"); ··· 270 265 acpi_restore_state_mem(); 271 266 272 267 return ACPI_SUCCESS(status) ? 0 : -EFAULT; 268 + } 269 + 270 + static void acpi_suspend_finish(void) 271 + { 272 + acpi_ec_unblock_transactions(); 273 + acpi_pm_finish(); 273 274 } 274 275 275 276 static int acpi_suspend_state_valid(suspend_state_t pm_state) ··· 299 288 .begin = acpi_suspend_begin, 300 289 .prepare_late = acpi_pm_prepare, 301 290 .enter = acpi_suspend_enter, 302 - .wake = acpi_pm_finish, 291 + .wake = acpi_suspend_finish, 303 292 .end = acpi_pm_end, 304 293 }; 305 294 ··· 325 314 static struct platform_suspend_ops acpi_suspend_ops_old = { 326 315 .valid = acpi_suspend_state_valid, 327 316 .begin = acpi_suspend_begin_old, 328 - .prepare_late = acpi_pm_disable_gpes, 317 + .prepare_late = acpi_pm_freeze, 329 318 .enter = acpi_suspend_enter, 330 - .wake = acpi_pm_finish, 319 + .wake = acpi_suspend_finish, 331 320 .end = acpi_pm_end, 332 321 .recover = acpi_pm_finish, 333 322 }; ··· 444 433 static void acpi_hibernation_finish(void) 445 434 { 446 435 hibernate_nvs_free(); 436 + acpi_ec_unblock_transactions(); 447 437 acpi_pm_finish(); 448 438 } 449 439 ··· 465 453 } 466 454 /* Restore the NVS memory area */ 467 455 hibernate_nvs_restore(); 456 + /* Allow EC transactions to happen. */ 457 + acpi_ec_unblock_transactions_early(); 468 458 } 469 459 470 - static int acpi_pm_pre_restore(void) 460 + static void acpi_pm_thaw(void) 471 461 { 472 - acpi_disable_all_gpes(); 473 - acpi_os_wait_events_complete(NULL); 474 - acpi_ec_suspend_transactions(); 475 - return 0; 476 - } 477 - 478 - static void acpi_pm_restore_cleanup(void) 479 - { 480 - acpi_ec_resume_transactions(); 462 + acpi_ec_unblock_transactions(); 481 463 acpi_enable_all_runtime_gpes(); 482 464 } 483 465 ··· 483 477 .prepare = acpi_pm_prepare, 484 478 .enter = acpi_hibernation_enter, 485 479 .leave = acpi_hibernation_leave, 486 - .pre_restore = acpi_pm_pre_restore, 487 - .restore_cleanup = acpi_pm_restore_cleanup, 480 + .pre_restore = acpi_pm_freeze, 481 + .restore_cleanup = acpi_pm_thaw, 488 482 }; 489 483 490 484 /** ··· 516 510 517 511 static int acpi_hibernation_pre_snapshot_old(void) 518 512 { 519 - int error = acpi_pm_disable_gpes(); 520 - 521 - if (!error) 522 - hibernate_nvs_save(); 523 - 524 - return error; 513 + acpi_pm_freeze(); 514 + hibernate_nvs_save(); 515 + return 0; 525 516 } 526 517 527 518 /* ··· 530 527 .end = acpi_pm_end, 531 528 .pre_snapshot = acpi_hibernation_pre_snapshot_old, 532 529 .finish = acpi_hibernation_finish, 533 - .prepare = acpi_pm_disable_gpes, 530 + .prepare = acpi_pm_freeze, 534 531 .enter = acpi_hibernation_enter, 535 532 .leave = acpi_hibernation_leave, 536 - .pre_restore = acpi_pm_pre_restore, 537 - .restore_cleanup = acpi_pm_restore_cleanup, 533 + .pre_restore = acpi_pm_freeze, 534 + .restore_cleanup = acpi_pm_thaw, 538 535 .recover = acpi_pm_finish, 539 536 }; 540 537 #endif /* CONFIG_HIBERNATION */