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

Commit 1c25c498 authored by Yeleswarapu Nagaradhesh's avatar Yeleswarapu Nagaradhesh
Browse files

ASoC: wcd: maintain different thresholds for CS and MICBIAS



Program different button thresholds for current source
and MICBIAS for proper button detection.Also enable PULL_UP
for MICBIAS2 during playback for proper button detection.

CRs-Fixed: 691749
Change-Id: I6720e33d7c2882648bd2f465dc3abb9f68c24e05
Signed-off-by: default avatarYeleswarapu Nagaradhesh <nagaradh@codeaurora.org>
parent 07692d57
Loading
Loading
Loading
Loading
+7 −2
Original line number Original line Diff line number Diff line
@@ -2222,12 +2222,17 @@ static int msm8x16_wcd_hph_pa_event(struct snd_soc_dapm_widget *w,


	switch (event) {
	switch (event) {
	case SND_SOC_DAPM_PRE_PMU:
	case SND_SOC_DAPM_PRE_PMU:
		if (w->shift == 5)
		if (w->shift == 5) {
			snd_soc_update_bits(codec,
			snd_soc_update_bits(codec,
				MSM8X16_WCD_A_ANALOG_RX_HPH_L_TEST, 0x04, 0x04);
				MSM8X16_WCD_A_ANALOG_RX_HPH_L_TEST, 0x04, 0x04);
		else if (w->shift == 4)
			msm8x16_notifier_call(codec,
					WCD_EVENT_PRE_HPHL_PA_ON);
		} else if (w->shift == 4) {
			snd_soc_update_bits(codec,
			snd_soc_update_bits(codec,
				MSM8X16_WCD_A_ANALOG_RX_HPH_R_TEST, 0x04, 0x04);
				MSM8X16_WCD_A_ANALOG_RX_HPH_R_TEST, 0x04, 0x04);
			msm8x16_notifier_call(codec,
					WCD_EVENT_PRE_HPHR_PA_ON);
		}
		snd_soc_update_bits(codec,
		snd_soc_update_bits(codec,
				MSM8X16_WCD_A_ANALOG_NCP_FBCTRL, 0x20, 0x20);
				MSM8X16_WCD_A_ANALOG_NCP_FBCTRL, 0x20, 0x20);
		break;
		break;
+50 −28
Original line number Original line Diff line number Diff line
@@ -119,6 +119,39 @@ static void hphlocp_off_report(struct wcd_mbhc *mbhc, u32 jack_status)
			    mbhc->intr_ids->hph_left_ocp);
			    mbhc->intr_ids->hph_left_ocp);
}
}


static void wcd_program_btn_threshold(const struct wcd_mbhc *mbhc, bool micbias)
{
	struct wcd_mbhc_btn_detect_cfg *btn_det;
	struct snd_soc_codec *codec = mbhc->codec;
	struct snd_soc_card *card = codec->card;
	u16 i;
	u32 course, fine, reg_val;
	u16 reg_addr = MSM8X16_WCD_A_ANALOG_MBHC_BTN0_ZDETL_CTL;
	s16 *btn_voltage;

	if (mbhc->mbhc_cfg->calibration == NULL) {
		dev_err(card->dev, "%s: calibration data is NULL\n", __func__);
		return;
	}

	btn_det = WCD_MBHC_CAL_BTN_DET_PTR(mbhc->mbhc_cfg->calibration);

	if (micbias)
		btn_voltage = btn_det->_v_btn_high;
	else
		btn_voltage = btn_det->_v_btn_low;
	for (i = 0; i <  btn_det->num_btn; i++) {
		course = (btn_voltage[i] / 100);
		fine = ((btn_voltage[i] % 100) / 12);

		reg_val = (course << 5) | (fine << 2);
		snd_soc_update_bits(codec, reg_addr, 0xFC, reg_val);
		pr_err("%s: course: %d fine: %d reg_addr: %x reg_val: %x\n",
				__func__, course, fine, reg_addr, reg_val);
		reg_addr++;
	}
}

static int wcd_event_notify(struct notifier_block *self, unsigned long val,
static int wcd_event_notify(struct notifier_block *self, unsigned long val,
				void *data)
				void *data)
{
{
@@ -144,6 +177,8 @@ static int wcd_event_notify(struct notifier_block *self, unsigned long val,
				    MSM8X16_WCD_A_ANALOG_MBHC_FSM_CTL,
				    MSM8X16_WCD_A_ANALOG_MBHC_FSM_CTL,
				    0xB0, 0x80);
				    0xB0, 0x80);
		mbhc->is_hs_recording = true;
		mbhc->is_hs_recording = true;
		/* Program Button threshold registers */
		wcd_program_btn_threshold(mbhc, true);
		break;
		break;
	/* MICBIAS usage change */
	/* MICBIAS usage change */
	case WCD_EVENT_PRE_MICBIAS_2_OFF:
	case WCD_EVENT_PRE_MICBIAS_2_OFF:
@@ -157,14 +192,28 @@ static int wcd_event_notify(struct notifier_block *self, unsigned long val,
				    MSM8X16_WCD_A_ANALOG_MBHC_FSM_CTL,
				    MSM8X16_WCD_A_ANALOG_MBHC_FSM_CTL,
				    0xB0, 0xB0);
				    0xB0, 0xB0);
		mbhc->is_hs_recording = false;
		mbhc->is_hs_recording = false;
		/* Program Button threshold registers */
		wcd_program_btn_threshold(mbhc, false);
		break;
		break;
	case WCD_EVENT_POST_HPHL_PA_OFF:
	case WCD_EVENT_POST_HPHL_PA_OFF:
		if (mbhc->hph_status & SND_JACK_OC_HPHL)
		if (mbhc->hph_status & SND_JACK_OC_HPHL)
			hphlocp_off_report(mbhc, SND_JACK_OC_HPHL);
			hphlocp_off_report(mbhc, SND_JACK_OC_HPHL);
		snd_soc_update_bits(codec,
				MSM8X16_WCD_A_ANALOG_MICB_2_EN,
				0x40, 0x0);
		break;
		break;
	case WCD_EVENT_POST_HPHR_PA_OFF:
	case WCD_EVENT_POST_HPHR_PA_OFF:
		if (mbhc->hph_status & SND_JACK_OC_HPHR)
		if (mbhc->hph_status & SND_JACK_OC_HPHR)
			hphrocp_off_report(mbhc, SND_JACK_OC_HPHR);
			hphrocp_off_report(mbhc, SND_JACK_OC_HPHR);
		snd_soc_update_bits(codec,
				MSM8X16_WCD_A_ANALOG_MICB_2_EN,
				0x40, 0x00);
		break;
	case WCD_EVENT_PRE_HPHL_PA_ON:
	case WCD_EVENT_PRE_HPHR_PA_ON:
		snd_soc_update_bits(codec,
				MSM8X16_WCD_A_ANALOG_MICB_2_EN,
				0x40, 0x40);
		break;
		break;
	default:
	default:
		break;
		break;
@@ -186,33 +235,6 @@ static int wcd_cancel_btn_work(struct wcd_mbhc *mbhc)
	return r;
	return r;
}
}


static void wcd_program_btn_threshold(const struct wcd_mbhc *mbhc)
{
	struct wcd_mbhc_btn_detect_cfg *btn_det;
	struct snd_soc_codec *codec = mbhc->codec;
	struct snd_soc_card *card = codec->card;
	u16 i;
	u32 course, fine, reg_val;
	u16 reg_addr = MSM8X16_WCD_A_ANALOG_MBHC_BTN0_ZDETL_CTL;

	if (mbhc->mbhc_cfg->calibration == NULL) {
		dev_err(card->dev, "%s: calibration data is NULL\n", __func__);
		return;
	}

	btn_det = WCD_MBHC_CAL_BTN_DET_PTR(mbhc->mbhc_cfg->calibration);

	for (i = 0; i <  btn_det->num_btn; i++) {
		course = (btn_det->_v_btn_high[i] / 100);
		fine = ((btn_det->_v_btn_high[i] % 100) / 12);
		reg_val = (course << 5) | (fine << 2);
		snd_soc_update_bits(codec, reg_addr, 0xFC, reg_val);
		pr_debug("%s: course: %d fine: %d reg_addr: %x reg_val: %x\n",
				__func__, course, fine, reg_addr, reg_val);
		reg_addr++;
	}
}

static bool wcd_swch_level_remove(struct wcd_mbhc *mbhc)
static bool wcd_swch_level_remove(struct wcd_mbhc *mbhc)
{
{
	u16 result2;
	u16 result2;
@@ -1604,7 +1626,7 @@ static int wcd_mbhc_initialise(struct wcd_mbhc *mbhc)
			MSM8X16_WCD_A_DIGITAL_CDC_DIG_CLK_CTL,
			MSM8X16_WCD_A_DIGITAL_CDC_DIG_CLK_CTL,
			0x08, 0x08);
			0x08, 0x08);
	/* Program Button threshold registers */
	/* Program Button threshold registers */
	wcd_program_btn_threshold(mbhc);
	wcd_program_btn_threshold(mbhc, false);


	INIT_WORK(&mbhc->correct_plug_swch, wcd_correct_swch_plug);
	INIT_WORK(&mbhc->correct_plug_swch, wcd_correct_swch_plug);
	/* enable the WCD MBHC IRQ's */
	/* enable the WCD MBHC IRQ's */
+11 −5
Original line number Original line Diff line number Diff line
@@ -1057,15 +1057,21 @@ static void *def_msm8x16_wcd_mbhc_cal(void)
	btn_low = btn_cfg->_v_btn_low;
	btn_low = btn_cfg->_v_btn_low;
	btn_high = btn_cfg->_v_btn_high;
	btn_high = btn_cfg->_v_btn_high;


	btn_low[0] = 0;
	/*
	 * In SW we are maintaining two sets of threshold register
	 * one for current source and another for Micbias.
	 * all btn_low corresponds to threshold for current source
	 * all bt_high corresponds to threshold for Micbias
	 */
	btn_low[0] = 25;
	btn_high[0] = 25;
	btn_high[0] = 25;
	btn_low[1] = 25;
	btn_low[1] = 50;
	btn_high[1] = 50;
	btn_high[1] = 50;
	btn_low[2] = 50;
	btn_low[2] = 75;
	btn_high[2] = 75;
	btn_high[2] = 75;
	btn_low[3] = 75;
	btn_low[3] = 112;
	btn_high[3] = 112;
	btn_high[3] = 112;
	btn_low[4] = 112;
	btn_low[4] = 137;
	btn_high[4] = 137;
	btn_high[4] = 137;


	return msm8x16_wcd_cal;
	return msm8x16_wcd_cal;