OSDN Git Service

leds: qpnp-flash-v2: Add operational current property
authorDevesh Jhunjhunwala <deveshj@codeaurora.org>
Thu, 30 Jun 2016 00:48:12 +0000 (17:48 -0700)
committerKyle Yan <kyan@codeaurora.org>
Fri, 8 Jul 2016 18:52:36 +0000 (11:52 -0700)
Add the qcom,current-ma property to specify the operational
current for the flash led. Also limit the minimum flash current
to 25mA since currents below this value cause unstable flash
operation.

CRs-Fixed: 1033071
Change-Id: Ia133b6c0cf0c21484f61631f04cba0d1112c9d48
Signed-off-by: Devesh Jhunjhunwala <deveshj@codeaurora.org>
Documentation/devicetree/bindings/leds/leds-qpnp-flash-v2.txt
drivers/leds/leds-qpnp-flash-v2.c
include/linux/leds-qpnp-flash-v2.h

index ce2cec5..f1a8c77 100644 (file)
@@ -36,6 +36,8 @@ serve as an overall switch.
                          10ms resolution. This is not required for switch node.
 
 Optional properties inside child node:
+- qcom,current-ma      : operational current intensity for LED in mA. Accepted values are a
+                         positive integer in the range of 0 to qcom,max-current inclusive.
 - qcom,ires-ua         : Integer type to specify current resolution. Accepted values should be
                          12500, 10000, 7500, and 5000. Unit is uA.
 - qcom,hdrm-voltage-mv : Integer type specifying headroom voltage. Values are from 125mV to 500mV
@@ -69,6 +71,7 @@ Example:
                        qcom,default-led-trigger =
                                                "flash0_trigger";
                        qcom,id = <0>;
+                       qcom,current-ma = <1000>;
                        qcom,duration-ms = <1280>;
                        qcom,ires-ua = <12500>;
                        qcom,hdrm-voltage-mv = <325>;
@@ -82,6 +85,7 @@ Example:
                        qcom,default-led-trigger =
                                                "flash1_trigger";
                        qcom,id = <1>;
+                       qcom,current-ma = <1000>;
                        qcom,duration-ms = <1280>;
                        qcom,ires-ua = <12500>;
                        qcom,hdrm-voltage-mv = <325>;
@@ -95,6 +99,7 @@ Example:
                        qcom,default-led-trigger =
                                                "flash2_trigger";
                        qcom,id = <2>;
+                       qcom,current-ma = <500>;
                        qcom,duration-ms = <1280>;
                        qcom,ires-ua = <12500>;
                        qcom,hdrm-voltage-mv = <325>;
@@ -111,6 +116,7 @@ Example:
                        qcom,default-led-trigger =
                                                "torch0_trigger";
                        qcom,id = <0>;
+                       qcom,current-ma = <300>;
                        qcom,ires-ua = <12500>;
                        qcom,hdrm-voltage-mv = <325>;
                        qcom,hdrm-vol-hi-lo-win-mv = <100>;
@@ -123,6 +129,7 @@ Example:
                        qcom,default-led-trigger =
                                                "torch1_trigger";
                        qcom,id = <1>;
+                       qcom,current-ma = <300>;
                        qcom,ires-ua = <12500>;
                        qcom,hdrm-voltage-mv = <325>;
                        qcom,hdrm-vol-hi-lo-win-mv = <100>;
@@ -135,6 +142,7 @@ Example:
                        qcom,default-led-trigger =
                                                "torch2_trigger";
                        qcom,id = <2>;
+                       qcom,current-ma = <300>;
                        qcom,ires-ua = <12500>;
                        qcom,hdrm-voltage-mv = <325>;
                        qcom,hdrm-vol-hi-lo-win-mv = <100>;
index 8963655..6f7ba04 100644 (file)
@@ -38,8 +38,6 @@
 #define        FLASH_LED_MOD_CTRL_MASK                 0x80
 #define        FLASH_LED_ISC_DELAY_MASK                0x03
 
-#define        FLASH_LED_TYPE_FLASH                    0
-#define        FLASH_LED_TYPE_TORCH                    1
 #define        FLASH_LED_HEADROOM_AUTO_MODE_ENABLED    true
 #define        FLASH_LED_ISC_DELAY_SHIFT               6
 #define        FLASH_LED_ISC_DELAY_DEFAULT_US          3
 #define        FLASH_LED_MOD_ENABLE                    0x80
 #define        FLASH_LED_DISABLE                       0x00
 #define        FLASH_LED_SAFETY_TMR_DISABLED           0x13
+#define        FLASH_LED_MIN_CURRENT_MA                25
+
+enum flash_led_type {
+       FLASH_LED_TYPE_FLASH,
+       FLASH_LED_TYPE_TORCH,
+};
 
 /*
  * Flash LED configuration read from device tree
@@ -141,13 +145,17 @@ static int qpnp_flash_led_init_settings(struct qpnp_flash_led *led)
 
 static void qpnp_flash_led_node_set(struct flash_node_data *fnode, int value)
 {
-       int prgm_current_ma;
+       int prgm_current_ma = value;
 
-       prgm_current_ma = value < 0 ? 0 : value;
-       prgm_current_ma = value > fnode->cdev.max_brightness ?
-                                       fnode->cdev.max_brightness : value;
+       if (value <= 0)
+               prgm_current_ma = 0;
+       else if (value < FLASH_LED_MIN_CURRENT_MA)
+               prgm_current_ma = FLASH_LED_MIN_CURRENT_MA;
+
+       prgm_current_ma = min(prgm_current_ma, fnode->max_current);
+       fnode->current_ma = prgm_current_ma;
        fnode->cdev.brightness = prgm_current_ma;
-       fnode->brightness = prgm_current_ma * 1000 / fnode->ires_ua + 1;
+       fnode->current_reg_val = prgm_current_ma * 1000 / fnode->ires_ua + 1;
        fnode->led_on = prgm_current_ma != 0;
 }
 
@@ -182,7 +190,7 @@ static int qpnp_flash_led_switch_set(struct flash_switch_data *snode, bool on)
 
                rc = qpnp_flash_led_masked_write(led,
                        FLASH_LED_REG_TGR_CURRENT(led->base + addr_offset),
-                       FLASH_LED_CURRENT_MASK, led->fnode[i].brightness);
+                       FLASH_LED_CURRENT_MASK, led->fnode[i].current_reg_val);
                if (rc)
                        return rc;
 
@@ -240,6 +248,7 @@ leds_turn_off:
                        FLASH_LED_CURRENT_MASK, 0);
                if (rc)
                        return rc;
+
                led->fnode[i].led_on = false;
 
                if (led->fnode[i].pinctrl) {
@@ -305,14 +314,6 @@ static int qpnp_flash_led_parse_each_led_dt(struct qpnp_flash_led *led,
                return rc;
        }
 
-       rc = of_property_read_u32(node, "qcom,max-current", &val);
-       if (!rc) {
-               fnode->cdev.max_brightness = val;
-       } else {
-               dev_err(&led->pdev->dev, "Unable to read max current\n");
-               return rc;
-       }
-
        rc = of_property_read_string(node, "label", &temp_string);
        if (!rc) {
                if (!strcmp(temp_string, "flash"))
@@ -355,6 +356,36 @@ static int qpnp_flash_led_parse_each_led_dt(struct qpnp_flash_led *led,
                return rc;
        }
 
+       rc = of_property_read_u32(node, "qcom,max-current", &val);
+       if (!rc) {
+               if (val < FLASH_LED_MIN_CURRENT_MA)
+                       val = FLASH_LED_MIN_CURRENT_MA;
+               fnode->max_current = val;
+               fnode->cdev.max_brightness = val;
+       } else {
+               dev_err(&led->pdev->dev,
+                               "Unable to read max current, rc=%d\n", rc);
+               return rc;
+       }
+
+       rc = of_property_read_u32(node, "qcom,current-ma", &val);
+       if (!rc) {
+               if (val < FLASH_LED_MIN_CURRENT_MA ||
+                               val > fnode->max_current)
+                       dev_warn(&led->pdev->dev,
+                                "Invalid operational current specified, capping it\n");
+               if (val < FLASH_LED_MIN_CURRENT_MA)
+                       val = FLASH_LED_MIN_CURRENT_MA;
+               if (val > fnode->max_current)
+                       val = fnode->max_current;
+               fnode->current_ma = val;
+               fnode->cdev.brightness = val;
+       } else if (rc != -EINVAL) {
+               dev_err(&led->pdev->dev,
+                       "Unable to read operational current, rc=%d\n", rc);
+               return rc;
+       }
+
        fnode->duration = FLASH_LED_SAFETY_TMR_DISABLED;
        rc = of_property_read_u32(node, "qcom,duration-ms", &val);
        if (!rc) {
index 353466f..ae36a16 100644 (file)
@@ -26,13 +26,14 @@ struct flash_node_data {
        struct pinctrl_state            *gpio_state_active;
        struct pinctrl_state            *gpio_state_suspend;
        int                             ires_ua;
-       u16                             prgm_current;
+       int                             max_current;
+       int                             current_ma;
        u8                              duration;
        u8                              id;
        u8                              type;
        u8                              ires;
        u8                              hdrm_val;
-       u8                              brightness;
+       u8                              current_reg_val;
        bool                            led_on;
 };