Thinkpad resume issues in 5.4
Kevin Oberman
oberman at es.net
Wed Oct 5 09:46:49 PDT 2005
> Date: Wed, 5 Oct 2005 18:03:57 +0200
> From: Fabian Keil <freebsd-listen at fabiankeil.de>
> Sender: owner-freebsd-mobile at freebsd.org
>
> --Signature_Wed__5_Oct_2005_18_03_57_+0200_EN2yrnIo7pjGIV9c
> Content-Type: text/plain; charset=US-ASCII
> Content-Transfer-Encoding: quoted-printable
>
> Lee Parsons <pars0080 at umn.edu> wrote:
>
> > I had previously ran my Freebsd 5.3 on my thinkpad R32, where I had
> > compiled acpi (but not apm) into my kernel. Under that
> > configuration, I could use the 'zzz' command to sleep my system, and
> > it would wake by opening the lid.
> > Doing the same in 5.4 has not worked. I again compiled acpi but not
> > apm into my kernel. However, when I try to resume by opening the
> > lid, my system comes back up in a mostly non-responsive state. By
> > that, I mean that the keyboard evokes some resonse (caps lock, for
> > example...), but I cannot actually do anything useful. Furthermore,
> > my colors (in X) are mostly reversed. There is no mouse response at
> > all.
> >
> > I have seen other comments on the contents of sysctl.conf. I checked
> > my /etc/sysctl.conf and there are no uncommented lines in there.
> >
> > I'm not sure what to do. Otherwise, 5.4 is working well.
>
> To handle this problem I put
>
> acpi_video_load="YES"
>
> in /boot/loader.conf and
>
> hw.acpi.reset_video=0
> hw.syscons.sc_no_suspend_vtswitch=1
>
> in /etc/sysctl.conf.
To get the back-light to turn off, you may need jhb's acpi_video_dpms
patch. I have re-posted it a couple of times with update for acpi_video
in current.
I don't think I have posted it since the last time I had to update it, so
I will post it again. I don't know if it will apply cleanly against 5.4,
but it should be close enough to figure out.
--
R. Kevin Oberman, Network Engineer
Energy Sciences Network (ESnet)
Ernest O. Lawrence Berkeley National Laboratory (Berkeley Lab)
E-mail: oberman at es.net Phone: +1 510 486-8634
-------------- next part --------------
--- sys/dev/acpica/acpi_video.c.orig Wed Mar 2 01:22:34 2005
+++ sys/dev/acpica/acpi_video.c Mon Aug 22 08:57:06 2005
@@ -1,5 +1,6 @@
/*-
* Copyright (c) 2002-2003 Taku YAMAMOTO <taku at cent.saitama-u.ac.jp>
+ * Copyright (c) 2004 Benjamin Close <Benjamin.Close at clearchain.com>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -37,10 +38,33 @@
#include <sys/power.h>
#include <sys/queue.h>
#include <sys/sysctl.h>
+#ifdef __i386__
+#include <machine/vm86.h>
+#endif
#include <contrib/dev/acpica/acpi.h>
#include <dev/acpica/acpivar.h>
+#ifdef __i386__
+#define USE_DPMS
+
+/*
+ * VESA DPMS States
+ */
+#define DPMS_ON 0x00
+#define DPMS_STANDBY 0x01
+#define DPMS_SUSPEND 0x02
+#define DPMS_OFF 0x04
+#define DPMS_REDUCEDON 0x08
+
+#define VBE_DPMS_FUNCTION 0x4F10
+#define VBE_DPMS_GET_SUPPORTED_STATES 0x00
+#define VBE_DPMS_GET_STATE 0x02
+#define VBE_DPMS_SET_STATE 0x01
+#define VBE_MAJORVERSION_MASK 0x0F
+#define VBE_MINORVERSION_MASK 0xF0
+#endif
+
/* ACPI video extension driver. */
struct acpi_video_output {
ACPI_HANDLE handle;
@@ -66,6 +90,10 @@
ACPI_HANDLE handle;
struct acpi_video_output_queue vid_outputs;
eventhandler_tag vid_pwr_evh;
+#ifdef USE_DPMS
+ int vid_dpms_supported_states;
+ int vid_dpms_initial_state;
+#endif
};
/* interfaces */
@@ -74,6 +102,8 @@
static int acpi_video_attach(device_t);
static int acpi_video_detach(device_t);
static int acpi_video_shutdown(device_t);
+static int acpi_video_suspend(device_t);
+static int acpi_video_resume(device_t);
static void acpi_video_notify_handler(ACPI_HANDLE, UINT32, void *);
static void acpi_video_power_profile(void *);
static void acpi_video_bind_outputs(struct acpi_video_softc *);
@@ -95,6 +125,11 @@
static UINT32 vo_get_device_status(ACPI_HANDLE);
static UINT32 vo_get_graphics_state(ACPI_HANDLE);
static void vo_set_device_state(ACPI_HANDLE, UINT32);
+#ifdef USE_DPMS
+static int dpms_get_supported_states(int *);
+static int dpms_get_current_state(int *);
+static int dpms_set_state(int);
+#endif
/* events */
#define VID_NOTIFY_SWITCHED 0x80
@@ -141,6 +176,8 @@
DEVMETHOD(device_attach, acpi_video_attach),
DEVMETHOD(device_detach, acpi_video_detach),
DEVMETHOD(device_shutdown, acpi_video_shutdown),
+ DEVMETHOD(device_resume, acpi_video_resume),
+ DEVMETHOD(device_suspend, acpi_video_suspend),
{ 0, 0 }
};
@@ -247,6 +284,13 @@
acpi_video_power_profile(sc);
+#ifdef USE_DPMS
+ if (dpms_get_supported_states(&sc->vid_dpms_supported_states) == 0)
+ dpms_get_current_state(&sc->vid_dpms_initial_state);
+ else
+ sc->vid_dpms_supported_states = -1;
+#endif
+
return (0);
}
@@ -284,6 +328,32 @@
return (0);
}
+static int
+acpi_video_suspend(device_t dev)
+{
+ struct acpi_video_softc *sc;
+
+ sc = device_get_softc(dev);
+#ifdef USE_DPMS
+ if (sc->vid_dpms_supported_states != -1)
+ dpms_set_state(DPMS_OFF);
+#endif
+ return (0);
+}
+
+static int
+acpi_video_resume(device_t dev)
+{
+ struct acpi_video_softc *sc;
+
+ sc = device_get_softc(dev);
+#ifdef USE_DPMS
+ if (sc->vid_dpms_supported_states != -1)
+ dpms_set_state(sc->vid_dpms_initial_state);
+#endif
+ return (0);
+}
+
static void
acpi_video_notify_handler(ACPI_HANDLE handle, UINT32 notify, void *context)
{
@@ -898,3 +968,49 @@
printf("can't evaluate %s._DSS - %s\n",
acpi_name(handle), AcpiFormatException(status));
}
+
+#ifdef USE_DPMS
+/* XXX: Requires VM86 support in the kernel. */
+static int
+dpms_call_bios(int subfunction, int *bh)
+{
+ struct vm86frame vmf;
+ int error;
+
+ bzero(&vmf, sizeof(vmf));
+ vmf.vmf_ax = VBE_DPMS_FUNCTION;
+ vmf.vmf_bl = subfunction;
+ vmf.vmf_bh = *bh;
+ vmf.vmf_es = 0;
+ vmf.vmf_di = 0;
+ error = vm86_intcall(0x10, &vmf);
+ if (error == 0 && (vmf.vmf_eax & 0xffff) != 0x004f)
+ error = ENXIO;
+ if (error == 0)
+ *bh = vmf.vmf_bh;
+ return (error);
+}
+
+static int
+dpms_get_supported_states(int *states)
+{
+
+ *states = 0;
+ return (dpms_call_bios(VBE_DPMS_GET_SUPPORTED_STATES, states));
+}
+
+static int
+dpms_get_current_state(int *state)
+{
+
+ *state = 0;
+ return (dpms_call_bios(VBE_DPMS_GET_STATE, state));
+}
+
+static int
+dpms_set_state(int state)
+{
+
+ return (dpms_call_bios(VBE_DPMS_SET_STATE, &state));
+}
+#endif
More information about the freebsd-mobile
mailing list