asmc(4): Add support for backlight(9) interface
MFC after: 1 month
This commit is contained in:
+10
-1
@@ -79,7 +79,9 @@ On
|
|||||||
systems, you can control the keyboard brightness by writing a value to
|
systems, you can control the keyboard brightness by writing a value to
|
||||||
the
|
the
|
||||||
.Va dev.asmc.%d.light.control
|
.Va dev.asmc.%d.light.control
|
||||||
sysctl MIB.
|
sysctl MIB or with
|
||||||
|
.Xr backlight 8
|
||||||
|
utility.
|
||||||
.Pp
|
.Pp
|
||||||
The following sysctl MIBs contains the raw value returned by the left
|
The following sysctl MIBs contains the raw value returned by the left
|
||||||
and right light sensors:
|
and right light sensors:
|
||||||
@@ -143,8 +145,15 @@ dramatically reduce your hard drive's life span.
|
|||||||
Do not rely solely on
|
Do not rely solely on
|
||||||
the SMS to protect your hard drive: good care and common sense can
|
the SMS to protect your hard drive: good care and common sense can
|
||||||
increase your hard drive's life.
|
increase your hard drive's life.
|
||||||
|
.Sh FILES
|
||||||
|
.Bl -tag -width ".Pa /dev/backlight/asmc0" -compact
|
||||||
|
.It Pa /dev/backlight/asmc0
|
||||||
|
Keyboard
|
||||||
|
.Xr backlight 8
|
||||||
|
device node.
|
||||||
.Sh SEE ALSO
|
.Sh SEE ALSO
|
||||||
.Xr ataidle 8 Pq Pa ports/sysutils/ataidle ,
|
.Xr ataidle 8 Pq Pa ports/sysutils/ataidle ,
|
||||||
|
.Xr backlight 8 ,
|
||||||
.Xr devd 8 ,
|
.Xr devd 8 ,
|
||||||
.Xr sysctl 8
|
.Xr sysctl 8
|
||||||
.Sh HISTORY
|
.Sh HISTORY
|
||||||
|
|||||||
@@ -58,6 +58,9 @@
|
|||||||
#include <dev/acpica/acpivar.h>
|
#include <dev/acpica/acpivar.h>
|
||||||
#include <dev/asmc/asmcvar.h>
|
#include <dev/asmc/asmcvar.h>
|
||||||
|
|
||||||
|
#include <dev/backlight/backlight.h>
|
||||||
|
#include "backlight_if.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Device interface.
|
* Device interface.
|
||||||
*/
|
*/
|
||||||
@@ -66,6 +69,15 @@ static int asmc_attach(device_t dev);
|
|||||||
static int asmc_detach(device_t dev);
|
static int asmc_detach(device_t dev);
|
||||||
static int asmc_resume(device_t dev);
|
static int asmc_resume(device_t dev);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Backlight interface.
|
||||||
|
*/
|
||||||
|
static int asmc_backlight_update_status(device_t dev,
|
||||||
|
struct backlight_props *props);
|
||||||
|
static int asmc_backlight_get_status(device_t dev,
|
||||||
|
struct backlight_props *props);
|
||||||
|
static int asmc_backlight_get_info(device_t dev, struct backlight_info *info);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* SMC functions.
|
* SMC functions.
|
||||||
*/
|
*/
|
||||||
@@ -581,6 +593,12 @@ static device_method_t asmc_methods[] = {
|
|||||||
DEVMETHOD(device_attach, asmc_attach),
|
DEVMETHOD(device_attach, asmc_attach),
|
||||||
DEVMETHOD(device_detach, asmc_detach),
|
DEVMETHOD(device_detach, asmc_detach),
|
||||||
DEVMETHOD(device_resume, asmc_resume),
|
DEVMETHOD(device_resume, asmc_resume),
|
||||||
|
|
||||||
|
/* Backlight interface */
|
||||||
|
DEVMETHOD(backlight_update_status, asmc_backlight_update_status),
|
||||||
|
DEVMETHOD(backlight_get_status, asmc_backlight_get_status),
|
||||||
|
DEVMETHOD(backlight_get_info, asmc_backlight_get_info),
|
||||||
|
|
||||||
DEVMETHOD_END
|
DEVMETHOD_END
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -609,6 +627,7 @@ static unsigned int light_control = 0;
|
|||||||
ACPI_PNP_INFO(asmc_ids);
|
ACPI_PNP_INFO(asmc_ids);
|
||||||
DRIVER_MODULE(asmc, acpi, asmc_driver, NULL, NULL);
|
DRIVER_MODULE(asmc, acpi, asmc_driver, NULL, NULL);
|
||||||
MODULE_DEPEND(asmc, acpi, 1, 1, 1);
|
MODULE_DEPEND(asmc, acpi, 1, 1, 1);
|
||||||
|
MODULE_DEPEND(asmc, backlight, 1, 1, 1);
|
||||||
|
|
||||||
static const struct asmc_model *
|
static const struct asmc_model *
|
||||||
asmc_match(device_t dev)
|
asmc_match(device_t dev)
|
||||||
@@ -800,6 +819,13 @@ asmc_attach(device_t dev)
|
|||||||
CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_ANYBODY | CTLFLAG_MPSAFE,
|
CTLTYPE_INT | CTLFLAG_RW | CTLFLAG_ANYBODY | CTLFLAG_MPSAFE,
|
||||||
dev, 0, model->smc_light_control, "I",
|
dev, 0, model->smc_light_control, "I",
|
||||||
"Keyboard backlight brightness control");
|
"Keyboard backlight brightness control");
|
||||||
|
|
||||||
|
sc->sc_kbd_bkl = backlight_register("asmc", dev);
|
||||||
|
if (sc->sc_kbd_bkl == NULL) {
|
||||||
|
device_printf(dev, "Can not register backlight\n");
|
||||||
|
ret = ENXIO;
|
||||||
|
goto err;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (model->smc_sms_x == NULL)
|
if (model->smc_sms_x == NULL)
|
||||||
@@ -882,6 +908,9 @@ asmc_detach(device_t dev)
|
|||||||
{
|
{
|
||||||
struct asmc_softc *sc = device_get_softc(dev);
|
struct asmc_softc *sc = device_get_softc(dev);
|
||||||
|
|
||||||
|
if (sc->sc_kbd_bkl != NULL)
|
||||||
|
backlight_destroy(sc->sc_kbd_bkl);
|
||||||
|
|
||||||
if (sc->sc_sms_tq) {
|
if (sc->sc_sms_tq) {
|
||||||
taskqueue_drain(sc->sc_sms_tq, &sc->sc_sms_task);
|
taskqueue_drain(sc->sc_sms_tq, &sc->sc_sms_task);
|
||||||
taskqueue_free(sc->sc_sms_tq);
|
taskqueue_free(sc->sc_sms_tq);
|
||||||
@@ -1739,6 +1768,7 @@ static int
|
|||||||
asmc_mbp_sysctl_light_control(SYSCTL_HANDLER_ARGS)
|
asmc_mbp_sysctl_light_control(SYSCTL_HANDLER_ARGS)
|
||||||
{
|
{
|
||||||
device_t dev = (device_t)arg1;
|
device_t dev = (device_t)arg1;
|
||||||
|
struct asmc_softc *sc = device_get_softc(dev);
|
||||||
uint8_t buf[2];
|
uint8_t buf[2];
|
||||||
int error;
|
int error;
|
||||||
int v;
|
int v;
|
||||||
@@ -1750,6 +1780,7 @@ asmc_mbp_sysctl_light_control(SYSCTL_HANDLER_ARGS)
|
|||||||
if (v < 0 || v > 255)
|
if (v < 0 || v > 255)
|
||||||
return (EINVAL);
|
return (EINVAL);
|
||||||
light_control = v;
|
light_control = v;
|
||||||
|
sc->sc_kbd_bkl_level = v * 100 / 255;
|
||||||
buf[0] = light_control;
|
buf[0] = light_control;
|
||||||
buf[1] = 0x00;
|
buf[1] = 0x00;
|
||||||
asmc_key_write(dev, ASMC_KEY_LIGHTVALUE, buf, sizeof(buf));
|
asmc_key_write(dev, ASMC_KEY_LIGHTVALUE, buf, sizeof(buf));
|
||||||
@@ -1817,3 +1848,38 @@ asmc_wol_sysctl(SYSCTL_HANDLER_ARGS)
|
|||||||
|
|
||||||
return (0);
|
return (0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
asmc_backlight_update_status(device_t dev, struct backlight_props *props)
|
||||||
|
{
|
||||||
|
struct asmc_softc *sc = device_get_softc(dev);
|
||||||
|
uint8_t buf[2];
|
||||||
|
|
||||||
|
sc->sc_kbd_bkl_level = props->brightness;
|
||||||
|
light_control = props->brightness * 255 / 100;
|
||||||
|
buf[0] = light_control;
|
||||||
|
buf[1] = 0x00;
|
||||||
|
asmc_key_write(dev, ASMC_KEY_LIGHTVALUE, buf, sizeof(buf));
|
||||||
|
|
||||||
|
return (0);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
asmc_backlight_get_status(device_t dev, struct backlight_props *props)
|
||||||
|
{
|
||||||
|
struct asmc_softc *sc = device_get_softc(dev);
|
||||||
|
|
||||||
|
props->brightness = sc->sc_kbd_bkl_level;
|
||||||
|
props->nlevels = 0;
|
||||||
|
|
||||||
|
return (0);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
asmc_backlight_get_info(device_t dev, struct backlight_info *info)
|
||||||
|
{
|
||||||
|
info->type = BACKLIGHT_TYPE_KEYBOARD;
|
||||||
|
strlcpy(info->name, "Apple MacBook Keyboard", BACKLIGHTMAXNAMELENGTH);
|
||||||
|
|
||||||
|
return (0);
|
||||||
|
}
|
||||||
|
|||||||
@@ -51,6 +51,8 @@ struct asmc_softc {
|
|||||||
struct taskqueue *sc_sms_tq;
|
struct taskqueue *sc_sms_tq;
|
||||||
struct task sc_sms_task;
|
struct task sc_sms_task;
|
||||||
uint8_t sc_sms_intr_works;
|
uint8_t sc_sms_intr_works;
|
||||||
|
struct cdev *sc_kbd_bkl;
|
||||||
|
uint32_t sc_kbd_bkl_level;
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
.PATH: ${SRCTOP}/sys/dev/asmc
|
.PATH: ${SRCTOP}/sys/dev/asmc
|
||||||
|
|
||||||
KMOD= asmc
|
KMOD= asmc
|
||||||
SRCS= asmc.c opt_acpi.h opt_asmc.h acpi_if.h bus_if.h device_if.h
|
SRCS= asmc.c opt_acpi.h opt_asmc.h
|
||||||
|
SRCS+= acpi_if.h backlight_if.h bus_if.h device_if.h
|
||||||
|
|
||||||
.include <bsd.kmod.mk>
|
.include <bsd.kmod.mk>
|
||||||
|
|||||||
Reference in New Issue
Block a user