From: Jan "Yenya" Kasprzak Date: Fri, 10 May 2013 21:52:55 +0000 (+0200) Subject: Deeper sleep when idle X-Git-Url: https://www.fi.muni.cz/~kas/git//home/kas/public_html/git/?p=tinyboard.git;a=commitdiff_plain;h=ccfee4572d781e2007f36ac30f1c80a7ef43e9ef Deeper sleep when idle --- diff --git a/projects/step-up/adc.c b/projects/step-up/adc.c index ea30935..55cd861 100644 --- a/projects/step-up/adc.c +++ b/projects/step-up/adc.c @@ -10,8 +10,9 @@ //#define NUM_ADCS ZERO_ADC #define NUM_ADCS 2 -volatile static unsigned char current_adc;; -volatile unsigned char need_battery_adc; +volatile static unsigned char current_adc; +volatile unsigned char adc_enabled; +volatile unsigned char need_battery_adc, need_pwmled_adc; static uint16_t adc_sum, read_zero, drop_count, read_count, n_reads_log; volatile uint16_t jiffies; @@ -40,13 +41,23 @@ void start_next_adc() drop_count = 1; read_count = 1; n_reads_log = 0; - } else { + } else if (need_pwmled_adc) { current_adc = 0; read_zero = 0; drop_count = 1; read_count = 1 << PWMLED_ADC_SHIFT; n_reads_log = PWMLED_ADC_SHIFT; + } else { + ADCSRA &= ~_BV(ADEN); + power_adc_disable(); + adc_enabled = 0; + return; + } + if (!adc_enabled) { + power_adc_enable(); + ADCSRA |= _BV(ADEN); + adc_enabled = 1; } adc_sum = 0; @@ -95,7 +106,9 @@ static uint16_t read_adc_sync() void init_adc() { need_battery_adc = 0; + need_pwmled_adc = 0; current_adc = 0; + adc_enabled = 1; power_adc_enable(); ACSR |= _BV(ACD); // but disable the analog comparator @@ -124,6 +137,8 @@ void susp_adc() { ADCSRA = 0; DIDR0 = 0; + power_adc_disable(); + adc_enabled = 0; } ISR(ADC_vect) { // IRQ handler diff --git a/projects/step-up/battery.c b/projects/step-up/battery.c index ceb53cb..0e51cb1 100644 --- a/projects/step-up/battery.c +++ b/projects/step-up/battery.c @@ -77,8 +77,10 @@ unsigned char battery_gauge() rv = 7; } +#if 0 if (rv == 1 && !initial_readings) set_error(ERR_BATTERY); +#endif #if 0 log_byte(0xbb); diff --git a/projects/step-up/lights.h b/projects/step-up/lights.h index 2980cd3..4a0b6b9 100644 --- a/projects/step-up/lights.h +++ b/projects/step-up/lights.h @@ -21,13 +21,14 @@ void inline log_word(uint16_t word) { } /* adc.c */ #define PWMLED_ADC_SHIFT 1 /* 1<<1 measurements per single callback */ extern volatile unsigned char need_battery_adc; -extern volatile unsigned char adc_running; +extern volatile unsigned char need_pwmled_adc; +extern volatile unsigned char adc_enabled; void init_adc(); void susp_adc(); /* pwm.c */ #define PWM_MAX 0xFF -extern volatile unsigned char pwm_running; +extern volatile unsigned char pwm_enabled; void init_pwm(); void susp_pwm(); void pwm_off(); diff --git a/projects/step-up/main.c b/projects/step-up/main.c index c1ee381..25d80df 100644 --- a/projects/step-up/main.c +++ b/projects/step-up/main.c @@ -72,13 +72,15 @@ int main(void) #if 1 while (1) { cli(); - if (pwm_running) { + if (pwm_enabled) { set_sleep_mode(SLEEP_MODE_IDLE); - } else if (adc_running) { + } else if (adc_enabled) { set_sleep_mode(SLEEP_MODE_ADC); } else { set_sleep_mode(SLEEP_MODE_PWR_DOWN); } + + sleep_enable(); // keep BOD active, no sleep_bod_disable(); sei(); sleep_cpu(); diff --git a/projects/step-up/pwm.c b/projects/step-up/pwm.c index 42ed777..b93a4fa 100644 --- a/projects/step-up/pwm.c +++ b/projects/step-up/pwm.c @@ -11,7 +11,7 @@ * Counts from 0 to 0xFF, without OCR1C compare. */ -static unsigned char pwm_enabled; +volatile unsigned char pwm_enabled; static void inline enable_pll() { @@ -57,6 +57,7 @@ void pwm_off() DDRB &= ~_BV(PB4); PLLCSR &= ~(_BV(PLLE) | _BV(PCKE)); + power_timer1_disable(); pwm_enabled = 0; } @@ -65,6 +66,7 @@ void pwm_set(uint8_t stride) OCR1B = stride; if (!pwm_enabled) { + power_timer1_enable(); enable_pll(); DDRB |= _BV(PB4); pwm_enabled = 1; diff --git a/projects/step-up/pwmled.c b/projects/step-up/pwmled.c index bc604da..485d024 100644 --- a/projects/step-up/pwmled.c +++ b/projects/step-up/pwmled.c @@ -60,9 +60,11 @@ void pwmled_on_off(unsigned char mode) if (mode) { state = ST_ON; mode_changed = 1; + need_pwmled_adc = 1; pwm_set(pwm_val); } else { state = ST_OFF; + need_pwmled_adc = 0; pwm_off(); } } @@ -113,6 +115,7 @@ void pwmled_adc(uint16_t adcval) if (pwm_val >= PWM_MAX || (pwm_val > (2*PWM_MAX/3) && adcval < 0x08)) { pwmled_err(); + need_pwmled_adc = 0; return; } diff --git a/projects/step-up/wdt.c b/projects/step-up/wdt.c index 15bfbbb..cb94ec8 100644 --- a/projects/step-up/wdt.c +++ b/projects/step-up/wdt.c @@ -17,10 +17,16 @@ void susp_wdt() ISR(WDT_vect) { ++jiffies; + if (pwm_enabled) { + need_pwmled_adc = 1; + } + if (jiffies & 0x000F) { need_battery_adc = 1; // about every 1s } patterns_next_tick(); timer_check_buttons(); + if (!adc_enabled) + start_next_adc(); // only if not running }