Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 117283
b: refs/heads/master
c: f5adfaa
h: refs/heads/master
i:
  117281: 129a030
  117279: 68e3a8e
v: v3
  • Loading branch information
Zhao Yakui authored and Len Brown committed Oct 22, 2008
1 parent ecf5645 commit 8ff3bf7
Show file tree
Hide file tree
Showing 5 changed files with 54 additions and 13 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: eab4b645769fa2f8703f5a3cb0cc4ac090d347af
refs/heads/master: f5adfaa372c76423b6e8e4727a9701330374f364
8 changes: 8 additions & 0 deletions trunk/Documentation/kernel-parameters.txt
Original file line number Diff line number Diff line change
Expand Up @@ -251,6 +251,14 @@ and is between 256 and 4096 characters. It is defined in the file
Warning: Many of these options can produce a lot of
output and make your system unusable. Be very careful.

acpi.power_nocheck= [HW,ACPI]
Format: 1/0 enable/disable the check of power state.
On some bogus BIOS the _PSC object/_STA object of
power resource can't return the correct device power
state. In such case it is unneccessary to check its
power state again in power transition.
1 : disable the power state check

acpi_pm_good [X86-32,X86-64]
Override the pmtimer bug detection: force the kernel
to assume that this machine's pmtimer latches its value
Expand Down
14 changes: 13 additions & 1 deletion trunk/drivers/acpi/bus.c
Original file line number Diff line number Diff line change
Expand Up @@ -223,7 +223,19 @@ int acpi_bus_set_power(acpi_handle handle, int state)
/*
* Get device's current power state
*/
acpi_bus_get_power(device->handle, &device->power.state);
if (!acpi_power_nocheck) {
/*
* Maybe the incorrect power state is returned on the bogus
* bios, which is different with the real power state.
* For example: the bios returns D0 state and the real power
* state is D3. OS expects to set the device to D0 state. In
* such case if OS uses the power state returned by the BIOS,
* the device can't be transisted to the correct power state.
* So if the acpi_power_nocheck is set, it is unnecessary to
* get the power state by calling acpi_bus_get_power.
*/
acpi_bus_get_power(device->handle, &device->power.state);
}
if ((state == device->power.state) && !device->flags.force_power_state) {
ACPI_DEBUG_PRINT((ACPI_DB_INFO, "Device is already at D%d\n",
state));
Expand Down
42 changes: 31 additions & 11 deletions trunk/drivers/acpi/power.c
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,14 @@ ACPI_MODULE_NAME("power");
#define ACPI_POWER_RESOURCE_STATE_OFF 0x00
#define ACPI_POWER_RESOURCE_STATE_ON 0x01
#define ACPI_POWER_RESOURCE_STATE_UNKNOWN 0xFF

#ifdef MODULE_PARAM_PREFIX
#undef MODULE_PARAM_PREFIX
#endif
#define MODULE_PARAM_PREFIX "acpi."
int acpi_power_nocheck;
module_param_named(power_nocheck, acpi_power_nocheck, bool, 000);

static int acpi_power_add(struct acpi_device *device);
static int acpi_power_remove(struct acpi_device *device, int type);
static int acpi_power_resume(struct acpi_device *device);
Expand Down Expand Up @@ -228,12 +236,18 @@ static int acpi_power_on(acpi_handle handle, struct acpi_device *dev)
if (ACPI_FAILURE(status))
return -ENODEV;

result = acpi_power_get_state(resource->device->handle, &state);
if (result)
return result;
if (state != ACPI_POWER_RESOURCE_STATE_ON)
return -ENOEXEC;

if (!acpi_power_nocheck) {
/*
* If acpi_power_nocheck is set, it is unnecessary to check
* the power state after power transition.
*/
result = acpi_power_get_state(resource->device->handle,
&state);
if (result)
return result;
if (state != ACPI_POWER_RESOURCE_STATE_ON)
return -ENOEXEC;
}
/* Update the power resource's _device_ power state */
resource->device->power.state = ACPI_STATE_D0;

Expand Down Expand Up @@ -279,11 +293,17 @@ static int acpi_power_off_device(acpi_handle handle, struct acpi_device *dev)
if (ACPI_FAILURE(status))
return -ENODEV;

result = acpi_power_get_state(handle, &state);
if (result)
return result;
if (state != ACPI_POWER_RESOURCE_STATE_OFF)
return -ENOEXEC;
if (!acpi_power_nocheck) {
/*
* If acpi_power_nocheck is set, it is unnecessary to check
* the power state after power transition.
*/
result = acpi_power_get_state(handle, &state);
if (result)
return result;
if (state != ACPI_POWER_RESOURCE_STATE_OFF)
return -ENOEXEC;
}

/* Update the power resource's _device_ power state */
resource->device->power.state = ACPI_STATE_D3;
Expand Down
1 change: 1 addition & 0 deletions trunk/include/acpi/acpi_drivers.h
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,7 @@ int acpi_enable_wakeup_device_power(struct acpi_device *dev, int sleep_state);
int acpi_disable_wakeup_device_power(struct acpi_device *dev);
int acpi_power_get_inferred_state(struct acpi_device *device);
int acpi_power_transition(struct acpi_device *device, int state);
extern int acpi_power_nocheck;
#endif

/* --------------------------------------------------------------------------
Expand Down

0 comments on commit 8ff3bf7

Please sign in to comment.