From 1ee4d3bd9057dce6b0750de8f0f3af575d8c1560 Mon Sep 17 00:00:00 2001 From: Jan Michel Date: Fri, 7 Feb 2020 10:26:35 +0100 Subject: [PATCH] add better startup and calibration. Manual calibration is available to compensate for offsets after relays switched on --- atmega32u4/power48/main.c | 54 +++++++++++++++++++++++++++------------ 1 file changed, 37 insertions(+), 17 deletions(-) diff --git a/atmega32u4/power48/main.c b/atmega32u4/power48/main.c index 73c90ce..047007b 100644 --- a/atmega32u4/power48/main.c +++ b/atmega32u4/power48/main.c @@ -7,7 +7,7 @@ #include #include -#define FIRMWARE_VERSION 0x011 +#define FIRMWARE_VERSION 0x012 //Channels 0 1 2 3: PD4, PB6, PF6, PF1 @@ -23,6 +23,8 @@ //Scc? -- read channel status - 2nd char: 'e' in case of overcurrent, 3rd char: enable 1/0 //Ccc? -- read current //Dcc? -- read averaged current +//Ecc? -- read raw ADC value +//Bcc? -- read ADC channel offset //Lccxxx -- set current limit (hex) //Lcc? -- read current limit //Axxx -- answer - three hex digits or chars @@ -30,6 +32,7 @@ //Pcc(0|1) -- Do a automatic power cycle (2 seconds long) //Rcc? -- read ADC measurement of internal 1.1V reference (one register) //Icc? -- Firmware Info +//F001 -- Force another calibration with relais #define ISMYADDR() (rxbuf[1] == '0' && (rxbuf[2] == '0' || rxbuf[2] == '1' || rxbuf[2] == '2' || rxbuf[2] == '3') ) @@ -44,8 +47,10 @@ uint8_t output_enable = 0x3; uint8_t output_error = 0; uint8_t adc_enable = 1; uint8_t calibphase = 1; +uint8_t forcecalib = 0; uint16_t adc_offset[4] = {0,0,0,0}; uint16_t adc[4]; +uint16_t raw[4]; uint16_t avgadc[4] = {0,0,0,0}; uint8_t countdown[4] = {0,0,0,0}; uint16_t adc_reference = 0; @@ -141,7 +146,7 @@ void switchoutput(uint8_t chan, int8_t to) { if(to >= -1) {settings_changed |= 16;} - if((output_enable & (1<< chan))) { // && !(output_error & (1<< chan)) + if((output_enable & (1<< chan)) ) { // && !(output_error & (1<< chan)) switch (chan) { case 0 : PORTD |= (1<<4); break; case 1 : PORTB |= (1<<6); break; @@ -173,13 +178,17 @@ void correct_adc(uint8_t channel) { } if (adc[channel] > 0x300) adc[channel] = 0; - if(adc_offset[channel] > adc[channel] ) { + if(adc_offset[channel]+0x30 > adc[channel] ) { adc[channel] = adc_offset[channel] - adc[channel]; adc[channel] *= 25; } else { adc[channel] = 0; } + if(channel == 3 && forcecalib == 1) { + calibphase = 1; + forcecalib = 0; + } } @@ -224,9 +233,12 @@ ISR(ADC_vect) { case 2: case 3: adc[channel] = ADC; + raw[channel] = adc[channel]; correct_adc(channel); avgadc[channel] -= avgadc[channel]/8; - avgadc[channel] += adc[channel]; + if(adc[channel] < 0x800) { + avgadc[channel] += adc[channel]; + } if(limit[channel]*8