提交 ac1e3d4f 编写于 作者: L Linus Torvalds

Merge tag 'pm-fixes-for-3.3' of git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm

Power management fixes for 3.3

Two fixes for regressions introduced during the merge window, one fix for
a long-standing obscure issue in the computation of hibernate image size
and two small PM documentation fixes.

* tag 'pm-fixes-for-3.3' of git://git.kernel.org/pub/scm/linux/kernel/git/rafael/linux-pm:
  PM / Sleep: Fix read_unlock_usermodehelper() call.
  PM / Hibernate: Rewrite unlock_system_sleep() to fix s2disk regression
  PM / Hibernate: Correct additional pages number calculation
  PM / Documentation: Fix minor issue in freezing_of_tasks.txt
  PM / Documentation: Fix spelling mistake in basic-pm-debugging.txt
...@@ -15,7 +15,7 @@ test at least a couple of times in a row for confidence. [This is necessary, ...@@ -15,7 +15,7 @@ test at least a couple of times in a row for confidence. [This is necessary,
because some problems only show up on a second attempt at suspending and because some problems only show up on a second attempt at suspending and
resuming the system.] Moreover, hibernating in the "reboot" and "shutdown" resuming the system.] Moreover, hibernating in the "reboot" and "shutdown"
modes causes the PM core to skip some platform-related callbacks which on ACPI modes causes the PM core to skip some platform-related callbacks which on ACPI
systems might be necessary to make hibernation work. Thus, if you machine fails systems might be necessary to make hibernation work. Thus, if your machine fails
to hibernate or resume in the "reboot" mode, you should try the "platform" mode: to hibernate or resume in the "reboot" mode, you should try the "platform" mode:
# echo platform > /sys/power/disk # echo platform > /sys/power/disk
......
...@@ -120,10 +120,10 @@ So in practice, the 'at all' may become a 'why freeze kernel threads?' and ...@@ -120,10 +120,10 @@ So in practice, the 'at all' may become a 'why freeze kernel threads?' and
freezing user threads I don't find really objectionable." freezing user threads I don't find really objectionable."
Still, there are kernel threads that may want to be freezable. For example, if Still, there are kernel threads that may want to be freezable. For example, if
a kernel that belongs to a device driver accesses the device directly, it in a kernel thread that belongs to a device driver accesses the device directly, it
principle needs to know when the device is suspended, so that it doesn't try to in principle needs to know when the device is suspended, so that it doesn't try
access it at that time. However, if the kernel thread is freezable, it will be to access it at that time. However, if the kernel thread is freezable, it will
frozen before the driver's .suspend() callback is executed and it will be be frozen before the driver's .suspend() callback is executed and it will be
thawed after the driver's .resume() callback has run, so it won't be accessing thawed after the driver's .resume() callback has run, so it won't be accessing
the device while it's suspended. the device while it's suspended.
......
...@@ -525,8 +525,7 @@ static int _request_firmware(const struct firmware **firmware_p, ...@@ -525,8 +525,7 @@ static int _request_firmware(const struct firmware **firmware_p,
if (!firmware) { if (!firmware) {
dev_err(device, "%s: kmalloc(struct firmware) failed\n", dev_err(device, "%s: kmalloc(struct firmware) failed\n",
__func__); __func__);
retval = -ENOMEM; return -ENOMEM;
goto out;
} }
if (fw_get_builtin_firmware(firmware, name)) { if (fw_get_builtin_firmware(firmware, name)) {
......
...@@ -357,14 +357,29 @@ extern bool pm_save_wakeup_count(unsigned int count); ...@@ -357,14 +357,29 @@ extern bool pm_save_wakeup_count(unsigned int count);
static inline void lock_system_sleep(void) static inline void lock_system_sleep(void)
{ {
freezer_do_not_count(); current->flags |= PF_FREEZER_SKIP;
mutex_lock(&pm_mutex); mutex_lock(&pm_mutex);
} }
static inline void unlock_system_sleep(void) static inline void unlock_system_sleep(void)
{ {
/*
* Don't use freezer_count() because we don't want the call to
* try_to_freeze() here.
*
* Reason:
* Fundamentally, we just don't need it, because freezing condition
* doesn't come into effect until we release the pm_mutex lock,
* since the freezer always works with pm_mutex held.
*
* More importantly, in the case of hibernation,
* unlock_system_sleep() gets called in snapshot_read() and
* snapshot_write() when the freezing condition is still in effect.
* Which means, if we use try_to_freeze() here, it would make them
* enter the refrigerator, thus causing hibernation to lockup.
*/
current->flags &= ~PF_FREEZER_SKIP;
mutex_unlock(&pm_mutex); mutex_unlock(&pm_mutex);
freezer_count();
} }
#else /* !CONFIG_PM_SLEEP */ #else /* !CONFIG_PM_SLEEP */
......
...@@ -812,7 +812,8 @@ unsigned int snapshot_additional_pages(struct zone *zone) ...@@ -812,7 +812,8 @@ unsigned int snapshot_additional_pages(struct zone *zone)
unsigned int res; unsigned int res;
res = DIV_ROUND_UP(zone->spanned_pages, BM_BITS_PER_BLOCK); res = DIV_ROUND_UP(zone->spanned_pages, BM_BITS_PER_BLOCK);
res += DIV_ROUND_UP(res * sizeof(struct bm_block), PAGE_SIZE); res += DIV_ROUND_UP(res * sizeof(struct bm_block),
LINKED_PAGE_DATA_SIZE);
return 2 * res; return 2 * res;
} }
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册