Loading drivers/input/misc/qcom-hv-haptics.c +54 −7 Original line number Diff line number Diff line Loading @@ -8,6 +8,7 @@ #include <linux/device.h> #include <linux/err.h> #include <linux/fs.h> #include <linux/hrtimer.h> #include <linux/init.h> #include <linux/input.h> #include <linux/interrupt.h> Loading Loading @@ -511,6 +512,7 @@ struct haptics_chip { struct device_node *pbs_node; struct class hap_class; struct regulator *hpwr_vreg; struct hrtimer hbst_off_timer; int fifo_empty_irq; u32 hpwr_voltage_mv; u32 effects_count; Loading @@ -529,6 +531,7 @@ struct haptics_chip { bool clamp_at_5v; bool hpwr_vreg_enabled; bool is_hv_haptics; bool hboost_enabled; }; struct haptics_reg_info { Loading Loading @@ -1292,6 +1295,9 @@ static int haptics_boost_vreg_enable(struct haptics_chip *chip, bool en) return 0; } if (chip->hboost_enabled == en) return 0; val = en ? HAP_VREG_ON_VAL : HAP_VREG_OFF_VAL; rc = nvmem_device_write(chip->hap_cfg_nvmem, PBS_ARG_REG, 1, &val); Loading @@ -1304,13 +1310,16 @@ static int haptics_boost_vreg_enable(struct haptics_chip *chip, bool en) val = PBS_TRIG_SET_VAL; rc = nvmem_device_write(chip->hap_cfg_nvmem, PBS_TRIG_SET_REG, 1, &val); if (rc < 0) if (rc < 0) { dev_err(chip->dev, "Write SDAM %#x failed, rc=%d\n", PBS_TRIG_SET_REG, rc); return rc; } chip->hboost_enabled = en; return 0; } static bool is_swr_play_enabled(struct haptics_chip *chip) { int rc; Loading Loading @@ -1357,6 +1366,14 @@ static int haptics_wait_hboost_ready(struct haptics_chip *chip) if (is_haptics_external_powered(chip)) return 0; if ((hrtimer_get_remaining(&chip->hbst_off_timer) > 0) || hrtimer_active(&chip->hbst_off_timer)) { hrtimer_cancel(&chip->hbst_off_timer); dev_dbg(chip->dev, "hboost is still on, ignore\n"); return 0; } /* * Wait ~20ms until hBoost is ready, otherwise * bail out and return -EBUSY Loading Loading @@ -1493,6 +1510,7 @@ static int haptics_open_loop_drive_config(struct haptics_chip *chip, bool en) return rc; } #define BOOST_VREG_OFF_DELAY_SECONDS 2 static int haptics_enable_play(struct haptics_chip *chip, bool en) { struct haptics_play_info *play = &chip->play; Loading Loading @@ -1526,11 +1544,17 @@ static int haptics_enable_play(struct haptics_chip *chip, bool en) return rc; } if (play->pattern_src == FIFO) { rc = haptics_boost_vreg_enable(chip, en); if (rc < 0) dev_err(chip->dev, "Notify vreg %s failed, rc=%d\n", en ? "enabling" : "disabling", rc); if (en) { rc = haptics_boost_vreg_enable(chip, true); if (rc < 0) { dev_err(chip->dev, "Keep boost vreg on failed, rc=%d\n", rc); return rc; } } else { hrtimer_start(&chip->hbst_off_timer, ktime_set(BOOST_VREG_OFF_DELAY_SECONDS, 0), HRTIMER_MODE_REL); } return rc; Loading Loading @@ -4582,6 +4606,21 @@ static bool is_swr_supported(struct haptics_chip *chip) return true; } static enum hrtimer_restart haptics_disable_hbst_timer(struct hrtimer *timer) { struct haptics_chip *chip = container_of(timer, struct haptics_chip, hbst_off_timer); int rc; rc = haptics_boost_vreg_enable(chip, false); if (rc < 0) dev_err(chip->dev, "disable boost vreg failed, rc=%d\n", rc); else dev_dbg(chip->dev, "boost vreg is disabled\n"); return HRTIMER_NORESTART; } static int haptics_probe(struct platform_device *pdev) { struct haptics_chip *chip; Loading Loading @@ -4646,6 +4685,8 @@ static int haptics_probe(struct platform_device *pdev) mutex_init(&chip->play.lock); disable_irq_nosync(chip->fifo_empty_irq); chip->fifo_empty_irq_en = false; hrtimer_init(&chip->hbst_off_timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); chip->hbst_off_timer.function = haptics_disable_hbst_timer; atomic_set(&chip->play.fifo_status.is_busy, 0); atomic_set(&chip->play.fifo_status.written_done, 0); Loading Loading @@ -4755,6 +4796,12 @@ static int haptics_suspend(struct device *dev) } mutex_unlock(&play->lock); /* * Cancel the hBoost turning off timer and disable * hBoost if it's still enabled */ hrtimer_cancel(&chip->hbst_off_timer); haptics_boost_vreg_enable(chip, false); rc = haptics_enable_hpwr_vreg(chip, false); if (rc < 0) return rc; Loading Loading
drivers/input/misc/qcom-hv-haptics.c +54 −7 Original line number Diff line number Diff line Loading @@ -8,6 +8,7 @@ #include <linux/device.h> #include <linux/err.h> #include <linux/fs.h> #include <linux/hrtimer.h> #include <linux/init.h> #include <linux/input.h> #include <linux/interrupt.h> Loading Loading @@ -511,6 +512,7 @@ struct haptics_chip { struct device_node *pbs_node; struct class hap_class; struct regulator *hpwr_vreg; struct hrtimer hbst_off_timer; int fifo_empty_irq; u32 hpwr_voltage_mv; u32 effects_count; Loading @@ -529,6 +531,7 @@ struct haptics_chip { bool clamp_at_5v; bool hpwr_vreg_enabled; bool is_hv_haptics; bool hboost_enabled; }; struct haptics_reg_info { Loading Loading @@ -1292,6 +1295,9 @@ static int haptics_boost_vreg_enable(struct haptics_chip *chip, bool en) return 0; } if (chip->hboost_enabled == en) return 0; val = en ? HAP_VREG_ON_VAL : HAP_VREG_OFF_VAL; rc = nvmem_device_write(chip->hap_cfg_nvmem, PBS_ARG_REG, 1, &val); Loading @@ -1304,13 +1310,16 @@ static int haptics_boost_vreg_enable(struct haptics_chip *chip, bool en) val = PBS_TRIG_SET_VAL; rc = nvmem_device_write(chip->hap_cfg_nvmem, PBS_TRIG_SET_REG, 1, &val); if (rc < 0) if (rc < 0) { dev_err(chip->dev, "Write SDAM %#x failed, rc=%d\n", PBS_TRIG_SET_REG, rc); return rc; } chip->hboost_enabled = en; return 0; } static bool is_swr_play_enabled(struct haptics_chip *chip) { int rc; Loading Loading @@ -1357,6 +1366,14 @@ static int haptics_wait_hboost_ready(struct haptics_chip *chip) if (is_haptics_external_powered(chip)) return 0; if ((hrtimer_get_remaining(&chip->hbst_off_timer) > 0) || hrtimer_active(&chip->hbst_off_timer)) { hrtimer_cancel(&chip->hbst_off_timer); dev_dbg(chip->dev, "hboost is still on, ignore\n"); return 0; } /* * Wait ~20ms until hBoost is ready, otherwise * bail out and return -EBUSY Loading Loading @@ -1493,6 +1510,7 @@ static int haptics_open_loop_drive_config(struct haptics_chip *chip, bool en) return rc; } #define BOOST_VREG_OFF_DELAY_SECONDS 2 static int haptics_enable_play(struct haptics_chip *chip, bool en) { struct haptics_play_info *play = &chip->play; Loading Loading @@ -1526,11 +1544,17 @@ static int haptics_enable_play(struct haptics_chip *chip, bool en) return rc; } if (play->pattern_src == FIFO) { rc = haptics_boost_vreg_enable(chip, en); if (rc < 0) dev_err(chip->dev, "Notify vreg %s failed, rc=%d\n", en ? "enabling" : "disabling", rc); if (en) { rc = haptics_boost_vreg_enable(chip, true); if (rc < 0) { dev_err(chip->dev, "Keep boost vreg on failed, rc=%d\n", rc); return rc; } } else { hrtimer_start(&chip->hbst_off_timer, ktime_set(BOOST_VREG_OFF_DELAY_SECONDS, 0), HRTIMER_MODE_REL); } return rc; Loading Loading @@ -4582,6 +4606,21 @@ static bool is_swr_supported(struct haptics_chip *chip) return true; } static enum hrtimer_restart haptics_disable_hbst_timer(struct hrtimer *timer) { struct haptics_chip *chip = container_of(timer, struct haptics_chip, hbst_off_timer); int rc; rc = haptics_boost_vreg_enable(chip, false); if (rc < 0) dev_err(chip->dev, "disable boost vreg failed, rc=%d\n", rc); else dev_dbg(chip->dev, "boost vreg is disabled\n"); return HRTIMER_NORESTART; } static int haptics_probe(struct platform_device *pdev) { struct haptics_chip *chip; Loading Loading @@ -4646,6 +4685,8 @@ static int haptics_probe(struct platform_device *pdev) mutex_init(&chip->play.lock); disable_irq_nosync(chip->fifo_empty_irq); chip->fifo_empty_irq_en = false; hrtimer_init(&chip->hbst_off_timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); chip->hbst_off_timer.function = haptics_disable_hbst_timer; atomic_set(&chip->play.fifo_status.is_busy, 0); atomic_set(&chip->play.fifo_status.written_done, 0); Loading Loading @@ -4755,6 +4796,12 @@ static int haptics_suspend(struct device *dev) } mutex_unlock(&play->lock); /* * Cancel the hBoost turning off timer and disable * hBoost if it's still enabled */ hrtimer_cancel(&chip->hbst_off_timer); haptics_boost_vreg_enable(chip, false); rc = haptics_enable_hpwr_vreg(chip, false); if (rc < 0) return rc; Loading