Thread (26 messages) 26 messages, 6 authors, 2020-09-15

Re: [PATCH v3 1/2] leds: mt6360: Add LED driver for MT6360

From: Gene Chen <hidden>
Date: 2020-09-10 08:11:35
Also in: linux-arm-kernel, linux-leds, linux-mediatek, lkml

Andy Shevchenko [off-list ref] 於 2020年9月9日 週三 下午9:48寫道:
On Mon, Sep 7, 2020 at 1:31 PM Gene Chen [off-list ref] wrote:
quoted
From: Gene Chen <redacted>

Add MT6360 LED driver include 2-channel Flash LED with torch/strobe mode,
and 4-channel RGB LED support Register/Flash/Breath Mode
I'm wondering why you don't use struct led_classdev_flash.

...
Both Flash and RGB LED use led_classdev_flash by
"devm_led_classdev_flash_register_ext".
quoted
+//
+// Copyright (C) 2020 MediaTek Inc.
+//
Do you really need these two // lines?
ACK, I will remove it
...
quoted
+enum {
+       MT6360_LED_ISNK1 = 0,
+       MT6360_LED_ISNK2,
+       MT6360_LED_ISNK3,
+       MT6360_LED_ISNK4,
+       MT6360_LED_FLASH1,
+       MT6360_LED_FLASH2,
quoted
+       MT6360_MAX_LEDS,
No comma for terminator entry.
ACK
quoted
+};
...
quoted
+#define MT6360_ISNK_MASK               0x1F
GENMASK()

...
quoted
+#define MT6360_ITORCH_MIN              25000
+#define MT6360_ITORCH_STEP             12500
+#define MT6360_ITORCH_MAX              400000
+#define MT6360_ISTRB_MIN               50000
+#define MT6360_ISTRB_STEP              12500
+#define MT6360_ISTRB_MAX               1500000
+#define MT6360_STRBTO_MIN              64000
+#define MT6360_STRBTO_STEP             32000
+#define MT6360_STRBTO_MAX              2432000
Add unit suffixes, please.
ACK
...
quoted
+#define FLED_TORCH_FLAG_MASK           0x0c
quoted
+#define FLED_STROBE_FLAG_MASK          0x03
GENMASK()
ACK
...
quoted
+       dev_dbg(lcdev->dev, "[%d] brightness %d\n", led->led_no, level);
Not production noise.
ACK
...
quoted
+       ret = regmap_update_bits(priv->regmap, MT6360_REG_RGBEN, enable_mask, val);
+       if (ret)
+               return ret;
+
+       return 0;
return regmap...
quoted
+       u32 val = (level) ? MT6360_FLCSEN_MASK(led->led_no) : 0;
Why parens?
ACK
...
quoted
+       dev_dbg(lcdev->dev, "[%d] brightness %d\n", led->led_no, level);
Noise.
ACK
...
quoted
+       if (priv->fled_strobe_used) {
+               dev_warn(lcdev->dev, "Please disable strobe first [%d]\n", priv->fled_strobe_used);
+               return -EINVAL;
Hmm... Shouldn't be guaranteed by some framework?
Because both Flash LED use single logically control.
It doesn't exist one LED is torch mode, and the other is strobe mode.
...
quoted
+               curr = prev & (~BIT(led->led_no));
Too many parens.
ACK
...
quoted
+static int mt6360_strobe_brightness_set(struct led_classdev_flash *fl_cdev, u32 brightness)
+{
+       struct mt6360_led *led = container_of(fl_cdev, struct mt6360_led, flash);
+       struct led_classdev *lcdev = &fl_cdev->led_cdev;
+
quoted
+       dev_dbg(lcdev->dev, "[%d] strobe brightness %d\n", led->led_no, brightness);
Noise. Point of this entire function?
ACK, I will remove it, reserve function entry only for register
ledcass_dev check ops exist
quoted
+       return 0;
+}
...
quoted
+       dev_dbg(lcdev->dev, "[%d] strobe state %d\n", led->led_no, state);
Noise.

If you wish to do it right, add trace events to the framework.
ACK, I will remove it.
...
quoted
+       if (priv->fled_torch_used) {
quoted
+               dev_warn(lcdev->dev, "Please disable torch first [0x%x]\n", priv->fled_torch_used);
Again, why the warning? Can this be a part of the framework?
Same as above.
quoted
+               return -EINVAL;
+       }
...
quoted
+               curr = prev & (~BIT(led->led_no));
Too many parens.
ACK
...
quoted
+       if (!prev && curr)
+               usleep_range(5000, 6000);
+       else if (prev && !curr)
+               udelay(500);
These delays must be explained.
ACK
...
quoted
+       if (led->led_no == MT6360_LED_FLASH1) {
+               strobe_timeout_mask = MT6360_FLED1STRBTO_MASK;
+               fled_short_mask = MT6360_FLED1SHORT_MASK;
quoted
+
Redundant blank line.
ACK
quoted
+       } else {
+               strobe_timeout_mask = MT6360_FLED2STRBTO_MASK;
+               fled_short_mask = MT6360_FLED2SHORT_MASK;
+       }
...
quoted
+static int mt6360_flash_external_strobe_set(struct v4l2_flash *v4l2_flash, bool enable)
+{
+       struct led_classdev_flash *flash = v4l2_flash->fled_cdev;
+       struct mt6360_led *led = container_of(flash, struct mt6360_led, flash);
+       struct mt6360_priv *priv = led->priv;
quoted
+       u32 enable_mask = MT6360_FLCSEN_MASK(led->led_no);
enable_mask -> mask
  u32 value = enable ? mask : 0;
quoted
+       int ret;
+
+       ret = regmap_update_bits(priv->regmap, MT6360_REG_FLEDEN, enable_mask,
quoted
+                                enable ? enable_mask : 0);
  ret =  ... mask, value);
ACK
quoted
+       if (ret)
+               return ret;
+
+       if (enable)
+               priv->fled_strobe_used |= BIT(led->led_no);
+       else
+               priv->fled_strobe_used &= (~BIT(led->led_no));
Too many parens.
ACK
quoted
+
+       return 0;
+}
...
quoted
+       s->val = s->max = (s->min) + (lcdev->max_brightness - 1) * s->step;
Ditto.
ACK
...
quoted
+static void clamp_align(u32 *v, u32 min, u32 max, u32 step)
Can we keep a similar API, i.e. return a new value rather than update old?
quoted
+{
quoted
+       *v = clamp_val(*v, min, max);
I would rather use a temporary variable (and it actually will be
required with above).
quoted
+       if (step > 1)
+               *v = (*v - min) / step * step + min;
Sounds like open coded rounddown().
ACK
quoted
+}
...
quoted
+       lcdev->max_brightness = (val - MT6360_ITORCH_MIN) / MT6360_ITORCH_STEP + 1;
DIV_ROUND_UP(val - MT6360_ITORCH_MIN, MT6360_ITORCH_STEP) ?
This is mapping 0~val to 1~max_brightness as level.
I convert val below MT6360_ITORCH_STEP to 1 for ignore max_brightness
= 0, because 0 means disable.
There is a little difference from DIV_ROUND_UP.
...
quoted
+static int mt6360_init_common_properties(struct mt6360_led *led, struct led_init_data *init_data)
+{
+       const char *str;
+
+       if (!fwnode_property_read_string(init_data->fwnode, "default-state", &str)) {
+               if (!strcmp(str, "on"))
+                       led->default_state = STATE_ON;
+               else if (!strcmp(str, "keep"))
+                       led->default_state = STATE_KEEP;
quoted
+               else
I wouldn't allow some garbage to be off.
ACK
quoted
+                       led->default_state = STATE_OFF;
+       }
What about

static const char * const states = { "on", "keep", "off" };

int ret;

ret = match_string(states, ARRAY_SIZE(states), str);
if (ret)
 ...

default_state = ret;

?
quoted
+       return 0;
+}
ACK
...
quoted
+static int mt6360_led_probe(struct platform_device *pdev)
+{
+       struct mt6360_priv *priv;
+       struct fwnode_handle *child;
+       int i, ret;
+
quoted
+       priv->regmap = dev_get_regmap(pdev->dev.parent, NULL);
+       if (!priv->regmap) {
+               dev_err(&pdev->dev, "Failed to get parent regmap\n");
+               return -ENODEV;
+       }
...
quoted
+out:
out_flash_leds_release: ?
ACK
quoted
+       for (i = MT6360_LED_FLASH1; i <= MT6360_LED_FLASH2; i++) {
+               struct mt6360_led *led = priv->leds[i];
+
+               if (led && led->v4l2_flash)
+                       v4l2_flash_release(led->v4l2_flash);
+
+       }
...
quoted
+static int mt6360_led_remove(struct platform_device *pdev)
+{
+       struct mt6360_priv *priv = platform_get_drvdata(pdev);
+       int i;
+
+       for (i = MT6360_LED_FLASH1; i <= MT6360_LED_FLASH2; i++) {
+               struct mt6360_led *led = priv->leds[i];
+
+               if (led && led->v4l2_flash)
+                       v4l2_flash_release(led->v4l2_flash);
+
+       }
Looks like a code duplication.
ACK
quoted
+
+       return 0;
+}
+
+static const struct of_device_id __maybe_unused mt6360_led_of_id[] = {
+       { .compatible = "mediatek,mt6360-led", },
quoted
+       {},
No need comma.
ACK
quoted
+};

--
With Best Regards,
Andy Shevchenko
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help