aboutsummaryrefslogtreecommitdiff
path: root/fsm/adc.c
diff options
context:
space:
mode:
Diffstat (limited to 'fsm/adc.c')
-rw-r--r--fsm/adc.c31
1 files changed, 29 insertions, 2 deletions
diff --git a/fsm/adc.c b/fsm/adc.c
index 13a76b6..73e282d 100644
--- a/fsm/adc.c
+++ b/fsm/adc.c
@@ -30,6 +30,7 @@ void adc_voltage_mode() {
}
+#if 0
#ifdef USE_VOLTAGE_DIVIDER
static inline uint8_t calc_voltage_divider(uint16_t value) {
// use 9.7 fixed-point to get sufficient precision
@@ -44,6 +45,7 @@ static inline uint8_t calc_voltage_divider(uint16_t value) {
return result;
}
#endif
+#endif
// Each full cycle runs ~2X per second with just voltage enabled,
// or ~1X per second with voltage and temperature.
@@ -67,7 +69,6 @@ ISR(ADC_vect) {
// update the latest value
#ifdef MCU_ADC_RESULT_PER_TYPE
- // thermal, convert ADC reading to left-aligned Kelvin
if (channel) m = mcu_adc_result_temp();
else m = mcu_adc_result_volts();
#else
@@ -208,6 +209,19 @@ static inline void ADC_voltage_handler() {
#endif
else measurement = adc_smooth[0];
+ // convert raw ADC value to FSM voltage units: (V * 100) << 6
+ // 0 .. 65535 = 0.0V .. 10.24V
+ measurement = voltage_raw2cooked(measurement) / (10 << 5);
+
+ // calculate actual voltage: volts * 10
+ // TODO: should be (volts * 40) for extra precision
+ voltage = (measurement + VOLTAGE_FUDGE_FACTOR
+ #ifdef USE_VOLTAGE_CORRECTION
+ + VOLT_CORR - 7
+ #endif
+ ) >> 1;
+
+ #if 0
// values stair-step between intervals of 64, with random variations
// of 1 or 2 in either direction, so if we chop off the last 6 bits
// it'll flap between N and N-1... but if we add half an interval,
@@ -231,6 +245,7 @@ static inline void ADC_voltage_handler() {
#endif
) >> 1;
#endif
+ #endif
// if low, callback EV_voltage_low / EV_voltage_critical
// (but only if it has been more than N seconds since last call)
@@ -290,8 +305,14 @@ static inline void ADC_temperature_handler() {
}
// latest 16-bit ADC reading
- uint16_t measurement = adc_smooth[1];
+ // convert raw ADC value to Kelvin << 6
+ // 0 .. 65535 = 0 K .. 1024 K
+ uint16_t measurement = temp_raw2cooked(adc_smooth[1]);
+ // (Kelvin << 6) to Celsius
+ temperature = (measurement>>6) + THERM_CAL_OFFSET + (int16_t)TH_CAL - 275;
+
+ #if 0
// values stair-step between intervals of 64, with random variations
// of 1 or 2 in either direction, so if we chop off the last 6 bits
// it'll flap between N and N-1... but if we add half an interval,
@@ -313,6 +334,12 @@ static inline void ADC_temperature_handler() {
// external sensor
temperature = EXTERN_TEMP_FORMULA(measurement>>1) + THERM_CAL_OFFSET + (int16_t)TH_CAL;
#endif
+ #endif
+
+ // instead of (K << 6), use (K << 1) now
+ // TODO: use more precision, if it can be done without overflow in 16 bits
+ // (and still work on attiny85 without increasing ROM size)
+ measurement = measurement >> 5;
// how much has the temperature changed between now and a few seconds ago?
int16_t diff;