/** * ti_bandgap_get_sensor_data() - helper function to get thermal * framework related data. * @bgp: pointer to bandgap instance * @id: sensor id * * Return: data stored by set function with sensor id on success or NULL */ void *ti_bandgap_get_sensor_data(struct ti_bandgap *bgp, int id) { int ret = ti_bandgap_validate(bgp, id); if (ret) return ERR_PTR(ret); return bgp->regval[id].data; }
/** * ti_bandgap_set_sensor_data() - helper function to store thermal * framework related data. * @bgp: pointer to bandgap instance * @id: sensor id * @data: thermal framework related data to be stored * * Return: 0 on success or the proper error code */ int ti_bandgap_set_sensor_data(struct ti_bandgap *bgp, int id, void *data) { int ret = ti_bandgap_validate(bgp, id); if (ret) return ret; bgp->regval[id].data = data; return 0; }
/** * ti_bandgap_get_trend() - To fetch the temperature trend of a sensor * @bgp: pointer to struct ti_bandgap * @id: id of the individual sensor * @trend: Pointer to trend. * * This function needs to be called to fetch the temperature trend of a * Particular sensor. The function computes the difference in temperature * w.r.t time. For the bandgaps with built in history buffer the temperatures * are read from the buffer and for those without the Buffer -ENOTSUPP is * returned. * * Return: 0 if no error, else return corresponding error. If no * error then the trend value is passed on to trend parameter */ int ti_bandgap_get_trend(struct ti_bandgap *bgp, int id, int *trend) { struct temp_sensor_registers *tsr; u32 temp1, temp2, reg1, reg2; int t1, t2, interval, ret = 0; ret = ti_bandgap_validate(bgp, id); if (ret) goto exit; if (!TI_BANDGAP_HAS(bgp, HISTORY_BUFFER) || !TI_BANDGAP_HAS(bgp, FREEZE_BIT)) { ret = -ENOTSUPP; goto exit; } tsr = bgp->conf->sensors[id].registers; /* Freeze and read the last 2 valid readings */ reg1 = tsr->ctrl_dtemp_1; reg2 = tsr->ctrl_dtemp_2; /* read temperature from history buffer */ temp1 = ti_bandgap_readl(bgp, reg1); temp1 &= tsr->bgap_dtemp_mask; temp2 = ti_bandgap_readl(bgp, reg2); temp2 &= tsr->bgap_dtemp_mask; /* Convert from adc values to mCelsius temperature */ ret = ti_bandgap_adc_to_mcelsius(bgp, temp1, &t1); if (ret) goto exit; ret = ti_bandgap_adc_to_mcelsius(bgp, temp2, &t2); if (ret) goto exit; /* Fetch the update interval */ ret = ti_bandgap_read_update_interval(bgp, id, &interval); if (ret || !interval) goto exit; *trend = (t1 - t2) / interval; dev_dbg(bgp->dev, "The temperatures are t1 = %d and t2 = %d and trend =%d\n", t1, t2, *trend); exit: return ret; }
/** * _ti_bandgap_write_threshold() - helper to update TALERT t_cold or t_hot * @bgp: struct ti_bandgap pointer * @id: bandgap sensor id * @val: value (mCelsius) of a new threshold * @hot: desired threshold to be updated. true if threshold hot, false if * threshold cold * * It will update the required thresholds (hot and cold) for TALERT signal. * This function can be used to update t_hot or t_cold, depending on @hot value. * Validates the mCelsius range and update the requested threshold. * Call this function only if bandgap features HAS(TALERT). * * Return: 0 if no error, else corresponding error value. */ static int _ti_bandgap_write_threshold(struct ti_bandgap *bgp, int id, int val, bool hot) { struct temp_sensor_data *ts_data; struct temp_sensor_registers *tsr; u32 adc_val; int ret; ret = ti_bandgap_validate(bgp, id); if (ret) goto exit; if (!TI_BANDGAP_HAS(bgp, TALERT)) { ret = -ENOTSUPP; goto exit; } ts_data = bgp->conf->sensors[id].ts_data; tsr = bgp->conf->sensors[id].registers; if (hot) { if (val < ts_data->min_temp + ts_data->hyst_val) ret = -EINVAL; } else { if (val > ts_data->max_temp + ts_data->hyst_val) ret = -EINVAL; } if (ret) goto exit; ret = ti_bandgap_mcelsius_to_adc(bgp, val, &adc_val); if (ret < 0) goto exit; spin_lock(&bgp->lock); ret = ti_bandgap_update_alert_threshold(bgp, id, adc_val, hot); spin_unlock(&bgp->lock); exit: return ret; }
/** * ti_bandgap_read_temperature() - report current temperature * @bgp: pointer to bandgap instance * @id: sensor id * @temperature: resulting temperature * * Return: 0 on success or the proper error code */ int ti_bandgap_read_temperature(struct ti_bandgap *bgp, int id, int *temperature) { u32 temp; int ret; ret = ti_bandgap_validate(bgp, id); if (ret) return ret; spin_lock(&bgp->lock); temp = ti_bandgap_read_temp(bgp, id); spin_unlock(&bgp->lock); ret |= ti_bandgap_adc_to_mcelsius(bgp, temp, &temp); if (ret) return -EIO; *temperature = temp; return 0; }
/** * ti_bandgap_write_update_interval() - set the update interval * @bgp: pointer to bandgap instance * @id: sensor id * @interval: desired update interval in miliseconds * * Return: 0 on success or the proper error code */ int ti_bandgap_write_update_interval(struct ti_bandgap *bgp, int id, u32 interval) { int ret = ti_bandgap_validate(bgp, id); if (ret) goto exit; if (!TI_BANDGAP_HAS(bgp, COUNTER) && !TI_BANDGAP_HAS(bgp, COUNTER_DELAY)) { ret = -ENOTSUPP; goto exit; } if (TI_BANDGAP_HAS(bgp, COUNTER)) { ti_bandgap_write_counter(bgp, id, interval); goto exit; } ret = ti_bandgap_write_counter_delay(bgp, id, interval); exit: return ret; }
/** * _ti_bandgap_read_threshold() - helper to read TALERT t_cold or t_hot * @bgp: struct ti_bandgap pointer * @id: bandgap sensor id * @val: value (mCelsius) of a threshold * @hot: desired threshold to be read. true if threshold hot, false if * threshold cold * * It will fetch the required thresholds (hot and cold) for TALERT signal. * This function can be used to read t_hot or t_cold, depending on @hot value. * Call this function only if bandgap features HAS(TALERT). * * Return: 0 if no error, -ENOTSUPP if it has no TALERT support, or the * corresponding error value if some operation fails. */ static int _ti_bandgap_read_threshold(struct ti_bandgap *bgp, int id, int *val, bool hot) { struct temp_sensor_registers *tsr; u32 temp, mask; int ret = 0; ret = ti_bandgap_validate(bgp, id); if (ret) goto exit; if (!TI_BANDGAP_HAS(bgp, TALERT)) { ret = -ENOTSUPP; goto exit; } tsr = bgp->conf->sensors[id].registers; if (hot) mask = tsr->threshold_thot_mask; else mask = tsr->threshold_tcold_mask; temp = ti_bandgap_readl(bgp, tsr->bgap_threshold); temp = (temp & mask) >> __ffs(mask); ret |= ti_bandgap_adc_to_mcelsius(bgp, temp, &temp); if (ret) { dev_err(bgp->dev, "failed to read thot\n"); ret = -EIO; goto exit; } *val = temp; exit: return ret; }