diff --git a/drivers/iio/adc/qcom-spmi-adc5.c b/drivers/iio/adc/qcom-spmi-adc5.c index 30c1003d0cbe..0fa010a58c63 100644 --- a/drivers/iio/adc/qcom-spmi-adc5.c +++ b/drivers/iio/adc/qcom-spmi-adc5.c @@ -616,6 +616,8 @@ static const struct adc5_channels adc7_chans_pmic[ADC5_MAX_CHANNEL] = { SCALE_HW_CALIB_DEFAULT) [ADC7_VBAT_SNS] = ADC5_CHAN_VOLT("vbat_sns", 3, SCALE_HW_CALIB_DEFAULT) + [ADC7_AMUX_THM3] = ADC5_CHAN_TEMP("smb_temp", 0, + SCALE_HW_CALIB_PM7_SMB_TEMP) [ADC7_DIE_TEMP] = ADC5_CHAN_TEMP("die_temp", 0, SCALE_HW_CALIB_PMIC_THERM_PM7) [ADC7_AMUX_THM1_100K_PU] = ADC5_CHAN_TEMP("amux_thm1_pu2", 0, diff --git a/drivers/iio/adc/qcom-vadc-common.c b/drivers/iio/adc/qcom-vadc-common.c index 8901c385a24b..e604a2695c34 100644 --- a/drivers/iio/adc/qcom-vadc-common.c +++ b/drivers/iio/adc/qcom-vadc-common.c @@ -560,6 +560,10 @@ static int qcom_vadc_scale_hw_smb_temp( const struct u32_fract *prescale, const struct adc5_data *data, u16 adc_code, int *result_mdec); +static int qcom_vadc_scale_hw_pm7_smb_temp( + const struct u32_fract *prescale, + const struct adc5_data *data, + u16 adc_code, int *result_mdec); static int qcom_vadc_scale_hw_smb1398_temp( const struct u32_fract *prescale, const struct adc5_data *data, @@ -595,6 +599,7 @@ static struct qcom_adc5_scale_type scale_adc5_fn[] = { [SCALE_HW_CALIB_PM5_CHG_TEMP] = {qcom_vadc_scale_hw_chg5_temp}, [SCALE_HW_CALIB_PM5_SMB_TEMP] = {qcom_vadc_scale_hw_smb_temp}, [SCALE_HW_CALIB_PM5_SMB1398_TEMP] = {qcom_vadc_scale_hw_smb1398_temp}, + [SCALE_HW_CALIB_PM7_SMB_TEMP] = {qcom_vadc_scale_hw_pm7_smb_temp}, }; static int qcom_vadc_map_voltage_temp(const struct vadc_map_pt *pts, @@ -912,6 +917,27 @@ static int qcom_vadc7_scale_hw_calib_die_temp( voltage, result_mdec); } +static int qcom_vadc_scale_hw_pm7_smb_temp( + const struct u32_fract *prescale, + const struct adc5_data *data, + u16 adc_code, int *result_mdec) +{ + s64 temp; + int result_uv; + + result_uv = qcom_vadc_scale_code_voltage_factor(adc_code, + prescale, data, 1); + + /* T(C) = 25 + (25*Vadc - 24.885) / 0.0894 */ + temp = div_s64(((25000LL * result_uv) - (24885 * 1000000LL)) * 10000, + 894 * 1000000) + 25000; + pr_debug("adc_code: %#x result_uv: %d temp: %lld\n", adc_code, + result_uv, temp); + *result_mdec = temp > 0 ? temp : 0; + + return 0; +} + static int qcom_vadc_scale_hw_smb_temp( const struct u32_fract *prescale, const struct adc5_data *data, diff --git a/include/linux/iio/adc/qcom-vadc-common.h b/include/linux/iio/adc/qcom-vadc-common.h index ba6eaa113e22..59cd0fe9a0ea 100644 --- a/include/linux/iio/adc/qcom-vadc-common.h +++ b/include/linux/iio/adc/qcom-vadc-common.h @@ -118,6 +118,8 @@ struct vadc_linear_graph { * code. * SCALE_HW_CALIB_PM5_SMB1398_TEMP: Returns result in millidegrees for PMIC5 * SMB1398 temperature. + * SCALE_HW_CALIB_PM7_SMB_TEMP: Returns result in millidegrees for PMIC7 + * SMB139x temperature. */ enum vadc_scale_fn_type { SCALE_DEFAULT = 0, @@ -128,16 +130,16 @@ enum vadc_scale_fn_type { SCALE_HW_CALIB_DEFAULT, SCALE_HW_CALIB_THERM_100K_PULLUP, SCALE_HW_CALIB_XOTHERM, + SCALE_HW_CALIB_THERM_100K_PU_PM7, SCALE_HW_CALIB_PMIC_THERM, - SCALE_HW_CALIB_CUR, + SCALE_HW_CALIB_PMIC_THERM_PM7, SCALE_HW_CALIB_PM5_CHG_TEMP, SCALE_HW_CALIB_PM5_SMB_TEMP, SCALE_HW_CALIB_BATT_THERM_100K, SCALE_HW_CALIB_BATT_THERM_30K, SCALE_HW_CALIB_BATT_THERM_400K, SCALE_HW_CALIB_PM5_SMB1398_TEMP, - SCALE_HW_CALIB_THERM_100K_PU_PM7, - SCALE_HW_CALIB_PMIC_THERM_PM7, + SCALE_HW_CALIB_PM7_SMB_TEMP, SCALE_HW_CALIB_INVALID, };