From f00c512d79fa2c40da39aa55a0f5d38137e8f03e Mon Sep 17 00:00:00 2001 From: Joseph Coffland Date: Thu, 27 Jun 2019 15:13:44 -0700 Subject: [PATCH] Better shunting in power firmware --- src/pwr/config.h | 7 +++---- src/pwr/main.c | 42 +++++++++++++++++------------------------- 2 files changed, 20 insertions(+), 29 deletions(-) diff --git a/src/pwr/config.h b/src/pwr/config.h index 364e8d3..132f540 100644 --- a/src/pwr/config.h +++ b/src/pwr/config.h @@ -30,7 +30,7 @@ #include "pins.h" -#define VERSION 2 +#define VERSION 3 // Pins @@ -93,10 +93,9 @@ enum { #define SHUNT_WATTS 5 #define SHUNT_OHMS 5.1 #define SHUNT_PERIOD 65000 // ms -#define SHUNT_JOULES 50 // Power per shunt period +#define SHUNT_JOULES 25 // Power per shunt period #define SHUNT_JOULES_PER_MS ((float)SHUNT_JOULES / SHUNT_PERIOD) -#define SHUNT_MIN_V 1 -#define SHUNT_MAX_V 3 +#define SHUNT_MIN_V 2 #define VOLTAGE_REF 1.1 #define VOLTAGE_REF_R1 37400 diff --git a/src/pwr/main.c b/src/pwr/main.c index a326520..01160e7 100644 --- a/src/pwr/main.c +++ b/src/pwr/main.c @@ -144,28 +144,21 @@ static void update_shunt() { if (SHUNT_JOULES < joules) joules = SHUNT_JOULES; // Max if (joules < shunt_joules) shunt_overload = true; - else if (shunt_joules) { - joules -= shunt_joules; // Subtract power dissipated - IO_DDR_SET(SHUNT_PIN); // Enable - return; - } - - IO_DDR_CLR(SHUNT_PIN); // Disable + else joules -= shunt_joules; // Subtract power dissipated } static void update_shunt_power(float vout, float vnom) { if (vnom + SHUNT_MIN_V < vout) { - float duty = (vout - vnom - SHUNT_MIN_V) / SHUNT_MAX_V; - if (duty < 0) duty = 0; - if (1 < duty) duty = 1; - if (VOLTAGE_MAX <= vout) duty = 1; // Full shunt at max voltage - // Compute joules shunted this cycle: J = V^2 / RT - shunt_joules = duty * vout * vout / (SHUNT_OHMS * 1000.0); - OCR1A = 0xff * duty; + shunt_joules = vout * vout / (SHUNT_OHMS * 1000.0); + IO_DDR_SET(SHUNT_PIN); // Enable + IO_PORT_CLR(SHUNT_PIN); // Lo - } else shunt_joules = 0; + } else { + shunt_joules = 0; + IO_DDR_CLR(SHUNT_PIN); // Disable + } } @@ -242,7 +235,11 @@ static void read_conversion(uint8_t ch) { switch (ch) { case TEMP_ADC: regs[TEMP_REG] = data; break; // in Kelvin case VIN_ADC: regs[VIN_REG] = convert_voltage(data); break; - case VOUT_ADC: regs[VOUT_REG] = convert_voltage(data); break; + + case VOUT_ADC: + regs[VOUT_REG] = convert_voltage(data); + update_shunt_power(regs[VOUT_REG] / 100.0, vnom); + break; case CS1_ADC: { update_current(MOTOR_REG, data); @@ -344,10 +341,11 @@ void init() { (1 << ADC0D) | (1 << AREFD); DIDR1 = (1 << ADC5D); - // ADC internal 1.1v, enable, with interrupt, prescale 128 + // ADC internal 1.1v, enable, with interrupt, prescale 64 + // Note, a conversion takes ~200uS ADMUX = (1 << REFS1) | (0 << REFS0); ADCSRA = (1 << ADEN) | (1 << ADIE) | - (1 << ADPS2) | (1 << ADPS1) | (1 << ADPS0); + (1 << ADPS2) | (1 << ADPS1) | (0 << ADPS0); ADCSRB = 0; // Timer 0 (Fast PWM, clk/1) @@ -355,12 +353,6 @@ void init() { TCCR0B = (0 << WGM02) | (0 << CS02) | (0 << CS01) | (1 << CS00); TIMSK = 1 << TOIE0; // Enable overflow interrupt - // Timer 1 (Set output A on compare match, Fast PWM, 8-bit, no prescale) - OCR1A = 0; // Shunt off - TCCR1A = (1 << COM1A1) | (1 << COM1A0) | (0 << WGM11) | (1 << WGM10); - TCCR1B = - (0 << WGM13) | (1 << WGM12) | (0 << CS12) | (0 << CS11) | (1 << CS10); - // I2C, enable, enable address/stop interrupt TWSCRA = (1 << TWEN) | (1 << TWASIE) | (1 << TWDIE); TWSA = I2C_ADDR << 1; @@ -412,7 +404,7 @@ int main() { float vin = get_reg(VIN_REG); float vout = get_reg(VOUT_REG); - update_shunt_power(vout, vnom); + //update_shunt_power(vout, vnom); // Fatal conditions if (vin < VOLTAGE_MIN) fatal |= UNDER_VOLTAGE_FLAG; -- 2.27.0