/* These registers are not used to control leds in LP3944, they can store *arbitraryvalueswhichthechipwillignore.
*/ #define LP3944_REG_REGISTER8 0x08 #define LP3944_REG_REGISTER9 0x09
#define LP3944_DIM0 0 #define LP3944_DIM1 1
/* period in ms */ #define LP3944_PERIOD_MIN 0 #define LP3944_PERIOD_MAX 1600
/* duty cycle is a percentage */ #define LP3944_DUTY_CYCLE_MIN 0 #define LP3944_DUTY_CYCLE_MAX 100
dev_dbg(&led->client->dev, "%s: %s, status before normalization:%d\n",
__func__, led->ldev.name, status);
switch (id) { case LP3944_LED0: case LP3944_LED1: case LP3944_LED2: case LP3944_LED3:
reg = LP3944_REG_LS0; break; case LP3944_LED4: case LP3944_LED5: case LP3944_LED6: case LP3944_LED7:
id -= LP3944_LED4;
reg = LP3944_REG_LS1; break; default: return -EINVAL;
}
if (status > LP3944_LED_STATUS_DIM1) return -EINVAL;
/* *Invertstatusonlywhenit's<2(i.e.0or1)whichmeansit's *controllingtheon/offstatedirectly. *When,instead,statusis>=2don'tinvertitbecauseitwouldmean *tomesswiththehardwareblinkingmode.
*/ if (led->type == LP3944_LED_TYPE_LED_INVERTED && status < 2)
status = 1 - status;
/* units are in ms */ if (*delay_on + *delay_off > LP3944_PERIOD_MAX) return -EINVAL;
if (*delay_on == 0 && *delay_off == 0) { /* Special case: the leds subsystem requires a default user *friendlyblinkpatternfortheLED.Let'sblinktheled *slowly(1Hz).
*/
*delay_on = 500;
*delay_off = 500;
}
period = (*delay_on) + (*delay_off);
/* duty_cycle is the percentage of period during which the led is ON */
duty_cycle = 100 * (*delay_on) / period;
/* invert duty cycle for inverted leds, this has the same effect of *swappingdelay_onanddelay_off
*/ if (led->type == LP3944_LED_TYPE_LED_INVERTED)
duty_cycle = 100 - duty_cycle;
/* NOTE: using always the first DIM mode, this means that all leds *willhavethesameblinkingpattern. * *Wecouldfindawaylatertohavetwoledsblinkinginhardware *withdifferentpatternsatthesametime,fallingbacktosoftware *controlfortheotherones.
*/
err = lp3944_dim_set_period(led->client, LP3944_DIM0, period); if (err) return err;
err = lp3944_dim_set_dutycycle(led->client, LP3944_DIM0, duty_cycle); if (err) return err;
dev_dbg(&led->client->dev, "%s: OK hardware accelerated blink!\n",
__func__);
err = led_classdev_register(&client->dev, &led->ldev); if (err < 0) {
dev_err(&client->dev, "couldn't register LED %s\n",
led->ldev.name); gotoexit;
}
/* to expose the default value to userspace */
led->ldev.brightness =
(enum led_brightness) pled->status;
/* Set the default led status */
err = lp3944_led_set(led, pled->status); if (err < 0) {
dev_err(&client->dev, "%s couldn't set STATUS %d\n",
led->ldev.name, pled->status); gotoexit;
} break;
case LP3944_LED_TYPE_NONE: default: break;
}
} return0;
exit: if (i > 0) for (i = i - 1; i >= 0; i--) switch (pdata->leds[i].type) {
case LP3944_LED_TYPE_LED: case LP3944_LED_TYPE_LED_INVERTED:
led_classdev_unregister(&data->leds[i].ldev); break;
if (lp3944_pdata == NULL) {
dev_err(&client->dev, "no platform data\n"); return -EINVAL;
}
/* Let's see whether this adapter can support what we need. */ if (!i2c_check_functionality(client->adapter,
I2C_FUNC_SMBUS_BYTE_DATA)) {
dev_err(&client->dev, "insufficient functionality!\n"); return -ENODEV;
}
data = devm_kzalloc(&client->dev, sizeof(struct lp3944_data),
GFP_KERNEL); if (!data) return -ENOMEM;
for (i = 0; i < pdata->leds_size; i++) switch (data->leds[i].type) { case LP3944_LED_TYPE_LED: case LP3944_LED_TYPE_LED_INVERTED:
led_classdev_unregister(&data->leds[i].ldev); break;
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.