]> git.donarmstrong.com Git - tmk_firmware.git/blobdiff - keyboard/hhkb_rn42/rn42/rn42_task.c
Monitor battery and alert low voltage
[tmk_firmware.git] / keyboard / hhkb_rn42 / rn42 / rn42_task.c
index 2813b1c5ff4490c1666ae305cb74f98b4d6a36a1..30914452e530296afcac18e7c45c3da5b2eb7b25 100644 (file)
@@ -9,6 +9,7 @@
 #include "print.h"
 #include "timer.h"
 #include "command.h"
+#include "battery.h"
 
 static bool config_mode = false;
 static bool force_usb = false;
@@ -24,65 +25,9 @@ static void status_led(bool on)
     }
 }
 
-static void battery_adc_init(void)
-{
-    ADMUX = (1<<REFS1) | (1<<REFS0);                // Ref:2.56V band-gap, Input:ADC0(PF0)
-    ADCSRA = (1<<ADPS2) | (1<<ADPS1) | (1<<ADPS0);  // Prescale:128 16MHz/128=125KHz
-    ADCSRA |= (1<<ADEN);                            // enable ADC
-}
-
-static uint16_t battery_adc(void)
-{
-    volatile uint16_t bat;
-    ADCSRA |= (1<<ADEN);
-
-    // discard first result
-    ADCSRA |= (1<<ADSC);
-    while (ADCSRA & (1<<ADSC)) ;
-    bat = ADC;
-
-    // discard second result
-    ADCSRA |= (1<<ADSC);
-    while (ADCSRA & (1<<ADSC)) ;
-    bat = ADC;
-
-    ADCSRA |= (1<<ADSC);
-    while (ADCSRA & (1<<ADSC)) ;
-    bat = ADC;
-
-    ADCSRA &= ~(1<<ADEN);
-    return bat;
-}
-
-static void battery_led(bool on)
-{
-    if (on) {
-        DDRF  |=  (1<<5);
-        PORTF &= ~(1<<5);   // Low
-    } else {
-        DDRF  &= ~(1<<5);
-        PORTF &= ~(1<<5);   // HiZ
-    }
-}
-
-static bool battery_charging(void)
-{
-    // MCP73831:STAT
-    //   Hi-Z:   Shutdown/No Battery
-    //   Low:    Charging
-    //   Hi:     Charged
-    DDRF  &= ~(1<<5);
-    PORTF |=  (1<<5);
-    return PINF&(1<<5) ? false : true;
-}
-
 void rn42_task_init(void)
 {
-    battery_adc_init();
-
-    // battery charging(HiZ)
-    DDRF  &= ~(1<<5);
-    PORTF &= ~(1<<5);
+    battery_init();
 }
 
 void rn42_task(void)
@@ -136,7 +81,49 @@ void rn42_task(void)
         }
     }
 
-    /* Battery monitor */
+
+    static uint16_t prev_timer = 0;
+    static uint8_t sec = 0;
+    // NOTE: not exact 1 sec
+    if (timer_elapsed(prev_timer) > 1000) {
+        /* every second */
+        prev_timer = timer_read();
+
+        /* Low voltage alert */
+        uint8_t bs = battery_status();
+        if (bs == LOW_VOLTAGE) {
+            battery_led(LED_ON);
+        } else {
+            battery_led(LED_CHARGER);
+        }
+
+        static uint8_t prev_status = UNKNOWN;
+        if (bs != prev_status) {
+            prev_status = bs;
+            switch (bs) {
+                case FULL_CHARGED:  xprintf("FULL_CHARGED\n"); break;
+                case CHARGING:      xprintf("CHARGING\n"); break;
+                case DISCHARGING:   xprintf("DISCHARGING\n"); break;
+                case LOW_VOLTAGE:   xprintf("LOW_VOLTAGE\n"); break;
+                default:            xprintf("UNKNOWN STATUS\n"); break;
+            };
+        }
+
+        /* every minute */
+        if (sec == 0) {
+            uint32_t t = timer_read32()/1000;
+            uint16_t v = battery_voltage();
+            uint8_t h = t/3600;
+            uint8_t m = t%3600/60;
+            uint8_t s = t%60;
+            xprintf("%02u:%02u:%02u\t%umV\n", h, m, s, v);
+            /* TODO: xprintf doesn't work for this.
+            xprintf("%02u:%02u:%02u\t%umV\n", (t/3600), (t%3600/60), (t%60), v);
+            */
+        }
+        sec++; sec = sec%60;
+    }
+
 
     /* Connection monitor */
     if (rn42_linked()) {
@@ -214,12 +201,13 @@ bool command_extra(uint8_t code)
             xprintf("config_mode: %X\n", config_mode);
             xprintf("VBUS: %X\n", USBSTA&(1<<VBUS));
             xprintf("battery_charging: %X\n", battery_charging());
+            xprintf("battery_status: %X\n", battery_status());
             return true;
         case KC_B:
             // battery monitor
             t = timer_read32()/1000;
-            b = battery_adc();
-            xprintf("BAT: %umV(%04X)\t",  (b-16)*5, b);
+            b = battery_voltage();
+            xprintf("BAT: %umV\t", b);
             xprintf("%02u:",   t/3600);
             xprintf("%02u:",   t%3600/60);
             xprintf("%02u\n",  t%60);