From 0d779b6c43559d5f291025183873d02d208e914b Mon Sep 17 00:00:00 2001 From: Jeremy Soller Date: Wed, 18 Apr 2018 10:25:38 -0600 Subject: [PATCH] Add hard drive LED --- hdd_led.c | 67 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ system76.c | 12 ++++++++-- 2 files changed, 77 insertions(+), 2 deletions(-) create mode 100644 hdd_led.c diff --git a/hdd_led.c b/hdd_led.c new file mode 100644 index 0000000..5e0153f --- /dev/null +++ b/hdd_led.c @@ -0,0 +1,67 @@ +/* + * hdd_led.c + * + * Copyright (C) 2017 Jeremy Soller + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or (at + * your option) any later version. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +static enum led_brightness hdd_led_brightness = 1; + +static enum led_brightness hdd_led_get(struct led_classdev *led_cdev) { + return hdd_led_brightness; +} + +static int hdd_led_set(struct led_classdev *led_cdev, enum led_brightness value) { + S76_INFO("hdd_led_set %d\n", (int)value); + + if (value > 0) { + s76_wmbb(0x79, 0x090000FF, NULL); + } else { + s76_wmbb(0x79, 0x09000000, NULL); + } + + return 0; +} + +static struct led_classdev hdd_led = { + .name = "system76::hdd", + .brightness_get = hdd_led_get, + .brightness_set_blocking = hdd_led_set, + .max_brightness = 1, + .default_trigger = "disk-activity" +}; + +static void hdd_led_resume(void) { + hdd_led_set(&hdd_led, hdd_led_brightness); +} + +static int __init hdd_led_init(struct device *dev) { + int err; + + err = led_classdev_register(dev, &hdd_led); + if (unlikely(err)) { + return err; + } + + hdd_led_resume(); + + return 0; +} + +static void __exit hdd_led_exit(void) { + if (!IS_ERR_OR_NULL(hdd_led.dev)) { + led_classdev_unregister(&hdd_led); + } +} diff --git a/system76.c b/system76.c index 7c1f92f..04b3528 100644 --- a/system76.c +++ b/system76.c @@ -92,6 +92,7 @@ static int s76_wmbb(u32 method_id, u32 arg, u32 *retval) { } #include "ap_led.c" +#include "hdd_led.c" #include "input.c" #include "kb_led.c" #include "hwmon.c" @@ -214,12 +215,17 @@ static int s76_probe(struct platform_device *dev) { err = ap_led_init(&dev->dev); if (unlikely(err)) { - S76_ERROR("Could not register LED device\n"); + S76_ERROR("Could not register airplane LED device\n"); + } + + err = hdd_led_init(&dev->dev); + if (unlikely(err)) { + S76_ERROR("Could not register harddrive LED device\n"); } err = kb_led_init(&dev->dev); if (unlikely(err)) { - S76_ERROR("Could not register LED device\n"); + S76_ERROR("Could not register keyboard LED device\n"); } err = s76_input_init(&dev->dev); @@ -257,6 +263,7 @@ static int s76_remove(struct platform_device *dev) { s76_input_exit(); kb_led_exit(); + hdd_led_exit(); ap_led_exit(); return 0; @@ -279,6 +286,7 @@ static int s76_resume(struct platform_device *dev) { s76_wmbb(0x46, 0, NULL); ap_led_resume(); + hdd_led_resume(); kb_led_resume(); return 0;