Lines Matching +full:led +full:- +full:current +full:- +full:microamp
1 // SPDX-License-Identifier: GPL-2.0
3 * Awinic AW20036/AW20054/AW20072 LED driver
22 #define AW200XX_DIM_MAX (BIT(6) - 1)
23 #define AW200XX_FADE_MAX (BIT(8) - 1)
40 AW200XX_REG(AW200XX_NUM_PAGES - 1, AW200XX_PAGE_SIZE - 1)
60 /* Global current configuration register */
75 ((x) + (((x) / (columns)) * (AW200XX_DSIZE_COLUMNS_MAX - (columns))))
77 /* DIM current configuration register on page 1 */
82 * DIM current configuration register (page 4).
83 * The even address for current DIM configuration.
84 * The odd address for current FADE configuration
126 struct aw200xx_led *led = container_of(cdev, struct aw200xx_led, cdev); in dim_show() local
127 int dim = led->dim; in dim_show()
139 struct aw200xx_led *led = container_of(cdev, struct aw200xx_led, cdev); in dim_store() local
140 struct aw200xx *chip = led->chip; in dim_store()
141 u32 columns = chip->cdef->display_size_columns; in dim_store()
146 dim = -1; in dim_store()
153 return -EINVAL; in dim_store()
156 mutex_lock(&chip->mutex); in dim_store()
159 ret = regmap_write(chip->regmap, in dim_store()
160 AW200XX_REG_DIM_PAGE1(led->num, columns), in dim_store()
166 led->dim = dim; in dim_store()
170 mutex_unlock(&chip->mutex); in dim_store()
184 struct aw200xx_led *led = container_of(cdev, struct aw200xx_led, cdev); in aw200xx_brightness_set() local
185 struct aw200xx *chip = led->chip; in aw200xx_brightness_set()
190 mutex_lock(&chip->mutex); in aw200xx_brightness_set()
192 reg = AW200XX_REG_DIM(led->num, chip->cdef->display_size_columns); in aw200xx_brightness_set()
194 dim = led->dim; in aw200xx_brightness_set()
200 ret = regmap_write(chip->regmap, reg, dim); in aw200xx_brightness_set()
204 ret = regmap_write(chip->regmap, in aw200xx_brightness_set()
208 mutex_unlock(&chip->mutex); in aw200xx_brightness_set()
219 * The output current of each LED (see p.14 of datasheet for formula): in aw200xx_imax_from_global()
229 led_imax_uA = global_imax_uA * AW200XX_DUTY_RATIO(chip->display_rows); in aw200xx_imax_from_global()
238 u32 duty = AW200XX_DUTY_RATIO(chip->display_rows); in aw200xx_imax_to_global()
240 /* The output current of each LED (see p.14 of datasheet for formula) */ in aw200xx_imax_to_global()
250 * The AW200XX has a 4-bit register (GCCR) to configure the global current,
252 * of the global current, divided into two parts:
254 * +-----------+-----------------+-----------+-----------------+
256 * +-----------+-----------------+-----------+-----------------+
265 * +-----------+-----------------+-----------+-----------------+
269 * So we have two formulas to calculate the global current:
307 return -EINVAL; in aw200xx_set_imax()
309 return regmap_update_bits(chip->regmap, AW200XX_REG_GCCR, in aw200xx_set_imax()
318 ret = regmap_write(chip->regmap, AW200XX_REG_RSTR, AW200XX_RSTR_RESET); in aw200xx_chip_reset()
322 regcache_mark_dirty(chip->regmap); in aw200xx_chip_reset()
323 return regmap_write(chip->regmap, AW200XX_REG_FCD, AW200XX_FCD_CLEAR); in aw200xx_chip_reset()
330 ret = regmap_write(chip->regmap, AW200XX_REG_DSIZE, in aw200xx_chip_init()
331 chip->display_rows - 1); in aw200xx_chip_init()
335 ret = regmap_write(chip->regmap, AW200XX_REG_SLPCR, in aw200xx_chip_init()
340 return regmap_update_bits(chip->regmap, AW200XX_REG_GCCR, in aw200xx_chip_init()
346 struct device *dev = &chip->client->dev; in aw200xx_chip_check()
350 ret = regmap_read(chip->regmap, AW200XX_REG_IDR, &chipid); in aw200xx_chip_check()
355 return dev_err_probe(dev, -ENODEV, in aw200xx_chip_check()
368 ret = device_property_read_u32(dev, "awinic,display-rows", in aw200xx_probe_fw()
369 &chip->display_rows); in aw200xx_probe_fw()
372 "Failed to read 'display-rows' property\n"); in aw200xx_probe_fw()
374 if (!chip->display_rows || in aw200xx_probe_fw()
375 chip->display_rows > chip->cdef->display_size_rows_max) { in aw200xx_probe_fw()
376 return dev_err_probe(dev, -EINVAL, in aw200xx_probe_fw()
378 chip->display_rows); in aw200xx_probe_fw()
388 struct aw200xx_led *led; in aw200xx_probe_fw() local
394 chip->num_leds--; in aw200xx_probe_fw()
398 if (source >= chip->cdef->channels) { in aw200xx_probe_fw()
399 dev_err(dev, "LED reg %u out of range (max %u)\n", in aw200xx_probe_fw()
400 source, chip->cdef->channels); in aw200xx_probe_fw()
401 chip->num_leds--; in aw200xx_probe_fw()
405 ret = fwnode_property_read_u32(child, "led-max-microamp", in aw200xx_probe_fw()
408 dev_info(&chip->client->dev, in aw200xx_probe_fw()
409 "DT property led-max-microamp is missing\n"); in aw200xx_probe_fw()
411 dev_err(dev, "Invalid value %u for led-max-microamp\n", in aw200xx_probe_fw()
413 chip->num_leds--; in aw200xx_probe_fw()
419 led = &chip->leds[i]; in aw200xx_probe_fw()
420 led->dim = -1; in aw200xx_probe_fw()
421 led->num = source; in aw200xx_probe_fw()
422 led->chip = chip; in aw200xx_probe_fw()
423 led->cdev.brightness_set_blocking = aw200xx_brightness_set; in aw200xx_probe_fw()
424 led->cdev.groups = dim_groups; in aw200xx_probe_fw()
427 ret = devm_led_classdev_register_ext(dev, &led->cdev, in aw200xx_probe_fw()
437 if (!chip->num_leds) in aw200xx_probe_fw()
438 return -EINVAL; in aw200xx_probe_fw()
497 cdef = device_get_match_data(&client->dev); in aw200xx_probe()
499 return -ENODEV; in aw200xx_probe()
501 count = device_get_child_node_count(&client->dev); in aw200xx_probe()
502 if (!count || count > cdef->channels) in aw200xx_probe()
503 return dev_err_probe(&client->dev, -EINVAL, in aw200xx_probe()
506 chip = devm_kzalloc(&client->dev, struct_size(chip, leds, count), in aw200xx_probe()
509 return -ENOMEM; in aw200xx_probe()
511 chip->cdef = cdef; in aw200xx_probe()
512 chip->num_leds = count; in aw200xx_probe()
513 chip->client = client; in aw200xx_probe()
516 chip->regmap = devm_regmap_init_i2c(client, &aw200xx_regmap_config); in aw200xx_probe()
517 if (IS_ERR(chip->regmap)) in aw200xx_probe()
518 return PTR_ERR(chip->regmap); in aw200xx_probe()
524 mutex_init(&chip->mutex); in aw200xx_probe()
527 mutex_lock(&chip->mutex); in aw200xx_probe()
533 ret = aw200xx_probe_fw(&client->dev, chip); in aw200xx_probe()
540 mutex_unlock(&chip->mutex); in aw200xx_probe()
549 mutex_destroy(&chip->mutex); in aw200xx_remove()
598 MODULE_DESCRIPTION("AW200XX LED driver");