diff --git a/include/probe.h b/include/probe.h index 34871f0..96df621 100644 --- a/include/probe.h +++ b/include/probe.h @@ -16,9 +16,6 @@ void probe_mode_switch(uint8_t mode); void probe_measure(); -void probe_set_thresh(uint8_t set); -uint8_t probe_get_thresh(); - #endif /* _INC_PROBE_H */ \ No newline at end of file diff --git a/src/flash.c b/src/flash.c index 11faf82..373b3d4 100644 --- a/src/flash.c +++ b/src/flash.c @@ -174,6 +174,7 @@ __attribute__ ((long_call, section(".ramfunc"))) void flash_erase_page(uint32_t // enable EOPIE (per DS, EOP isn't set unless EOPIE is set) // and signal that we want to erase a page + FLASH->SR = FLASH_SR_EOP; FLASH->CR |= FLASH_CR_EOPIE | FLASH_CR_PER; // disable interrupts @@ -186,15 +187,13 @@ __attribute__ ((long_call, section(".ramfunc"))) void flash_erase_page(uint32_t // ensure flash is not busy, then wait for end of programming while (FLASH->SR & FLASH_SR_BSY); while (!(FLASH->SR & FLASH_SR_EOP)); - - // re-enable interrupts - __set_PRIMASK(primask); - - // clear EOP FLASH->SR |= FLASH_SR_EOP; - // and re-lock flash + // re-lock flash FLASH->CR = FLASH_CR_LOCK; + + // re-enable interrupts + __set_PRIMASK(primask); } /* @@ -209,7 +208,7 @@ __attribute__ ((long_call, section(".ramfunc"))) void flash_write_page(uint32_t uint8_t i; uint32_t *src; - volatile uint32_t *dst; + uint32_t *dst; // ensure flash is not busy while (FLASH->SR & FLASH_SR_BSY); @@ -221,6 +220,7 @@ __attribute__ ((long_call, section(".ramfunc"))) void flash_write_page(uint32_t // enable EOPIE (per DS, EOP isn't set unless EOPIE is set) // and signal that we want to write a page + FLASH->SR = FLASH_SR_EOP; FLASH->CR |= FLASH_CR_EOPIE | FLASH_CR_PG; // disable interrupts @@ -229,28 +229,25 @@ __attribute__ ((long_call, section(".ramfunc"))) void flash_write_page(uint32_t // write data to flash src = data; - dst = (volatile uint32_t *)addr; - for (i = 0; i < (FLASH_PAGE_SIZE / 4); i++) { - // on the last page, enable the page write start bit to commit to flash - if (i == (FLASH_PAGE_SIZE / 4) - 1) { - FLASH->CR |= FLASH_CR_PGSTRT; - } - + dst = (uint32_t *)addr; + for (i = 0; i < (FLASH_PAGE_SIZE / 4) - 1; i++) { *dst++ = *src++; } + // for the last word, enable the PGSTRT bit then write the word to commit to flash + FLASH->CR |= FLASH_CR_PGSTRT; + *dst = *src; + // ensure flash is not busy, then wait for end of programming while (FLASH->SR & FLASH_SR_BSY); while (!(FLASH->SR & FLASH_SR_EOP)); - - // re-enable interrupts - __set_PRIMASK(primask); - - // clear EOP FLASH->SR |= FLASH_SR_EOP; - // and re-lock flash + // re-lock flash FLASH->CR = FLASH_CR_LOCK; + + // re-enable interrupts + __set_PRIMASK(primask); } /* @@ -262,7 +259,7 @@ void flash_commit_conf() uint32_t i; uint8_t flash_idx = 0; - uint8_t flash_full; + uint8_t flash_full = 0; struct UConf *fconf; uint32_t *f32, *u32; @@ -280,7 +277,6 @@ void flash_commit_conf() // if all pages are occupied, erase the first page if (i == UCONF_COUNT) { flash_full = 1; - flash_erase_page(UCONF_FLASH_START); } // copy flash page from ROM to the write buffer, @@ -310,6 +306,12 @@ void flash_commit_conf() *u32++ = *f32++; } + // erase this page + flash_erase_page(UCONF_FLASH_START + (UCONF_SIZE * flash_idx)); + + // commit to flash + flash_write_page(UCONF_FLASH_START + (UCONF_SIZE * flash_idx), write); + // if flash was full, erase other pages if (flash_full) { for (i = (UCONF_FLASH_START + FLASH_PAGE_SIZE); i < FLASH_END; i += FLASH_PAGE_SIZE) { diff --git a/src/probe.c b/src/probe.c index d63b87f..862554a 100644 --- a/src/probe.c +++ b/src/probe.c @@ -16,56 +16,49 @@ #include "adc.h" #include "led.h" +#include "rgbprog.h" #include "userio.h" - - -#define CONT_OPEN 1240 +#include "flash.h" // diode measurements at 3V3 -#define DIODE_OPEN 3860 // test unit measures ~4060 no D1, ~3960 with D1 -#define DIODE_SCHOTTKY 1960 // vishay 40V 1A SB140 -#define DIODE_STANDARD 2330 // fairchild 5V2 zener, forward biased -#define DIODE_LED_BLUE 3190 -#define DIODE_LED_GRN 3040 // very dim -#define DIODE_LED_RED 3020 -#define DIODE_SHORT 1900 // test unit measures ~1820 +#define DIODE_OPEN 3860 // test unit measures ~4060 no D1, ~3960 with D1 +#define DIODE_SCHOTTKY 1960 // vishay 40V 1A SB140 +#define DIODE_STANDARD 2330 // fairchild 5V2 zener, forward biased +#define DIODE_LED_BLUE 3190 +#define DIODE_LED_GRN 3040 // very dim +#define DIODE_LED_RED 3020 +#define DIODE_SHORT 1900 // test unit measures ~1820 -#define CONT_SHORTED 858 // worst case measured value of short -#define CONT_47OHM 869 // measured value of 47ohm 1% resistor at room temp -#define CONT_100OHM 886 // measured value of 100ohm 1% resistor at room temp -#define CONT_EXTRA_COUNTS 8 // extra raw counts as a fudge factor, post-scaling -#define CONT_LATCH_THRESH 15 // extra raw counts for latching indicator, post-scaling +// continuity offsets from calibrated short value +#define CONT_47OHM 16 +#define CONT_100OHM 34 -#define CONT_LATCH_TIMEOUT 4 // probe measurement passes to hold latched indicator +#define CONT_EXTRA_COUNTS 3 // extra raw counts as a fudge factor + +#define CONT_CAL_THRESHOLD 890 // typical short is ~845-860 region + +#define CONT_LATCH_THRESHOLD 5 // extra raw counts for latching indicator +#define CONT_LATCH_TIMEOUT 4 // probe measurement passes to hold latched indicator static uint16_t vref; -static uint16_t cont_thresh_set = 0; -static const uint16_t cont_thresh[] = { +static uint8_t cont_cal_timer; +static uint16_t cont_cal_low; +static uint16_t cont_cal_avg; +static const uint16_t cont_thresh_tbl[] = { CONT_100OHM, CONT_47OHM }; static uint8_t latch = 0; -static uint8_t buzzer = 0; -void probe_set_thresh(uint8_t set) -{ - cont_thresh_set = set; -} - -uint8_t probe_get_thresh() -{ - return cont_thresh_set; -} - static inline void probe_measure_cont() { uint16_t probe, v_ext; @@ -75,57 +68,105 @@ static inline void probe_measure_cont() probe = adc_avg[ADC_PROBE]; v_ext = adc_avg[ADC_VREF_EXT]; - // if the button has been pushed, toggle the buzzer - if (userio_get_btn() > 0) { - buzzer ^= 1; - } + // update vref + if (!vref) vref = v_ext; + vref += v_ext; + vref >>= 1; // if the button has been held, change the threshold if (userio_get_btn_held() == 60) { userio_set_btn_override(); - cont_thresh_set ^= 1; + conf.cont_sensitivity ^= 1; } - // this LED will not set anything, + // if the button has _really_ been held, clear the calibration + if (userio_get_btn_held() == 600) { + conf.cont_shorted = 0; + } + + // if there is no calibration, try to perform it + if (!conf.cont_shorted) { + // until this is performed, show error LEDs + rgbprog_error_flasher(5, 0, 0, 100); + + // initialize + if (!cont_cal_timer) { + cont_cal_low = 0xfff; + cont_cal_avg = 0; + } + + // if probe appears to be shorted, calibrate to lowest value read + if (adc_avg[ADC_PROBE] < CONT_CAL_THRESHOLD) { + // low value + if (adc_avg[ADC_PROBE] < cont_cal_low) { + cont_cal_low = adc_avg[ADC_PROBE]; + } + // average value + if (!cont_cal_avg) { + cont_cal_avg = adc_avg[ADC_PROBE]; + } else { + cont_cal_avg += adc_avg[ADC_PROBE]; + cont_cal_avg >>= 1; + } + cont_cal_timer++; + } else { + cont_cal_timer = 0; + } + + // after held long enough, commit + if (cont_cal_timer == 180) { + cont_cal_timer = 0; + conf.cont_shorted = (cont_cal_avg + cont_cal_low) >> 1; + flash_commit_conf(); + } + } + + // right LED remains unused while buzzer is being used, // but zero it out anyway led_setrgb(1, 0, 0, 0); + + // if no calibration yet, bail here + if (!conf.cont_shorted) return; + + // if the button has been pushed, toggle buzzer on/off + if (userio_get_btn() > 0) { + conf.cont_buzzer ^= 1; + } if (vref) { + // note: we don't use VREF anymore... + // it's too noisy :/ + // probe level - x = probe << 12; // maximum possible level - x /= vref; // normalize to 4096max - if (x > 4095) x = 4095; + x = probe - conf.cont_shorted; + if (x > 0xfff) x = 0; // threshold level - c = cont_thresh[cont_thresh_set] << 12; - c /= vref; + c = cont_thresh_tbl[conf.cont_sensitivity]; - // are we measuring a lower value? + // are we measuring a lower ohm value on the probes than our threshold? if (x < (c + CONT_EXTRA_COUNTS)) { // roughly 100ohm or lower latch = CONT_LATCH_TIMEOUT; // latch any continuity for a while } - b = buzzer ? 100 : 0; + // blue led to indicate buzzer is enabled + b = conf.cont_buzzer ? 20 : 0; if (latch) { // hysteresis - if (x >= c + CONT_LATCH_THRESH) latch--; + if (x >= (c + CONT_LATCH_THRESHOLD)) latch--; // indicate continuity led_setrgb(0, 0, 250, b); led_buzz(0); - if (buzzer) led_buzz(1); + if (conf.cont_buzzer) led_buzz(1); } else { // idle - g = cont_thresh_set ? 40 : 0; + g = conf.cont_sensitivity ? 40 : 0; led_setrgb(0, 120, g, b); led_buzz(0); } } - - if (!vref) vref = v_ext; - vref += v_ext; - vref >>= 1; } static inline void probe_measure_diode()