Register LEDs immediately after parsing their properties. This allows us to get rid of platdata, and since no one in tree uses header linux/platform_data/leds-pca963x.h, remove it. Signed-off-by: Marek Behún <marek.behun@xxxxxx> Cc: Peter Meerwald <p.meerwald@xxxxxxxxxxxxxxxxxx> Cc: Ricardo Ribalda <ribalda@xxxxxxxxxx> Cc: Zahari Petkov <zahari@xxxxxxxxx> --- drivers/leds/leds-pca963x.c | 188 ++++++++------------- include/linux/platform_data/leds-pca963x.h | 35 ---- 2 files changed, 71 insertions(+), 152 deletions(-) delete mode 100644 include/linux/platform_data/leds-pca963x.h diff --git a/drivers/leds/leds-pca963x.c b/drivers/leds/leds-pca963x.c index 73dc00787beed..5083ccce1a519 100644 --- a/drivers/leds/leds-pca963x.c +++ b/drivers/leds/leds-pca963x.c @@ -32,7 +32,6 @@ #include <linux/property.h> #include <linux/slab.h> #include <linux/of.h> -#include <linux/platform_data/leds-pca963x.h> /* LED select registers determine the source that drives LED outputs */ #define PCA963X_LED_OFF 0x0 /* LED driver off */ @@ -102,7 +101,6 @@ struct pca963x_led { struct pca963x *chip; struct led_classdev led_cdev; int led_num; /* 0 .. 15 potentially */ - char name[32]; u8 gdc; u8 gfrq; }; @@ -284,72 +282,85 @@ static int pca963x_blink_set(struct led_classdev *led_cdev, return 0; } -static struct pca963x_platform_data * -pca963x_get_pdata(struct device *dev, struct pca963x_chipdef *chipdef) +static int pca963x_register_leds(struct i2c_client *client, + struct pca963x *chip) { - struct pca963x_platform_data *pdata; - struct led_info *pca963x_leds; + struct pca963x_chipdef *chipdef = chip->chipdef; + struct pca963x_led *led = chip->leds; + struct device *dev = &client->dev; struct fwnode_handle *child; - int count; + const char *name; + char label[64]; + bool hw_blink; + s32 mode2; + u32 reg; + int ret; - count = device_get_child_node_count(dev); - if (!count || count > chipdef->n_leds) - return ERR_PTR(-ENODEV); + if (device_property_read_u32(dev, "nxp,period-scale", + &chipdef->scaling)) + chipdef->scaling = 1000; - pca963x_leds = devm_kcalloc(dev, chipdef->n_leds, - sizeof(struct led_info), GFP_KERNEL); - if (!pca963x_leds) - return ERR_PTR(-ENOMEM); + hw_blink = device_property_read_bool(dev, "nxp,hw-blink"); - device_for_each_child_node(dev, child) { - struct led_info led = {}; - u32 reg; - int res; + mode2 = i2c_smbus_read_byte_data(client, PCA963X_MODE2); + if (mode2 < 0) + return mode2; - res = fwnode_property_read_u32(child, "reg", ®); - if ((res != 0) || (reg >= chipdef->n_leds)) - continue; + /* default to open-drain unless totem pole (push-pull) is specified */ + if (device_property_read_bool(dev, "nxp,totem-pole")) + mode2 |= PCA963X_MODE2_OUTDRV; + else + mode2 &= ~PCA963X_MODE2_OUTDRV; - res = fwnode_property_read_string(child, "label", &led.name); - if ((res != 0) && is_of_node(child)) - led.name = to_of_node(child)->name; + /* default to non-inverted output, unless inverted is specified */ + if (device_property_read_bool(dev, "nxp,inverted-out")) + mode2 |= PCA963X_MODE2_INVRT; + else + mode2 &= ~PCA963X_MODE2_INVRT; - fwnode_property_read_string(child, "linux,default-trigger", - &led.default_trigger); + ret = i2c_smbus_write_byte_data(client, PCA963X_MODE2, mode2); + if (ret < 0) + return ret; - pca963x_leds[reg] = led; - } - pdata = devm_kzalloc(dev, sizeof(struct pca963x_platform_data), - GFP_KERNEL); - if (!pdata) - return ERR_PTR(-ENOMEM); + device_for_each_child_node(dev, child) { + ret = fwnode_property_read_u32(child, "reg", ®); + if (ret || reg >= chipdef->n_leds) { + dev_err(dev, "Invalid 'reg' property for node %pfw\n", + child); + ret = -EINVAL; + goto err; + } - pdata->leds.leds = pca963x_leds; - pdata->leds.num_leds = chipdef->n_leds; + ret = fwnode_property_read_string(child, "label", &name); + if (!fwnode_property_read_string(child, "label", &name)) + snprintf(label, sizeof(label), "pca963x:%s", name); + else + snprintf(label, sizeof(label), "pca963x::"); - /* default to open-drain unless totem pole (push-pull) is specified */ - if (device_property_read_bool(dev, "nxp,totem-pole")) - pdata->outdrv = PCA963X_TOTEM_POLE; - else - pdata->outdrv = PCA963X_OPEN_DRAIN; + fwnode_property_read_string(child, "linux,default-trigger", + &led->led_cdev.default_trigger); - /* default to software blinking unless hardware blinking is specified */ - if (device_property_read_bool(dev, "nxp,hw-blink")) - pdata->blink_type = PCA963X_HW_BLINK; - else - pdata->blink_type = PCA963X_SW_BLINK; + led->led_num = reg; + led->chip = chip; + led->led_cdev.name = label; + led->led_cdev.brightness_set_blocking = pca963x_led_set; + if (hw_blink) + led->led_cdev.blink_set = pca963x_blink_set; - if (device_property_read_u32(dev, "nxp,period-scale", - &chipdef->scaling)) - chipdef->scaling = 1000; + ret = devm_led_classdev_register(dev, &led->led_cdev); + if (ret) { + dev_err(dev, "Failed to register LED for node %pfw\n", + child); + goto err; + } - /* default to non-inverted output, unless inverted is specified */ - if (device_property_read_bool(dev, "nxp,inverted-out")) - pdata->dir = PCA963X_INVERTED; - else - pdata->dir = PCA963X_NORMAL; + ++led; + } - return pdata; + return 0; +err: + fwnode_handle_put(child); + return ret; } static const struct of_device_id of_pca963x_match[] = { @@ -366,30 +377,19 @@ static int pca963x_probe(struct i2c_client *client, { struct device *dev = &client->dev; struct pca963x_chipdef *chipdef; - struct pca963x_platform_data *pdata; struct pca963x *chip; - int i, err; + int i, count; chipdef = &pca963x_chipdefs[id->driver_data]; - pdata = dev_get_platdata(dev); - if (!pdata) { - pdata = pca963x_get_pdata(dev, chipdef); - if (IS_ERR(pdata)) { - dev_warn(dev, "could not parse configuration\n"); - pdata = NULL; - } - } - - if (pdata && (pdata->leds.num_leds < 1 || - pdata->leds.num_leds > chipdef->n_leds)) { - dev_err(dev, "board info must claim 1-%d LEDs", - chipdef->n_leds); + count = device_get_child_node_count(dev); + if (!count || count > chipdef->n_leds) { + dev_err(dev, "Node %pfw must define between 1 and %d LEDs\n", + dev_fwnode(dev), chipdef->n_leds); return -EINVAL; } - chip = devm_kzalloc(dev, struct_size(chip, leds, chipdef->n_leds), - GFP_KERNEL); + chip = devm_kzalloc(dev, struct_size(chip, leds, count), GFP_KERNEL); if (!chip) return -ENOMEM; @@ -403,56 +403,10 @@ static int pca963x_probe(struct i2c_client *client, for (i = 0; i < chipdef->n_leds / 4; i++) i2c_smbus_write_byte_data(client, chipdef->ledout_base + i, 0x00); - for (i = 0; i < chipdef->n_leds; i++) { - struct pca963x_led *led = &chip->leds[i]; - - led->led_num = i; - led->chip = chip; - - /* Platform data can specify LED names and default triggers */ - if (pdata && i < pdata->leds.num_leds) { - if (pdata->leds.leds[i].name) - snprintf(led->name, - sizeof(led->name), "pca963x:%s", - pdata->leds.leds[i].name); - if (pdata->leds.leds[i].default_trigger) - led->led_cdev.default_trigger = - pdata->leds.leds[i].default_trigger; - } - if (!pdata || i >= pdata->leds.num_leds || - !pdata->leds.leds[i].name) - snprintf(led->name, sizeof(led->name), - "pca963x:%d:%.2x:%d", client->adapter->nr, - client->addr, i); - - led->led_cdev.name = led->name; - led->led_cdev.brightness_set_blocking = pca963x_led_set; - - if (pdata && pdata->blink_type == PCA963X_HW_BLINK) - led->led_cdev.blink_set = pca963x_blink_set; - - err = devm_led_classdev_register(dev, &led->led_cdev); - if (err < 0) - return err; - } - /* Disable LED all-call address, and power down initially */ i2c_smbus_write_byte_data(client, PCA963X_MODE1, BIT(4)); - if (pdata) { - u8 mode2 = i2c_smbus_read_byte_data(client, PCA963X_MODE2); - /* Configure output: open-drain or totem pole (push-pull) */ - if (pdata->outdrv == PCA963X_OPEN_DRAIN) - mode2 &= ~PCA963X_MODE2_OUTDRV; - else - mode2 |= PCA963X_MODE2_OUTDRV; - /* Configure direction: normal or inverted */ - if (pdata->dir == PCA963X_INVERTED) - mode2 |= PCA963X_MODE2_INVRT; - i2c_smbus_write_byte_data(client, PCA963X_MODE2, mode2); - } - - return 0; + return pca963x_register_leds(client, chip); } static struct i2c_driver pca963x_driver = { diff --git a/include/linux/platform_data/leds-pca963x.h b/include/linux/platform_data/leds-pca963x.h deleted file mode 100644 index 6091337ce4bfb..0000000000000 --- a/include/linux/platform_data/leds-pca963x.h +++ /dev/null @@ -1,35 +0,0 @@ -/* SPDX-License-Identifier: GPL-2.0-only */ -/* - * PCA963X LED chip driver. - * - * Copyright 2012 bct electronic GmbH - * Copyright 2013 Qtechnology A/S - */ - -#ifndef __LINUX_PCA963X_H -#define __LINUX_PCA963X_H -#include <linux/leds.h> - -enum pca963x_outdrv { - PCA963X_OPEN_DRAIN, - PCA963X_TOTEM_POLE, /* aka push-pull */ -}; - -enum pca963x_blink_type { - PCA963X_SW_BLINK, - PCA963X_HW_BLINK, -}; - -enum pca963x_direction { - PCA963X_NORMAL, - PCA963X_INVERTED, -}; - -struct pca963x_platform_data { - struct led_platform_data leds; - enum pca963x_outdrv outdrv; - enum pca963x_blink_type blink_type; - enum pca963x_direction dir; -}; - -#endif /* __LINUX_PCA963X_H*/ -- 2.26.2