Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit df410d52 authored by Marco Chiappero's avatar Marco Chiappero Committed by Matthew Garrett
Browse files

sony-laptop: keyboard backlight fixes



Restore the original state on module removal, set the latest values on
resume.
When setting the keyboard backlight mode try to turn on/off backlight
immediately.

[malattia@linux.it: patch taken from a largely modified sony-laptop.c,
ported and slightly modified to use defines already available.]

Signed-off-by: default avatarMattia Dongili <malattia@linux.it>
Signed-off-by: default avatarMatthew Garrett <mjg@redhat.com>
parent 855b8bc9
Loading
Loading
Loading
Loading
+34 −1
Original line number Diff line number Diff line
@@ -138,6 +138,8 @@ MODULE_PARM_DESC(kbd_backlight_timeout,
		 "1 for 30 seconds, 2 for 60 seconds and 3 to disable timeout "
		 "(default: 0)");

static void sony_nc_kbd_backlight_resume(void);

enum sony_nc_rfkill {
	SONY_WIFI,
	SONY_BLUETOOTH,
@@ -1176,6 +1178,9 @@ static int sony_nc_resume(struct acpi_device *device)
	/* re-read rfkill state */
	sony_nc_rfkill_update();

	/* restore kbd backlight states */
	sony_nc_kbd_backlight_resume();

	return 0;
}

@@ -1363,6 +1368,7 @@ out_no_enum:
#define KBDBL_HANDLER	0x137
#define KBDBL_PRESENT	0xB00
#define	SET_MODE	0xC00
#define SET_STATE	0xD00
#define SET_TIMEOUT	0xE00

struct kbd_backlight {
@@ -1385,6 +1391,10 @@ static ssize_t __sony_nc_kbd_backlight_mode_set(u8 value)
				(value << 0x10) | SET_MODE, &result))
		return -EIO;

	/* Try to turn the light on/off immediately */
	sony_call_snc_handle(KBDBL_HANDLER, (value << 0x10) | SET_STATE,
			&result);

	kbdbl_handle->mode = value;

	return 0;
@@ -1466,7 +1476,7 @@ static int sony_nc_kbd_backlight_setup(struct platform_device *pd)
{
	int result;

	if (sony_call_snc_handle(0x137, KBDBL_PRESENT, &result))
	if (sony_call_snc_handle(KBDBL_HANDLER, KBDBL_PRESENT, &result))
		return 0;
	if (!(result & 0x02))
		return 0;
@@ -1509,13 +1519,36 @@ outkzalloc:
static int sony_nc_kbd_backlight_cleanup(struct platform_device *pd)
{
	if (kbdbl_handle) {
		int result;

		device_remove_file(&pd->dev, &kbdbl_handle->mode_attr);
		device_remove_file(&pd->dev, &kbdbl_handle->timeout_attr);

		/* restore the default hw behaviour */
		sony_call_snc_handle(KBDBL_HANDLER, 0x1000 | SET_MODE, &result);
		sony_call_snc_handle(KBDBL_HANDLER, SET_TIMEOUT, &result);

		kfree(kbdbl_handle);
	}
	return 0;
}

static void sony_nc_kbd_backlight_resume(void)
{
	int ignore = 0;

	if (!kbdbl_handle)
		return;

	if (kbdbl_handle->mode == 0)
		sony_call_snc_handle(KBDBL_HANDLER, SET_MODE, &ignore);

	if (kbdbl_handle->timeout != 0)
		sony_call_snc_handle(KBDBL_HANDLER,
				(kbdbl_handle->timeout << 0x10) | SET_TIMEOUT,
				&ignore);
}

static void sony_nc_backlight_setup(void)
{
	acpi_handle unused;