xref: /linux/drivers/leds/leds-cobalt-raq.c (revision 58e16d792a6a8c6b750f637a4649967fcac853dc)
1*16216333SThomas Gleixner // SPDX-License-Identifier: GPL-2.0-or-later
297da7aafSYoichi Yuasa /*
397da7aafSYoichi Yuasa  *  LEDs driver for the Cobalt Raq series.
497da7aafSYoichi Yuasa  *
5ada8e951SYoichi Yuasa  *  Copyright (C) 2007  Yoichi Yuasa <yuasa@linux-mips.org>
697da7aafSYoichi Yuasa  */
797da7aafSYoichi Yuasa #include <linux/init.h>
897da7aafSYoichi Yuasa #include <linux/io.h>
997da7aafSYoichi Yuasa #include <linux/ioport.h>
1097da7aafSYoichi Yuasa #include <linux/leds.h>
1197da7aafSYoichi Yuasa #include <linux/platform_device.h>
1297da7aafSYoichi Yuasa #include <linux/spinlock.h>
1397da7aafSYoichi Yuasa #include <linux/types.h>
14d131c496SPaul Gortmaker #include <linux/export.h>
1597da7aafSYoichi Yuasa 
1697da7aafSYoichi Yuasa #define LED_WEB		0x04
1797da7aafSYoichi Yuasa #define LED_POWER_OFF	0x08
1897da7aafSYoichi Yuasa 
1997da7aafSYoichi Yuasa static void __iomem *led_port;
2097da7aafSYoichi Yuasa static u8 led_value;
2197da7aafSYoichi Yuasa static DEFINE_SPINLOCK(led_value_lock);
2297da7aafSYoichi Yuasa 
raq_web_led_set(struct led_classdev * led_cdev,enum led_brightness brightness)2397da7aafSYoichi Yuasa static void raq_web_led_set(struct led_classdev *led_cdev,
2497da7aafSYoichi Yuasa 			    enum led_brightness brightness)
2597da7aafSYoichi Yuasa {
2697da7aafSYoichi Yuasa 	unsigned long flags;
2797da7aafSYoichi Yuasa 
2897da7aafSYoichi Yuasa 	spin_lock_irqsave(&led_value_lock, flags);
2997da7aafSYoichi Yuasa 
3097da7aafSYoichi Yuasa 	if (brightness)
3197da7aafSYoichi Yuasa 		led_value |= LED_WEB;
3297da7aafSYoichi Yuasa 	else
3397da7aafSYoichi Yuasa 		led_value &= ~LED_WEB;
3497da7aafSYoichi Yuasa 	writeb(led_value, led_port);
3597da7aafSYoichi Yuasa 
3697da7aafSYoichi Yuasa 	spin_unlock_irqrestore(&led_value_lock, flags);
3797da7aafSYoichi Yuasa }
3897da7aafSYoichi Yuasa 
3997da7aafSYoichi Yuasa static struct led_classdev raq_web_led = {
40db3f5207SOlaf Hering 	.name		= "raq::web",
4197da7aafSYoichi Yuasa 	.brightness_set	= raq_web_led_set,
4297da7aafSYoichi Yuasa };
4397da7aafSYoichi Yuasa 
raq_power_off_led_set(struct led_classdev * led_cdev,enum led_brightness brightness)4497da7aafSYoichi Yuasa static void raq_power_off_led_set(struct led_classdev *led_cdev,
4597da7aafSYoichi Yuasa 				  enum led_brightness brightness)
4697da7aafSYoichi Yuasa {
4797da7aafSYoichi Yuasa 	unsigned long flags;
4897da7aafSYoichi Yuasa 
4997da7aafSYoichi Yuasa 	spin_lock_irqsave(&led_value_lock, flags);
5097da7aafSYoichi Yuasa 
5197da7aafSYoichi Yuasa 	if (brightness)
5297da7aafSYoichi Yuasa 		led_value |= LED_POWER_OFF;
5397da7aafSYoichi Yuasa 	else
5497da7aafSYoichi Yuasa 		led_value &= ~LED_POWER_OFF;
5597da7aafSYoichi Yuasa 	writeb(led_value, led_port);
5697da7aafSYoichi Yuasa 
5797da7aafSYoichi Yuasa 	spin_unlock_irqrestore(&led_value_lock, flags);
5897da7aafSYoichi Yuasa }
5997da7aafSYoichi Yuasa 
6097da7aafSYoichi Yuasa static struct led_classdev raq_power_off_led = {
61db3f5207SOlaf Hering 	.name			= "raq::power-off",
6297da7aafSYoichi Yuasa 	.brightness_set		= raq_power_off_led_set,
6397da7aafSYoichi Yuasa 	.default_trigger	= "power-off",
6497da7aafSYoichi Yuasa };
6597da7aafSYoichi Yuasa 
cobalt_raq_led_probe(struct platform_device * pdev)6698ea1ea2SBill Pemberton static int cobalt_raq_led_probe(struct platform_device *pdev)
6797da7aafSYoichi Yuasa {
6897da7aafSYoichi Yuasa 	struct resource *res;
6997da7aafSYoichi Yuasa 	int retval;
7097da7aafSYoichi Yuasa 
7197da7aafSYoichi Yuasa 	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
7297da7aafSYoichi Yuasa 	if (!res)
7397da7aafSYoichi Yuasa 		return -EBUSY;
7497da7aafSYoichi Yuasa 
7550e51943SJingoo Han 	led_port = devm_ioremap(&pdev->dev, res->start, resource_size(res));
7697da7aafSYoichi Yuasa 	if (!led_port)
7797da7aafSYoichi Yuasa 		return -ENOMEM;
7897da7aafSYoichi Yuasa 
7997da7aafSYoichi Yuasa 	retval = led_classdev_register(&pdev->dev, &raq_power_off_led);
8097da7aafSYoichi Yuasa 	if (retval)
8150e51943SJingoo Han 		goto err_null;
8297da7aafSYoichi Yuasa 
8397da7aafSYoichi Yuasa 	retval = led_classdev_register(&pdev->dev, &raq_web_led);
8497da7aafSYoichi Yuasa 	if (retval)
8597da7aafSYoichi Yuasa 		goto err_unregister;
8697da7aafSYoichi Yuasa 
8797da7aafSYoichi Yuasa 	return 0;
8897da7aafSYoichi Yuasa 
8997da7aafSYoichi Yuasa err_unregister:
9097da7aafSYoichi Yuasa 	led_classdev_unregister(&raq_power_off_led);
9197da7aafSYoichi Yuasa 
9250e51943SJingoo Han err_null:
9397da7aafSYoichi Yuasa 	led_port = NULL;
9497da7aafSYoichi Yuasa 
9597da7aafSYoichi Yuasa 	return retval;
9697da7aafSYoichi Yuasa }
9797da7aafSYoichi Yuasa 
9897da7aafSYoichi Yuasa static struct platform_driver cobalt_raq_led_driver = {
9997da7aafSYoichi Yuasa 	.probe	= cobalt_raq_led_probe,
10097da7aafSYoichi Yuasa 	.driver = {
10197da7aafSYoichi Yuasa 		.name	= "cobalt-raq-leds",
10297da7aafSYoichi Yuasa 	},
10397da7aafSYoichi Yuasa };
10497da7aafSYoichi Yuasa 
105cee0122dSGeliang Tang builtin_platform_driver(cobalt_raq_led_driver);
106