summaryrefslogtreecommitdiffstats
path: root/drivers/led/led-pwm.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/led/led-pwm.c')
-rw-r--r--drivers/led/led-pwm.c51
1 files changed, 24 insertions, 27 deletions
diff --git a/drivers/led/led-pwm.c b/drivers/led/led-pwm.c
index 16d22b5569..6f4abf97c8 100644
--- a/drivers/led/led-pwm.c
+++ b/drivers/led/led-pwm.c
@@ -1,21 +1,8 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
/*
* pwm LED support for barebox
*
* (C) Copyright 2010 Sascha Hauer, Pengutronix
- *
- * See file CREDITS for list of people who contributed to this
- * project.
- *
- * 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.
- *
*/
#include <common.h>
#include <malloc.h>
@@ -23,52 +10,61 @@
#include <led.h>
#include <pwm.h>
#include <of.h>
-#include <asm-generic/div64.h>
+#include <linux/math64.h>
struct pwmled {
bool active_low;
struct led led;
struct pwm_device *pwm;
- uint32_t period;
};
static void led_pwm_set(struct led *led, unsigned int brightness)
{
struct pwmled *pwmled = container_of(led, struct pwmled, led);
- unsigned long long duty = pwmled->period;
+ unsigned long long duty;
+ struct pwm_state state;
unsigned int max = pwmled->led.max_value;
- duty *= brightness;
+ pwm_get_state(pwmled->pwm, &state);
+
+ duty = state.period * brightness;
do_div(duty, max);
- pwm_config(pwmled->pwm, duty, pwmled->period);
+ if (pwmled->active_low)
+ duty = state.period - duty;
+
+ state.enabled = true;
+ state.duty_cycle = duty;
+
+ pwm_apply_state(pwmled->pwm, &state);
}
-static int led_pwm_of_probe(struct device_d *dev)
+static int led_pwm_of_probe(struct device *dev)
{
struct device_node *child;
int ret;
- for_each_child_of_node(dev->device_node, child) {
+ for_each_child_of_node(dev->of_node, child) {
struct pwmled *pwmled;
struct pwm_device *pwm;
pwm = of_pwm_request(child, NULL);
- if (pwm < 0)
+ if (IS_ERR(pwm))
continue;
pwmled = xzalloc(sizeof(*pwmled));
pwmled->led.name = xstrdup(child->name);
pwmled->pwm = pwm;
- of_property_read_u32(child, "max-brightness", &pwmled->led.max_value);
+ ret = of_property_read_u32(child, "max-brightness", &pwmled->led.max_value);
+ if (ret)
+ return ret;
- pwmled->period = pwm_get_period(pwmled->pwm);
+ pwmled->active_low = of_property_read_bool(child, "active-low");
pwmled->led.set = led_pwm_set;
- pwm_config(pwmled->pwm, 0, pwmled->period);
- pwm_enable(pwmled->pwm);
+ led_pwm_set(&pwmled->led, 0);
ret = led_register(&pwmled->led);
if (ret)
@@ -84,8 +80,9 @@ static struct of_device_id led_pwm_of_ids[] = {
{ .compatible = "pwm-leds", },
{ }
};
+MODULE_DEVICE_TABLE(of, led_pwm_of_ids);
-static struct driver_d led_pwm_of_driver = {
+static struct driver led_pwm_of_driver = {
.name = "pwm-leds",
.probe = led_pwm_of_probe,
.of_compatible = DRV_OF_COMPAT(led_pwm_of_ids),