Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit d6287a3c authored by Chun Zhang's avatar Chun Zhang Committed by Abinaya P
Browse files

leds: leds-qpnp-flash: modify code to support single/dual flash



Flash LEDs were hardcoded as 0,1 and Torch LEDs were hard coded
as 2,3 in LED array. This may lead to issues in targets where
only single flash/torch LED is present. Hence, modify the code
to make it applicable for any generic case (single/dual LED).

Change-Id: Ia8d6eb98fb84310b3234b8deccfe7f604d6aa09a
Signed-off-by: default avatarChun Zhang <chunz@codeaurora.org>
parent 0e4d2cfe
Loading
Loading
Loading
Loading
+118 −108
Original line number Diff line number Diff line
@@ -175,6 +175,7 @@ struct flash_node_data {
	u32				boost_voltage_max;
	u16				max_current;
	u16				prgm_current;
	u16				prgm_current2;
	u16				duration;
	u8				id;
	u8				type;
@@ -918,6 +919,8 @@ static int qpnp_flash_led_module_disable(struct qpnp_flash_led *led,
	}

	if (led->pdata->hdrm_sns_ch0_en) {
		if (flash_node->id == FLASH_LED_0 ||
				flash_node->id == FLASH_LED_SWITCH) {
			rc = qpnp_led_masked_write(led->spmi_dev,
				FLASH_HDRM_SNS_ENABLE_CTRL0(led->base),
				FLASH_LED_HDRM_SNS_ENABLE_MASK,
@@ -928,8 +931,11 @@ static int qpnp_flash_led_module_disable(struct qpnp_flash_led *led,
				return rc;
			}
		}
	}

	if (led->pdata->hdrm_sns_ch1_en) {
		if (flash_node->id == FLASH_LED_1 ||
				flash_node->id == FLASH_LED_SWITCH) {
			rc = qpnp_led_masked_write(led->spmi_dev,
				FLASH_HDRM_SNS_ENABLE_CTRL1(led->base),
				FLASH_LED_HDRM_SNS_ENABLE_MASK,
@@ -940,6 +946,7 @@ static int qpnp_flash_led_module_disable(struct qpnp_flash_led *led,
				return rc;
			}
		}
	}

	rc = qpnp_led_masked_write(led->spmi_dev,
			FLASH_MODULE_ENABLE_CTRL(led->base),
@@ -973,8 +980,10 @@ static int qpnp_flash_led_module_disable(struct qpnp_flash_led *led,
		}
	}

	if (!led->flash_node[0].flash_on &&
		!led->flash_node[2].flash_on) {
	if (flash_node->id == FLASH_LED_SWITCH)
		flash_node->trigger = 0;

	if (!(flash_node->trigger & FLASH_LED0_TRIGGER)) {
		rc = qpnp_led_masked_write(led->spmi_dev,
				led->current_addr,
				FLASH_CURRENT_MASK, 0x00);
@@ -985,8 +994,7 @@ static int qpnp_flash_led_module_disable(struct qpnp_flash_led *led,
		}
	}

	if (!led->flash_node[1].flash_on &&
		!led->flash_node[3].flash_on) {
	if (!(flash_node->trigger & FLASH_LED1_TRIGGER)) {
		rc = qpnp_led_masked_write(led->spmi_dev,
				led->current2_addr,
				FLASH_CURRENT_MASK, 0x00);
@@ -1018,6 +1026,7 @@ static void qpnp_flash_led_work(struct work_struct *work)
	union power_supply_propval psy_prop;
	int rc, brightness = flash_node->cdev.brightness;
	int max_curr_avail_ma = 0;
	int total_curr_ma = 0;
	int i;
	u8 val;

@@ -1114,11 +1123,11 @@ static void qpnp_flash_led_work(struct work_struct *work)
				"Torch reg write failed\n");
			goto exit_flash_led_work;
		}
		if (led->flash_node[led->num_leds - 1].id ==
							FLASH_LED_SWITCH) {
			val = (u8)(led->flash_node[2].prgm_current *

		if (flash_node->id == FLASH_LED_SWITCH) {
			val = (u8)(flash_node->prgm_current *
						FLASH_TORCH_MAX_LEVEL
					/ led->flash_node[2].max_current);
						/ flash_node->max_current);
			rc = qpnp_led_masked_write(led->spmi_dev,
						led->current_addr,
						FLASH_CURRENT_MASK, val);
@@ -1128,9 +1137,9 @@ static void qpnp_flash_led_work(struct work_struct *work)
				goto exit_flash_led_work;
			}

			val = (u8)(led->flash_node[3].prgm_current *
			val = (u8)(flash_node->prgm_current2 *
						FLASH_TORCH_MAX_LEVEL
					/ led->flash_node[3].max_current);
						/ flash_node->max_current);
			rc = qpnp_led_masked_write(led->spmi_dev,
					led->current2_addr,
					FLASH_CURRENT_MASK, val);
@@ -1182,46 +1191,49 @@ static void qpnp_flash_led_work(struct work_struct *work)
			goto exit_flash_led_work;
		}

		if (led->pdata->hdrm_sns_ch0_en) {
			if (led->flash_node[2].flash_on) {
		if (led->pdata->hdrm_sns_ch0_en ||
						led->pdata->hdrm_sns_ch1_en) {
			if (flash_node->id == FLASH_LED_SWITCH) {
				rc = qpnp_led_masked_write(led->spmi_dev,
					FLASH_HDRM_SNS_ENABLE_CTRL0(led->base),
					FLASH_LED_HDRM_SNS_ENABLE_MASK,
					FLASH_LED_HDRM_SNS_ENABLE);
					flash_node->trigger &
					FLASH_LED0_TRIGGER ?
					FLASH_LED_HDRM_SNS_ENABLE :
					FLASH_LED_HDRM_SNS_DISABLE);
				if (rc) {
					dev_err(&led->spmi_dev->dev,
					"Headroom sense enable failed\n");
					goto exit_flash_led_work;
				}
			} else {

				rc = qpnp_led_masked_write(led->spmi_dev,
					FLASH_HDRM_SNS_ENABLE_CTRL0(led->base),
					FLASH_HDRM_SNS_ENABLE_CTRL1(led->base),
					FLASH_LED_HDRM_SNS_ENABLE_MASK,
					flash_node->trigger &
					FLASH_LED1_TRIGGER ?
					FLASH_LED_HDRM_SNS_ENABLE :
					FLASH_LED_HDRM_SNS_DISABLE);
				if (rc) {
					dev_err(&led->spmi_dev->dev,
					"Headroom sense disable failed\n");
					"Headroom sense enable failed\n");
					goto exit_flash_led_work;
				}
			}
		}

		if (led->pdata->hdrm_sns_ch1_en) {
			if (led->flash_node[3].flash_on) {
			} else if (flash_node->id == FLASH_LED_0) {
				rc = qpnp_led_masked_write(led->spmi_dev,
					FLASH_HDRM_SNS_ENABLE_CTRL1(led->base),
					FLASH_HDRM_SNS_ENABLE_CTRL0(led->base),
					FLASH_LED_HDRM_SNS_ENABLE_MASK,
					FLASH_LED_HDRM_SNS_ENABLE);
				if (rc) {
					dev_err(&led->spmi_dev->dev,
					"Headroom sense enable failed\n");
					"Headroom sense disable failed\n");
					goto exit_flash_led_work;
				}
			} else {
			} else if (flash_node->id == FLASH_LED_1) {
				rc = qpnp_led_masked_write(led->spmi_dev,
					FLASH_HDRM_SNS_ENABLE_CTRL1(led->base),
					FLASH_LED_HDRM_SNS_ENABLE_MASK,
					FLASH_LED_HDRM_SNS_DISABLE);
					FLASH_LED_HDRM_SNS_ENABLE);
				if (rc) {
					dev_err(&led->spmi_dev->dev,
					"Headroom sense disable failed\n");
@@ -1232,18 +1244,19 @@ static void qpnp_flash_led_work(struct work_struct *work)

		rc = qpnp_led_masked_write(led->spmi_dev,
			FLASH_LED_STROBE_CTRL(led->base),
			FLASH_STROBE_MASK,
			(flash_node->id == FLASH_LED_SWITCH ? FLASH_STROBE_MASK
							: flash_node->trigger),
							flash_node->trigger);
		if (rc) {
			dev_err(&led->spmi_dev->dev,
				"Strobe ctrl reg write failed\n");
				"Strobe reg write failed\n");
			goto exit_flash_led_work;
		}
	} else if (flash_node->type == FLASH) {
		if (led->flash_node[0].flash_on)
			max_curr_avail_ma += led->flash_node[0].max_current;
		if (led->flash_node[1].flash_on)
			max_curr_avail_ma += led->flash_node[1].max_current;
		if (flash_node->trigger & FLASH_LED0_TRIGGER)
			max_curr_avail_ma += flash_node->max_current;
		if (flash_node->trigger & FLASH_LED1_TRIGGER)
			max_curr_avail_ma += flash_node->max_current;

		psy_prop.intval = true;
		rc = led->battery_psy->set_property(led->battery_psy,
@@ -1286,53 +1299,33 @@ static void qpnp_flash_led_work(struct work_struct *work)
			}
		}

		if (led->flash_node[led->num_leds - 1].id ==
							FLASH_LED_SWITCH) {
			if (led->flash_node[0].flash_on &&
					led->flash_node[1].flash_on) {
				if (max_curr_avail_ma <
					flash_node->prgm_current) {
					led->flash_node[0].prgm_current =
						led->flash_node[0].prgm_current
						* max_curr_avail_ma /
						flash_node->prgm_current;
					led->flash_node[1].prgm_current =
						led->flash_node[1].prgm_current
							* max_curr_avail_ma /
						flash_node->prgm_current;
		if (flash_node->id == FLASH_LED_SWITCH) {
			if (flash_node->trigger & FLASH_LED0_TRIGGER)
				total_curr_ma += flash_node->prgm_current;
			else if (flash_node->trigger & FLASH_LED1_TRIGGER)
				total_curr_ma += flash_node->prgm_current2;

			if (max_curr_avail_ma < total_curr_ma) {
				flash_node->prgm_current *=
					max_curr_avail_ma / total_curr_ma;
				flash_node->prgm_current2 *=
					max_curr_avail_ma / total_curr_ma;
			}
			} else {
				led->flash_node[0].prgm_current
					= (max_curr_avail_ma <
					led->flash_node[0].prgm_current)
					? max_curr_avail_ma :
					led->flash_node[0].prgm_current;

				led->flash_node[1].prgm_current
					= (max_curr_avail_ma <
					led->flash_node[1].prgm_current)
					? max_curr_avail_ma :
					led->flash_node[1].prgm_current;
			}

			val = (u8)(led->flash_node[0].prgm_current *
						FLASH_MAX_LEVEL /
					led->flash_node[0].max_current);

			val = (u8)(flash_node->prgm_current *
				FLASH_MAX_LEVEL / flash_node->max_current);
			rc = qpnp_led_masked_write(led->spmi_dev,
						led->current_addr,
						FLASH_CURRENT_MASK, val);
				led->current_addr, FLASH_CURRENT_MASK, val);
			if (rc) {
				dev_err(&led->spmi_dev->dev,
					"Current register write failed\n");
				goto exit_flash_led_work;
			}

			val = (u8)(led->flash_node[1].prgm_current *
						FLASH_MAX_LEVEL /
					led->flash_node[1].max_current);
			val = (u8)(flash_node->prgm_current2 *
				FLASH_MAX_LEVEL / flash_node->max_current);
			rc = qpnp_led_masked_write(led->spmi_dev,
						led->current2_addr,
						FLASH_CURRENT_MASK, val);
				led->current2_addr, FLASH_CURRENT_MASK, val);
			if (rc) {
				dev_err(&led->spmi_dev->dev,
					"Current register write failed\n");
@@ -1408,46 +1401,49 @@ static void qpnp_flash_led_work(struct work_struct *work)
						FLASH_RAMP_UP_DELAY_US_MAX);
		}

		if (led->pdata->hdrm_sns_ch0_en) {
			if (led->flash_node[0].flash_on) {
		if (led->pdata->hdrm_sns_ch0_en ||
					led->pdata->hdrm_sns_ch1_en) {
			if (flash_node->id == FLASH_LED_SWITCH) {
				rc = qpnp_led_masked_write(led->spmi_dev,
					FLASH_HDRM_SNS_ENABLE_CTRL0(led->base),
					FLASH_LED_HDRM_SNS_ENABLE_MASK,
					FLASH_LED_HDRM_SNS_ENABLE);
					(flash_node->trigger &
					FLASH_LED0_TRIGGER ?
					FLASH_LED_HDRM_SNS_ENABLE :
					FLASH_LED_HDRM_SNS_DISABLE));
				if (rc) {
					dev_err(&led->spmi_dev->dev,
					"Headroom sense enable failed\n");
					goto exit_flash_led_work;
				}
			} else {

				rc = qpnp_led_masked_write(led->spmi_dev,
					FLASH_HDRM_SNS_ENABLE_CTRL0(led->base),
					FLASH_HDRM_SNS_ENABLE_CTRL1(led->base),
					FLASH_LED_HDRM_SNS_ENABLE_MASK,
					FLASH_LED_HDRM_SNS_DISABLE);
					(flash_node->trigger &
					FLASH_LED1_TRIGGER ?
					FLASH_LED_HDRM_SNS_ENABLE :
					FLASH_LED_HDRM_SNS_DISABLE));
				if (rc) {
					dev_err(&led->spmi_dev->dev,
					"Headroom sense disable failed\n");
					"Headroom sense enable failed\n");
					goto exit_flash_led_work;
				}
			}
		}

		if (led->pdata->hdrm_sns_ch1_en) {
			if (led->flash_node[1].flash_on) {
			} else if (flash_node->id == FLASH_LED_0) {
				rc = qpnp_led_masked_write(led->spmi_dev,
					FLASH_HDRM_SNS_ENABLE_CTRL1(led->base),
					FLASH_HDRM_SNS_ENABLE_CTRL0(led->base),
					FLASH_LED_HDRM_SNS_ENABLE_MASK,
					FLASH_LED_HDRM_SNS_ENABLE);
				if (rc) {
					dev_err(&led->spmi_dev->dev,
					"Headroom sense enable failed\n");
					"Headroom sense disable failed\n");
					goto exit_flash_led_work;
				}
			} else {
			} else if (flash_node->id == FLASH_LED_1) {
				rc = qpnp_led_masked_write(led->spmi_dev,
					FLASH_HDRM_SNS_ENABLE_CTRL1(led->base),
					FLASH_LED_HDRM_SNS_ENABLE_MASK,
					FLASH_LED_HDRM_SNS_DISABLE);
					FLASH_LED_HDRM_SNS_ENABLE);
				if (rc) {
					dev_err(&led->spmi_dev->dev,
					"Headroom sense disable failed\n");
@@ -1458,7 +1454,8 @@ static void qpnp_flash_led_work(struct work_struct *work)

		rc = qpnp_led_masked_write(led->spmi_dev,
			FLASH_LED_STROBE_CTRL(led->base),
			FLASH_STROBE_MASK,
			(flash_node->id == FLASH_LED_SWITCH ? FLASH_STROBE_MASK
							: flash_node->trigger),
							flash_node->trigger);
		if (rc) {
			dev_err(&led->spmi_dev->dev,
@@ -1548,24 +1545,37 @@ static void qpnp_flash_led_brightness_set(struct led_classdev *led_cdev,
		else if (flash_node->type == FLASH)
			led->flash_node[led->num_leds - 1].type = FLASH;

		led->flash_node[led->num_leds - 1].max_current
						= flash_node->max_current;

		if (flash_node->id == FLASH_LED_0 ||
					 flash_node->id == FLASH_LED_1) {
			if (value < FLASH_LED_MIN_CURRENT_MA && value != 0)
				value = FLASH_LED_MIN_CURRENT_MA;

			flash_node->prgm_current = value;
			flash_node->flash_on = value ? true : false;
			if (value)
			if (value) {
				led->flash_node[led->num_leds - 1].trigger |=
						0x80 >> flash_node->id;
			else
				led->flash_node[led->num_leds - 1].trigger = 0;
						(0x80 >> flash_node->id);
				if (flash_node->id == FLASH_LED_0)
					led->flash_node[led->num_leds - 1].
					prgm_current = flash_node->prgm_current;
				else if (flash_node->id == FLASH_LED_1)
					led->flash_node[led->num_leds - 1].
					prgm_current2 =
					flash_node->prgm_current;
			} else {
				led->flash_node[led->num_leds - 1].trigger &=
						~(0x80 >> flash_node->id);
			}

			return;
		} else if (flash_node->id == FLASH_LED_SWITCH) {
			if (led->flash_node[0].flash_on ||
					led->flash_node[1].flash_on)
				flash_node->prgm_current =
					led->flash_node[0].prgm_current +
					led->flash_node[1].prgm_current;
			if (!value) {
				flash_node->prgm_current = 0;
				flash_node->prgm_current2 = 0;
			}
		}
	} else {
		if (value < FLASH_LED_MIN_CURRENT_MA && value != 0)