Merge "power: battery: Add support to enable PPS to work in CV mode"
diff --git a/drivers/power/supply/qcom/battery.c b/drivers/power/supply/qcom/battery.c
index a87725b..8a119ca 100644
--- a/drivers/power/supply/qcom/battery.c
+++ b/drivers/power/supply/qcom/battery.c
@@ -43,6 +43,7 @@
#define FCC_STEPPER_VOTER "FCC_STEPPER_VOTER"
#define FCC_VOTER "FCC_VOTER"
#define MAIN_FCC_VOTER "MAIN_FCC_VOTER"
+#define PD_VOTER "PD_VOTER"
struct pl_data {
int pl_mode;
@@ -190,30 +191,57 @@ static int cp_get_parallel_mode(struct pl_data *chip, int mode)
return pval.intval;
}
-static int get_hvdcp3_icl_limit(struct pl_data *chip)
+static int get_adapter_icl_based_ilim(struct pl_data *chip)
{
- int main_icl, target_icl = -EINVAL;
+ int main_icl, adapter_icl = -EINVAL, rc = -EINVAL, final_icl = -EINVAL;
+ union power_supply_propval pval = {0, };
+ rc = power_supply_get_property(chip->usb_psy,
+ POWER_SUPPLY_PROP_PD_ACTIVE, &pval);
+ if (rc < 0)
+ pr_err("Failed to read PD_ACTIVE status rc=%d\n",
+ rc);
+ /* Check for QC 3, 3.5 and PPS adapters, return if its none of them */
if (chip->charger_type != POWER_SUPPLY_TYPE_USB_HVDCP_3 &&
- chip->charger_type != POWER_SUPPLY_TYPE_USB_HVDCP_3P5)
- return target_icl;
+ chip->charger_type != POWER_SUPPLY_TYPE_USB_HVDCP_3P5 &&
+ pval.intval != POWER_SUPPLY_PD_PPS_ACTIVE)
+ return final_icl;
/*
- * For HVDCP3 adapters, limit max. ILIM as follows:
- * HVDCP3_ICL: Maximum ICL of HVDCP3 adapter(from DT configuration)
- * For Parallel input configurations:
- * VBUS: target_icl = HVDCP3_ICL - main_ICL
- * VMID: target_icl = HVDCP3_ICL
+ * For HVDCP3/HVDCP_3P5 adapters, limit max. ILIM as:
+ * HVDCP3_ICL: Maximum ICL of HVDCP3 adapter(from DT
+ * configuration).
+ *
+ * For PPS adapters, limit max. ILIM to
+ * MIN(qc4_max_icl, PD_CURRENT_MAX)
*/
- target_icl = chip->chg_param->hvdcp3_max_icl_ua;
+ if (pval.intval == POWER_SUPPLY_PD_PPS_ACTIVE) {
+ adapter_icl = min_t(int, chip->chg_param->qc4_max_icl_ua,
+ get_client_vote_locked(chip->usb_icl_votable,
+ PD_VOTER));
+ if (adapter_icl <= 0)
+ adapter_icl = chip->chg_param->qc4_max_icl_ua;
+ } else {
+ adapter_icl = chip->chg_param->hvdcp3_max_icl_ua;
+ }
+
+ /*
+ * For Parallel input configurations:
+ * VBUS: final_icl = adapter_icl - main_ICL
+ * VMID: final_icl = adapter_icl
+ */
+ final_icl = adapter_icl;
if (cp_get_parallel_mode(chip, PARALLEL_INPUT_MODE)
== POWER_SUPPLY_PL_USBIN_USBIN) {
main_icl = get_effective_result_locked(chip->usb_icl_votable);
- if ((main_icl >= 0) && (main_icl < target_icl))
- target_icl -= main_icl;
+ if ((main_icl >= 0) && (main_icl < adapter_icl))
+ final_icl = adapter_icl - main_icl;
}
- return target_icl;
+ pr_debug("charger_type=%d final_icl=%d adapter_icl=%d main_icl=%d\n",
+ chip->charger_type, final_icl, adapter_icl, main_icl);
+
+ return final_icl;
}
/*
@@ -244,7 +272,7 @@ static void cp_configure_ilim(struct pl_data *chip, const char *voter, int ilim)
== POWER_SUPPLY_PL_OUTPUT_VPH)
return;
- target_icl = get_hvdcp3_icl_limit(chip);
+ target_icl = get_adapter_icl_based_ilim(chip);
ilim = (target_icl > 0) ? min(ilim, target_icl) : ilim;
rc = power_supply_get_property(chip->cp_master_psy,
@@ -742,7 +770,7 @@ static void get_fcc_stepper_params(struct pl_data *chip, int main_fcc_ua,
if (!chip->cp_ilim_votable)
chip->cp_ilim_votable = find_votable("CP_ILIM");
- target_icl = get_hvdcp3_icl_limit(chip) * 2;
+ target_icl = get_adapter_icl_based_ilim(chip) * 2;
total_fcc_ua -= chip->main_fcc_ua;
/*
diff --git a/drivers/power/supply/qcom/battery.h b/drivers/power/supply/qcom/battery.h
index acb4984..c614544 100644
--- a/drivers/power/supply/qcom/battery.h
+++ b/drivers/power/supply/qcom/battery.h
@@ -13,6 +13,7 @@ struct charger_param {
u32 hvdcp2_max_icl_ua;
u32 hvdcp3_max_icl_ua;
u32 forced_main_fcc;
+ u32 qc4_max_icl_ua;
};
int qcom_batt_init(struct charger_param *param);
diff --git a/drivers/power/supply/qcom/qpnp-smb5.c b/drivers/power/supply/qcom/qpnp-smb5.c
index 103ca3a..5672c31 100644
--- a/drivers/power/supply/qcom/qpnp-smb5.c
+++ b/drivers/power/supply/qcom/qpnp-smb5.c
@@ -433,6 +433,7 @@ static int smb5_configure_internal_pull(struct smb_charger *chg, int type,
#define MICRO_P1A 100000
#define MICRO_1PA 1000000
#define MICRO_3PA 3000000
+#define MICRO_4PA 4000000
#define OTG_DEFAULT_DEGLITCH_TIME_MS 50
#define DEFAULT_WD_BARK_TIME 64
#define DEFAULT_WD_SNARL_TIME_8S 0x07
@@ -605,6 +606,12 @@ static int smb5_parse_dt_misc(struct smb5 *chip, struct device_node *node)
if (chg->chg_param.hvdcp2_max_icl_ua <= 0)
chg->chg_param.hvdcp2_max_icl_ua = MICRO_3PA;
+ /* Used only in Adapter CV mode of operation */
+ of_property_read_u32(node, "qcom,qc4-max-icl-ua",
+ &chg->chg_param.qc4_max_icl_ua);
+ if (chg->chg_param.qc4_max_icl_ua <= 0)
+ chg->chg_param.qc4_max_icl_ua = MICRO_4PA;
+
return 0;
}