1 // SPDX-License-Identifier: GPL-2.0+ 2 /* 3 * Copyright (c) 2015 Google, Inc 4 * Written by Simon Glass <sjg@chromium.org> 5 */ 6 7 #include <common.h> 8 #include <dm.h> 9 #include <errno.h> 10 #include <led.h> 11 #include <dm/device-internal.h> 12 #include <dm/root.h> 13 #include <dm/uclass-internal.h> 14 15 int led_get_by_label(const char *label, struct udevice **devp) 16 { 17 struct udevice *dev; 18 struct uclass *uc; 19 int ret; 20 21 ret = uclass_get(UCLASS_LED, &uc); 22 if (ret) 23 return ret; 24 uclass_foreach_dev(dev, uc) { 25 struct led_uc_plat *uc_plat = dev_get_uclass_platdata(dev); 26 27 /* Ignore the top-level LED node */ 28 if (uc_plat->label && !strcmp(label, uc_plat->label)) 29 return uclass_get_device_tail(dev, 0, devp); 30 } 31 32 return -ENODEV; 33 } 34 35 int led_set_state(struct udevice *dev, enum led_state_t state) 36 { 37 struct led_ops *ops = led_get_ops(dev); 38 39 if (!ops->set_state) 40 return -ENOSYS; 41 42 return ops->set_state(dev, state); 43 } 44 45 enum led_state_t led_get_state(struct udevice *dev) 46 { 47 struct led_ops *ops = led_get_ops(dev); 48 49 if (!ops->get_state) 50 return -ENOSYS; 51 52 return ops->get_state(dev); 53 } 54 55 #ifdef CONFIG_LED_BLINK 56 int led_set_period(struct udevice *dev, int period_ms) 57 { 58 struct led_ops *ops = led_get_ops(dev); 59 60 if (!ops->set_period) 61 return -ENOSYS; 62 63 return ops->set_period(dev, period_ms); 64 } 65 #endif 66 67 int led_default_state(void) 68 { 69 struct udevice *dev; 70 struct uclass *uc; 71 const char *default_state; 72 int ret; 73 74 ret = uclass_get(UCLASS_LED, &uc); 75 if (ret) 76 return ret; 77 for (uclass_find_first_device(UCLASS_LED, &dev); 78 dev; 79 uclass_find_next_device(&dev)) { 80 default_state = dev_read_string(dev, "default-state"); 81 if (!default_state) 82 continue; 83 ret = device_probe(dev); 84 if (ret) 85 return ret; 86 if (!strncmp(default_state, "on", 2)) 87 led_set_state(dev, LEDST_ON); 88 else if (!strncmp(default_state, "off", 3)) 89 led_set_state(dev, LEDST_OFF); 90 /* default-state = "keep" : device is only probed */ 91 } 92 93 return ret; 94 } 95 96 UCLASS_DRIVER(led) = { 97 .id = UCLASS_LED, 98 .name = "led", 99 .per_device_platdata_auto_alloc_size = sizeof(struct led_uc_plat), 100 }; 101