diff options
| -rw-r--r-- | Documentation/devicetree/bindings/power/supply/qcom/qpnp-smb2.txt | 6 | ||||
| -rw-r--r-- | drivers/power/supply/qcom/qpnp-smb2.c | 11 | ||||
| -rw-r--r-- | drivers/power/supply/qcom/smb-lib.c | 52 | ||||
| -rw-r--r-- | drivers/power/supply/qcom/smb-lib.h | 3 |
4 files changed, 49 insertions, 23 deletions
diff --git a/Documentation/devicetree/bindings/power/supply/qcom/qpnp-smb2.txt b/Documentation/devicetree/bindings/power/supply/qcom/qpnp-smb2.txt index 894c34553a22..b41219d51973 100644 --- a/Documentation/devicetree/bindings/power/supply/qcom/qpnp-smb2.txt +++ b/Documentation/devicetree/bindings/power/supply/qcom/qpnp-smb2.txt @@ -181,6 +181,12 @@ Charger specific properties: Definition: Specifies the maximum charger buck/boost switching frequency in KHz. It overrides the max frequency defined for the charger. +- qcom,otg-deglitch-time-ms + Usage: optional + Value type: <u32> + Definition: Specifies the deglitch interval for OTG detection. + If the value is not present, 50 msec is used as default. + ============================================= Second Level Nodes - SMB2 Charger Peripherals ============================================= diff --git a/drivers/power/supply/qcom/qpnp-smb2.c b/drivers/power/supply/qcom/qpnp-smb2.c index 94b9e9c4d912..b2597987292b 100644 --- a/drivers/power/supply/qcom/qpnp-smb2.c +++ b/drivers/power/supply/qcom/qpnp-smb2.c @@ -266,8 +266,9 @@ module_param_named( debug_mask, __debug_mask, int, S_IRUSR | S_IWUSR ); -#define MICRO_1P5A 1500000 -#define MICRO_P1A 100000 +#define MICRO_1P5A 1500000 +#define MICRO_P1A 100000 +#define OTG_DEFAULT_DEGLITCH_TIME_MS 50 static int smb2_parse_dt(struct smb2 *chip) { struct smb_charger *chg = &chip->chg; @@ -400,6 +401,12 @@ static int smb2_parse_dt(struct smb2 *chip) chg->suspend_input_on_debug_batt = of_property_read_bool(node, "qcom,suspend-input-on-debug-batt"); + + rc = of_property_read_u32(node, "qcom,otg-deglitch-time-ms", + &chg->otg_delay_ms); + if (rc < 0) + chg->otg_delay_ms = OTG_DEFAULT_DEGLITCH_TIME_MS; + return 0; } diff --git a/drivers/power/supply/qcom/smb-lib.c b/drivers/power/supply/qcom/smb-lib.c index a191391a3904..cc50e0f478d1 100644 --- a/drivers/power/supply/qcom/smb-lib.c +++ b/drivers/power/supply/qcom/smb-lib.c @@ -3750,26 +3750,6 @@ static void smblib_handle_typec_debounce_done(struct smb_charger *chg, smblib_typec_mode_name[pval.intval]); } -irqreturn_t smblib_handle_usb_typec_change_for_uusb(struct smb_charger *chg) -{ - int rc; - u8 stat; - - rc = smblib_read(chg, TYPE_C_STATUS_3_REG, &stat); - if (rc < 0) { - smblib_err(chg, "Couldn't read TYPE_C_STATUS_3 rc=%d\n", rc); - return IRQ_HANDLED; - } - smblib_dbg(chg, PR_REGISTER, "TYPE_C_STATUS_3 = 0x%02x OTG=%d\n", - stat, !!(stat & (U_USB_GND_NOVBUS_BIT | U_USB_GND_BIT))); - - extcon_set_cable_state_(chg->extcon, EXTCON_USB_HOST, - !!(stat & (U_USB_GND_NOVBUS_BIT | U_USB_GND_BIT))); - power_supply_changed(chg->usb_psy); - - return IRQ_HANDLED; -} - static void smblib_usb_typec_change(struct smb_charger *chg) { int rc; @@ -3804,7 +3784,11 @@ irqreturn_t smblib_handle_usb_typec_change(int irq, void *data) struct smb_charger *chg = irq_data->parent_data; if (chg->micro_usb_mode) { - smblib_handle_usb_typec_change_for_uusb(chg); + cancel_delayed_work_sync(&chg->uusb_otg_work); + vote(chg->awake_votable, OTG_DELAY_VOTER, true, 0); + smblib_dbg(chg, PR_INTERRUPT, "Scheduling OTG work\n"); + schedule_delayed_work(&chg->uusb_otg_work, + msecs_to_jiffies(chg->otg_delay_ms)); return IRQ_HANDLED; } @@ -3889,6 +3873,30 @@ irqreturn_t smblib_handle_wdog_bark(int irq, void *data) /*************** * Work Queues * ***************/ +static void smblib_uusb_otg_work(struct work_struct *work) +{ + struct smb_charger *chg = container_of(work, struct smb_charger, + uusb_otg_work.work); + int rc; + u8 stat; + bool otg; + + rc = smblib_read(chg, TYPE_C_STATUS_3_REG, &stat); + if (rc < 0) { + smblib_err(chg, "Couldn't read TYPE_C_STATUS_3 rc=%d\n", rc); + goto out; + } + + otg = !!(stat & (U_USB_GND_NOVBUS_BIT | U_USB_GND_BIT)); + extcon_set_cable_state_(chg->extcon, EXTCON_USB_HOST, otg); + smblib_dbg(chg, PR_REGISTER, "TYPE_C_STATUS_3 = 0x%02x OTG=%d\n", + stat, otg); + power_supply_changed(chg->usb_psy); + +out: + vote(chg->awake_votable, OTG_DELAY_VOTER, false, 0); +} + static void smblib_hvdcp_detect_work(struct work_struct *work) { @@ -4482,6 +4490,7 @@ int smblib_init(struct smb_charger *chg) INIT_DELAYED_WORK(&chg->icl_change_work, smblib_icl_change_work); INIT_DELAYED_WORK(&chg->pl_enable_work, smblib_pl_enable_work); INIT_WORK(&chg->legacy_detection_work, smblib_legacy_detection_work); + INIT_DELAYED_WORK(&chg->uusb_otg_work, smblib_uusb_otg_work); chg->fake_capacity = -EINVAL; chg->fake_input_current_limited = -EINVAL; @@ -4536,6 +4545,7 @@ int smblib_deinit(struct smb_charger *chg) cancel_delayed_work_sync(&chg->icl_change_work); cancel_delayed_work_sync(&chg->pl_enable_work); cancel_work_sync(&chg->legacy_detection_work); + cancel_delayed_work_sync(&chg->uusb_otg_work); power_supply_unreg_notifier(&chg->nb); smblib_destroy_votables(chg); qcom_batt_deinit(); diff --git a/drivers/power/supply/qcom/smb-lib.h b/drivers/power/supply/qcom/smb-lib.h index 5dc60ecb9436..3fedff8897ee 100644 --- a/drivers/power/supply/qcom/smb-lib.h +++ b/drivers/power/supply/qcom/smb-lib.h @@ -64,6 +64,7 @@ enum print_reason { #define CC2_WA_VOTER "CC2_WA_VOTER" #define QNOVO_VOTER "QNOVO_VOTER" #define BATT_PROFILE_VOTER "BATT_PROFILE_VOTER" +#define OTG_DELAY_VOTER "OTG_DELAY_VOTER" #define VCONN_MAX_ATTEMPTS 3 #define OTG_MAX_ATTEMPTS 3 @@ -230,6 +231,7 @@ struct smb_charger { bool external_vconn; struct smb_chg_freq chg_freq; int smb_version; + int otg_delay_ms; /* locks */ struct mutex lock; @@ -290,6 +292,7 @@ struct smb_charger { struct delayed_work icl_change_work; struct delayed_work pl_enable_work; struct work_struct legacy_detection_work; + struct delayed_work uusb_otg_work; /* cached status */ int voltage_min_uv; |
