altos: Check for full log and complain
[fw/altos] / src / ao_report.c
index 8885ea4e8b13f8196a7132247e6e47ec3c9b2cac..cc8b512b095ca0af903620e9d7802fd32e3905ca 100644 (file)
 
 #include "ao.h"
 
-static const char * __xdata flight_reports[] = {
-       "...",          /* startup, 'S' */
-       "..",           /* idle 'I' */
-       ".--.",         /* pad 'P' */
-       "-...",         /* boost 'B' */
-       "..-.",         /* fast 'F' */
-       ".-",           /* apogee 'A' */
-       "-..",          /* drogue 'D' */
-       "--",           /* main 'M' */
-       ".-..",         /* landed 'L' */
-       ".-.-.-",       /* invalid */
+#define BIT(i,x)          ((x) ? (1 << (i)) : 0)
+#define MORSE1(a)          (1 | BIT(3,a))
+#define MORSE2(a,b)        (2 | BIT(3,a) | BIT(4,b))
+#define MORSE3(a,b,c)      (3 | BIT(3,a) | BIT(4,b) | BIT(5,c))
+#define MORSE4(a,b,c,d)    (4 | BIT(3,a) | BIT(4,b) | BIT(5,c) | BIT(6,d))
+#define MORSE5(a,b,c,d,e)  (5 | BIT(3,a) | BIT(4,b) | BIT(5,c) | BIT(6,d) | BIT(7,e))
+
+static const uint8_t flight_reports[] = {
+       MORSE3(0,0,0),          /* startup, 'S' */
+       MORSE2(0,0),            /* idle 'I' */
+       MORSE4(0,1,1,0),        /* pad 'P' */
+       MORSE4(1,0,0,0),        /* boost 'B' */
+       MORSE4(0,0,1,0),        /* fast 'F' */
+       MORSE4(1,0,1,0),        /* coast 'C' */
+       MORSE3(1,0,0),          /* drogue 'D' */
+       MORSE2(1,1),            /* main 'M' */
+       MORSE4(0,1,0,0),        /* landed 'L' */
+       MORSE4(1,0,0,1),        /* invalid 'X' */
 };
 
 #if 1
@@ -42,17 +49,18 @@ static __xdata enum ao_flight_state ao_report_state;
 static void
 ao_report_beep(void) __reentrant
 {
-       char *r = flight_reports[ao_flight_state];
-       char c;
+       uint8_t r = flight_reports[ao_flight_state];
+       uint8_t l = r & 7;
 
        if (!r)
                return;
-       while (c = *r++) {
-               if (c == '.')
-                       signal(AO_MS_TO_TICKS(200));
-               else
+       while (l--) {
+               if (r & 8)
                        signal(AO_MS_TO_TICKS(600));
+               else
+                       signal(AO_MS_TO_TICKS(200));
                pause(AO_MS_TO_TICKS(200));
+               r >>= 1;
        }
        pause(AO_MS_TO_TICKS(400));
 }
@@ -97,6 +105,44 @@ ao_report_altitude(void)
        }
 }
 
+static uint8_t
+ao_report_igniter_ready(enum ao_igniter igniter)
+{
+       return ao_igniter_status(igniter) == ao_igniter_ready ? 1 : 0;
+}
+
+static void
+ao_report_continuity(void) __reentrant
+{
+       uint8_t c = (ao_report_igniter_ready(ao_igniter_drogue) |
+                    (ao_report_igniter_ready(ao_igniter_main) << 1));
+       if (c) {
+               while (c--) {
+                       ao_beep_for(AO_BEEP_HIGH, AO_MS_TO_TICKS(25));
+                       pause(AO_MS_TO_TICKS(100));
+               }
+       } else {
+               c = 10;
+               while (c--) {
+                       ao_beep_for(AO_BEEP_HIGH, AO_MS_TO_TICKS(20));
+                       ao_beep_for(AO_BEEP_LOW, AO_MS_TO_TICKS(20));
+               }
+       }
+       if (ao_log_full()) {
+               pause(AO_MS_TO_TICKS(100));
+               c = 2;
+               while (c--) {
+                       ao_beep_for(AO_BEEP_LOW, AO_MS_TO_TICKS(100));
+                       ao_beep_for(AO_BEEP_MID, AO_MS_TO_TICKS(100));
+                       ao_beep_for(AO_BEEP_HIGH, AO_MS_TO_TICKS(100));
+                       ao_beep_for(AO_BEEP_MID, AO_MS_TO_TICKS(100));
+               }
+       }
+       c = 50;
+       while (c-- && ao_flight_state == ao_flight_pad)
+               pause(AO_MS_TO_TICKS(100));
+}
+
 void
 ao_report(void)
 {
@@ -105,6 +151,10 @@ ao_report(void)
                if (ao_flight_state == ao_flight_landed)
                        ao_report_altitude();
                ao_report_beep();
+               if (ao_flight_state == ao_flight_idle)
+                       ao_report_continuity();
+               while (ao_flight_state == ao_flight_pad)
+                       ao_report_continuity();
                __critical {
                        while (ao_report_state == ao_flight_state)
                                ao_sleep(DATA_TO_XDATA(&ao_flight_state));