diff --git a/sys/amd64/acpica/acpi_wakeup.c b/sys/amd64/acpica/acpi_wakeup.c --- a/sys/amd64/acpica/acpi_wakeup.c +++ b/sys/amd64/acpica/acpi_wakeup.c @@ -74,7 +74,7 @@ extern struct susppcb **susppcbs; static cpuset_t suspcpus; -static void acpi_stop_beep(void *); +static void acpi_stop_beep(void *, enum sleep_type); static int acpi_wakeup_ap(struct acpi_softc *, int); static void acpi_wakeup_cpus(struct acpi_softc *); @@ -88,7 +88,7 @@ } while (0) static void -acpi_stop_beep(void *arg) +acpi_stop_beep(void *arg, enum sleep_type stype) { if (acpi_resume_beep != 0) diff --git a/sys/cam/ata/ata_da.c b/sys/cam/ata/ata_da.c --- a/sys/cam/ata/ata_da.c +++ b/sys/cam/ata/ata_da.c @@ -878,8 +878,8 @@ uint32_t sense_flags); static callout_func_t adasendorderedtag; static void adashutdown(void *arg, int howto); -static void adasuspend(void *arg); -static void adaresume(void *arg); +static void adasuspend(void *arg, int stype); +static void adaresume(void *arg, int stype); #ifndef ADA_DEFAULT_TIMEOUT #define ADA_DEFAULT_TIMEOUT 30 /* Timeout in seconds */ @@ -3747,7 +3747,7 @@ } static void -adasuspend(void *arg) +adasuspend(void *arg, int stype) { adaflush(); @@ -3760,7 +3760,7 @@ } static void -adaresume(void *arg) +adaresume(void *arg, int stype) { struct cam_periph *periph; struct ada_softc *softc; diff --git a/sys/cam/nvme/nvme_da.c b/sys/cam/nvme/nvme_da.c --- a/sys/cam/nvme/nvme_da.c +++ b/sys/cam/nvme/nvme_da.c @@ -159,7 +159,7 @@ static int ndaerror(union ccb *ccb, uint32_t cam_flags, uint32_t sense_flags); static void ndashutdown(void *arg, int howto); -static void ndasuspend(void *arg); +static void ndasuspend(void *arg, int stype); #ifndef NDA_DEFAULT_SEND_ORDERED #define NDA_DEFAULT_SEND_ORDERED 1 @@ -1365,7 +1365,7 @@ } static void -ndasuspend(void *arg) +ndasuspend(void *arg, int stype) { ndaflush(); diff --git a/sys/compat/linuxkpi/common/src/linux_acpi.c b/sys/compat/linuxkpi/common/src/linux_acpi.c --- a/sys/compat/linuxkpi/common/src/linux_acpi.c +++ b/sys/compat/linuxkpi/common/src/linux_acpi.c @@ -112,21 +112,33 @@ } static void -linux_handle_power_suspend_event(void *arg __unused) +linux_handle_power_suspend_event(void *arg __unused, enum sleep_type stype) { - /* - * Only support S3 for now. - * acpi_sleep_event isn't always called so we use power_suspend_early - * instead which means we don't know what state we're switching to. - * TODO: Make acpi_sleep_event consistent - */ - linux_acpi_target_sleep_state = ACPI_STATE_S3; - pm_suspend_target_state = PM_SUSPEND_MEM; + + switch (stype) { + case STYPE_SUSPEND_TO_IDLE: + /* XXX: obiwac Not 100% sure this is correct, but + * acpi_target_sleep_state does seem to be set to + * ACPI_STATE_S3 during s2idle on Linux. + */ + linux_acpi_target_sleep_state = ACPI_STATE_S3; + pm_suspend_target_state = PM_SUSPEND_TO_IDLE; + break; + case STYPE_SUSPEND: + linux_acpi_target_sleep_state = ACPI_STATE_S3; + pm_suspend_target_state = PM_SUSPEND_MEM; + break; + default: + printf("%s: sleep type %d not yet supported\n", + __func__, stype); + break; + } } static void -linux_handle_power_resume_event(void *arg __unused) +linux_handle_power_resume_event(void *arg __unused, enum sleep_type stype) { + linux_acpi_target_sleep_state = ACPI_STATE_S0; pm_suspend_target_state = PM_SUSPEND_ON; } diff --git a/sys/dev/acpica/acpi.c b/sys/dev/acpica/acpi.c --- a/sys/dev/acpica/acpi.c +++ b/sys/dev/acpica/acpi.c @@ -3671,10 +3671,10 @@ return_ACPI_STATUS (AE_OK); } - EVENTHANDLER_INVOKE(power_suspend_early); + EVENTHANDLER_INVOKE(power_suspend_early, stype); stop_all_proc(); suspend_all_fs(); - EVENTHANDLER_INVOKE(power_suspend); + EVENTHANDLER_INVOKE(power_suspend, stype); #ifdef EARLY_AP_STARTUP MPASS(mp_ncpus == 1 || smp_started); @@ -3828,7 +3828,7 @@ resume_all_fs(); resume_all_proc(); - EVENTHANDLER_INVOKE(power_resume); + EVENTHANDLER_INVOKE(power_resume, stype); /* Allow another sleep request after a while. */ callout_schedule(&acpi_sleep_timer, hz * ACPI_MINIMUM_AWAKETIME); diff --git a/sys/dev/acpica/acpi_timer.c b/sys/dev/acpica/acpi_timer.c --- a/sys/dev/acpica/acpi_timer.c +++ b/sys/dev/acpica/acpi_timer.c @@ -69,8 +69,9 @@ static void acpi_timer_identify(driver_t *driver, device_t parent); static int acpi_timer_probe(device_t dev); static int acpi_timer_attach(device_t dev); -static void acpi_timer_resume_handler(struct timecounter *); -static void acpi_timer_suspend_handler(struct timecounter *); +static void acpi_timer_resume_handler(struct timecounter *, enum sleep_type); +static void acpi_timer_suspend_handler(struct timecounter *, + enum sleep_type); static u_int acpi_timer_get_timecount(struct timecounter *tc); static u_int acpi_timer_get_timecount_safe(struct timecounter *tc); static int acpi_timer_sysctl_freq(SYSCTL_HANDLER_ARGS); @@ -235,7 +236,7 @@ } static void -acpi_timer_resume_handler(struct timecounter *newtc) +acpi_timer_resume_handler(struct timecounter *newtc, enum sleep_type stype) { struct timecounter *tc; @@ -251,7 +252,7 @@ } static void -acpi_timer_suspend_handler(struct timecounter *newtc) +acpi_timer_suspend_handler(struct timecounter *newtc, enum sleep_type stype) { struct timecounter *tc; diff --git a/sys/dev/vt/vt_core.c b/sys/dev/vt/vt_core.c --- a/sys/dev/vt/vt_core.c +++ b/sys/dev/vt/vt_core.c @@ -195,8 +195,8 @@ #ifndef SC_NO_CUTPASTE static void vt_mouse_paste(void); #endif -static void vt_suspend_handler(void *priv); -static void vt_resume_handler(void *priv); +static void vt_suspend_handler(void *priv, int stype); +static void vt_resume_handler(void *priv, int stype); SET_DECLARE(vt_drv_set, struct vt_driver); @@ -3330,7 +3330,7 @@ } static void -vt_suspend_handler(void *priv) +vt_suspend_handler(void *priv, int stype) { struct vt_device *vd; @@ -3341,7 +3341,7 @@ } static void -vt_resume_handler(void *priv) +vt_resume_handler(void *priv, int stype) { struct vt_device *vd; diff --git a/sys/dev/xen/control/control.c b/sys/dev/xen/control/control.c --- a/sys/dev/xen/control/control.c +++ b/sys/dev/xen/control/control.c @@ -175,12 +175,16 @@ cpuset_t cpu_suspend_map; #endif - EVENTHANDLER_INVOKE(power_suspend_early); + /* + * TODO Once enum sleep_type is made available on non-ACPI, this should + * be STYPE_SUSPEND instead. + */ + EVENTHANDLER_INVOKE(power_suspend_early, 0); xs_lock(); stop_all_proc(); xs_unlock(); suspend_all_fs(); - EVENTHANDLER_INVOKE(power_suspend); + EVENTHANDLER_INVOKE(power_suspend, 0); #ifdef EARLY_AP_STARTUP MPASS(mp_ncpus == 1 || smp_started); @@ -297,7 +301,7 @@ resume_all_fs(); resume_all_proc(); - EVENTHANDLER_INVOKE(power_resume); + EVENTHANDLER_INVOKE(power_resume, 0); if (bootverbose) printf("System resumed after suspension\n"); diff --git a/sys/i386/acpica/acpi_wakeup.c b/sys/i386/acpica/acpi_wakeup.c --- a/sys/i386/acpica/acpi_wakeup.c +++ b/sys/i386/acpica/acpi_wakeup.c @@ -84,7 +84,7 @@ static struct susppcb **susppcbs; #endif -static void acpi_stop_beep(void *); +static void acpi_stop_beep(void *, enum sleep_type); #ifdef SMP static int acpi_wakeup_ap(struct acpi_softc *, int); @@ -100,7 +100,7 @@ } while (0) static void -acpi_stop_beep(void *arg) +acpi_stop_beep(void *arg, enum sleep_type stype) { if (acpi_resume_beep != 0) diff --git a/sys/sys/eventhandler.h b/sys/sys/eventhandler.h --- a/sys/sys/eventhandler.h +++ b/sys/sys/eventhandler.h @@ -200,8 +200,13 @@ EVENTHANDLER_DECLARE(shutdown_post_sync, shutdown_fn); /* after fs sync */ EVENTHANDLER_DECLARE(shutdown_final, shutdown_fn); -/* Power state change events */ -typedef void (*power_change_fn)(void *); +/* + * Power state change events. + * + * TODO Maybe enum sleep_type shouldn't be defined in dev/acpica/acpivar.h, cuz + * then I can't use it here/on non-ACPI systems. + */ +typedef void (*power_change_fn)(void *, int stype); EVENTHANDLER_DECLARE(power_resume, power_change_fn); EVENTHANDLER_DECLARE(power_suspend, power_change_fn); EVENTHANDLER_DECLARE(power_suspend_early, power_change_fn);