Merge "qcom: smb-lib: force 9V for QC2.0 adapter"

This commit is contained in:
Linux Build Service Account 2017-03-08 15:47:22 -08:00 committed by Gerrit - the friendly Code Review server
commit 3e0acafdee
3 changed files with 81 additions and 10 deletions

View file

@ -239,7 +239,6 @@ static struct smb_params pm660_params = {
struct smb_dt_props {
int fcc_ua;
int usb_icl_ua;
int otg_cl_ua;
int dc_icl_ua;
int boost_threshold_ua;
int fv_uv;
@ -323,9 +322,9 @@ static int smb2_parse_dt(struct smb2 *chip)
chip->dt.usb_icl_ua = -EINVAL;
rc = of_property_read_u32(node,
"qcom,otg-cl-ua", &chip->dt.otg_cl_ua);
"qcom,otg-cl-ua", &chg->otg_cl_ua);
if (rc < 0)
chip->dt.otg_cl_ua = MICRO_1P5A;
chg->otg_cl_ua = MICRO_1P5A;
rc = of_property_read_u32(node,
"qcom,dc-icl-ua", &chip->dt.dc_icl_ua);
@ -1386,7 +1385,8 @@ static int smb2_init_hw(struct smb2 *chip)
/* set OTG current limit */
rc = smblib_set_charge_param(chg, &chg->param.otg_cl,
chip->dt.otg_cl_ua);
(chg->wa_flags & OTG_WA) ?
chg->param.otg_cl.min_u : chg->otg_cl_ua);
if (rc < 0) {
pr_err("Couldn't set otg current limit rc=%d\n", rc);
return rc;
@ -1649,7 +1649,7 @@ static int smb2_chg_config_init(struct smb2 *chip)
break;
case PM660_SUBTYPE:
chip->chg.smb_version = PM660_SUBTYPE;
chip->chg.wa_flags |= BOOST_BACK_WA;
chip->chg.wa_flags |= BOOST_BACK_WA | OTG_WA;
chg->param.freq_buck = pm660_params.freq_buck;
chg->param.freq_boost = pm660_params.freq_boost;
chg->chg_freq.freq_5V = 600;

View file

@ -1290,11 +1290,14 @@ int smblib_vconn_regulator_is_enabled(struct regulator_dev *rdev)
/*****************
* OTG REGULATOR *
*****************/
#define MAX_RETRY 15
#define MIN_DELAY_US 2000
#define MAX_DELAY_US 9000
static int _smblib_vbus_regulator_enable(struct regulator_dev *rdev)
{
struct smb_charger *chg = rdev_get_drvdata(rdev);
int rc;
int rc, retry_count = 0, min_delay = MIN_DELAY_US;
u8 stat;
smblib_dbg(chg, PR_OTG, "halt 1 in 8 mode\n");
rc = smblib_masked_write(chg, OTG_ENG_OTG_CFG_REG,
@ -1313,6 +1316,42 @@ static int _smblib_vbus_regulator_enable(struct regulator_dev *rdev)
return rc;
}
if (chg->wa_flags & OTG_WA) {
/* check for softstart */
do {
usleep_range(min_delay, min_delay + 100);
rc = smblib_read(chg, OTG_STATUS_REG, &stat);
if (rc < 0) {
smblib_err(chg,
"Couldn't read OTG status rc=%d\n",
rc);
goto out;
}
if (stat & BOOST_SOFTSTART_DONE_BIT) {
rc = smblib_set_charge_param(chg,
&chg->param.otg_cl, chg->otg_cl_ua);
if (rc < 0)
smblib_err(chg,
"Couldn't set otg limit\n");
break;
}
/* increase the delay for following iterations */
if (retry_count > 5)
min_delay = MAX_DELAY_US;
} while (retry_count++ < MAX_RETRY);
if (retry_count >= MAX_RETRY) {
smblib_dbg(chg, PR_OTG, "Boost Softstart not done\n");
goto out;
}
}
return 0;
out:
/* disable OTG if softstart failed */
smblib_write(chg, CMD_OTG_REG, 0);
return rc;
}
@ -1346,6 +1385,17 @@ static int _smblib_vbus_regulator_disable(struct regulator_dev *rdev)
smblib_err(chg, "Couldn't disable VCONN rc=%d\n", rc);
}
if (chg->wa_flags & OTG_WA) {
/* set OTG current limit to minimum value */
rc = smblib_set_charge_param(chg, &chg->param.otg_cl,
chg->param.otg_cl.min_u);
if (rc < 0) {
smblib_err(chg,
"Couldn't set otg current limit rc=%d\n", rc);
return rc;
}
}
smblib_dbg(chg, PR_OTG, "disabling OTG\n");
rc = smblib_write(chg, CMD_OTG_REG, 0);
if (rc < 0) {
@ -1354,7 +1404,6 @@ static int _smblib_vbus_regulator_disable(struct regulator_dev *rdev)
}
smblib_dbg(chg, PR_OTG, "start 1 in 8 mode\n");
rc = smblib_write(chg, CMD_OTG_REG, 0);
rc = smblib_masked_write(chg, OTG_ENG_OTG_CFG_REG,
ENG_BUCKBOOST_HALT1_8_MODE_BIT, 0);
if (rc < 0) {
@ -2955,6 +3004,14 @@ irqreturn_t smblib_handle_otg_overcurrent(int irq, void *data)
return IRQ_HANDLED;
}
if (chg->wa_flags & OTG_WA) {
if (stat & OTG_OC_DIS_SW_STS_RT_STS_BIT)
smblib_err(chg, "OTG disabled by hw\n");
/* not handling software based hiccups for PM660 */
return IRQ_HANDLED;
}
if (stat & OTG_OVERCURRENT_RT_STS_BIT)
schedule_work(&chg->otg_oc_work);
@ -3170,6 +3227,7 @@ irqreturn_t smblib_handle_icl_change(int irq, void *data)
|| (stat & AICL_DONE_BIT))
delay = 0;
cancel_delayed_work_sync(&chg->icl_change_work);
schedule_delayed_work(&chg->icl_change_work,
msecs_to_jiffies(delay));
}
@ -3279,11 +3337,22 @@ static void smblib_handle_hvdcp_3p0_auth_done(struct smb_charger *chg,
if (chg->mode == PARALLEL_MASTER)
vote(chg->pl_enable_votable_indirect, USBIN_V_VOTER, true, 0);
/* the APSD done handler will set the USB supply type */
apsd_result = smblib_get_apsd_result(chg);
if (get_effective_result(chg->hvdcp_hw_inov_dis_votable)) {
if (apsd_result->pst == POWER_SUPPLY_TYPE_USB_HVDCP) {
/* force HVDCP2 to 9V if INOV is disabled */
rc = smblib_masked_write(chg, CMD_HVDCP_2_REG,
FORCE_9V_BIT, FORCE_9V_BIT);
if (rc < 0)
smblib_err(chg,
"Couldn't force 9V HVDCP rc=%d\n", rc);
}
}
/* QC authentication done, parallel charger can be enabled now */
vote(chg->pl_disable_votable, PL_DELAY_HVDCP_VOTER, false, 0);
/* the APSD done handler will set the USB supply type */
apsd_result = smblib_get_apsd_result(chg);
smblib_dbg(chg, PR_INTERRUPT, "IRQ: hvdcp-3p0-auth-done rising; %s detected\n",
apsd_result->name);
}

View file

@ -80,6 +80,7 @@ enum {
BOOST_BACK_WA = BIT(1),
TYPEC_CC2_REMOVAL_WA_BIT = BIT(2),
QC_AUTH_INTERRUPT_WA_BIT = BIT(3),
OTG_WA = BIT(4),
};
enum smb_irq_index {
@ -305,6 +306,7 @@ struct smb_charger {
int otg_attempts;
int vconn_attempts;
int default_icl_ua;
int otg_cl_ua;
/* workaround flag */
u32 wa_flags;