Merge branch 'master' of ssh://git.gag.com/scm/git/fw/altos
[fw/altos] / src / kernel / ao_flight.c
index 9031a54ae070e97e42a6d182e0d4b802e9897918..f72efa068b8bc506305b73471c895c3f5a9564c9 100644 (file)
@@ -3,7 +3,8 @@
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; version 2 of the License.
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
  *
  * This program is distributed in the hope that it will be useful, but
  * WITHOUT ANY WARRANTY; without even the implied warranty of
@@ -20,7 +21,7 @@
 #include <ao_log.h>
 #endif
 
-#if HAS_MPU6000
+#if HAS_MPU6000 || HAS_MPU9250
 #include <ao_quaternion.h>
 #endif
 
 
 /* Main flight thread. */
 
-__pdata enum ao_flight_state   ao_flight_state;        /* current flight state */
-__pdata uint16_t               ao_boost_tick;          /* time of launch detect */
-__pdata uint16_t               ao_motor_number;        /* number of motors burned so far */
+enum ao_flight_state   ao_flight_state;        /* current flight state */
+uint16_t               ao_boost_tick;          /* time of most recent boost detect */
+uint16_t               ao_launch_tick;         /* time of first boost detect */
+uint16_t               ao_motor_number;        /* number of motors burned so far */
 
 #if HAS_SENSOR_ERRORS
 /* Any sensor can set this to mark the flight computer as 'broken' */
-__xdata uint8_t                        ao_sensor_errors;
+uint8_t                        ao_sensor_errors;
 #endif
 
 /*
  * track min/max data over a long interval to detect
  * resting
  */
-static __data uint16_t         ao_interval_end;
-static __data ao_v_t           ao_interval_min_height;
-static __data ao_v_t           ao_interval_max_height;
+static uint16_t                ao_interval_end;
+static ao_v_t          ao_interval_min_height;
+static ao_v_t          ao_interval_max_height;
 #if HAS_ACCEL
-static __data ao_v_t           ao_coast_avg_accel;
+static ao_v_t          ao_coast_avg_accel;
 #endif
 
-__pdata uint8_t                        ao_flight_force_idle;
+uint8_t                        ao_flight_force_idle;
 
 /* We also have a clock, which can be used to sanity check things in
  * case of other failures
@@ -173,7 +175,7 @@ ao_flight(void)
 #endif
                        }
                        /* wakeup threads due to state change */
-                       ao_wakeup(DATA_TO_XDATA(&ao_flight_state));
+                       ao_wakeup(&ao_flight_state);
 
                        break;
                case ao_flight_pad:
@@ -198,7 +200,7 @@ ao_flight(void)
                                )
                        {
                                ao_flight_state = ao_flight_boost;
-                               ao_boost_tick = ao_sample_tick;
+                               ao_launch_tick = ao_boost_tick = ao_sample_tick;
 
                                /* start logging data */
                                ao_log_start();
@@ -217,7 +219,7 @@ ao_flight(void)
                                ao_wakeup(&ao_gps_new);
 #endif
 
-                               ao_wakeup(DATA_TO_XDATA(&ao_flight_state));
+                               ao_wakeup(&ao_flight_state);
                        }
                        break;
                case ao_flight_boost:
@@ -232,7 +234,7 @@ ao_flight(void)
                         * deceleration, or by waiting until the maximum burn duration
                         * (15 seconds) has past.
                         */
-                       if ((ao_accel < AO_MSS_TO_ACCEL(-2.5) && ao_height > AO_M_TO_HEIGHT(100)) ||
+                       if ((ao_accel < AO_MSS_TO_ACCEL(-2.5)) ||
                            (int16_t) (ao_sample_tick - ao_boost_tick) > BOOST_TICKS_MAX)
                        {
 #if HAS_ACCEL
@@ -242,7 +244,7 @@ ao_flight(void)
                                ao_flight_state = ao_flight_coast;
 #endif
                                ++ao_motor_number;
-                               ao_wakeup(DATA_TO_XDATA(&ao_flight_state));
+                               ao_wakeup(&ao_flight_state);
                        }
                        break;
 #if HAS_ACCEL
@@ -255,7 +257,7 @@ ao_flight(void)
                        if (ao_speed < AO_MS_TO_SPEED(AO_MAX_BARO_SPEED))
                        {
                                ao_flight_state = ao_flight_coast;
-                               ao_wakeup(DATA_TO_XDATA(&ao_flight_state));
+                               ao_wakeup(&ao_flight_state);
                        } else
                                goto check_re_boost;
                        break;
@@ -268,7 +270,7 @@ ao_flight(void)
                         * number of seconds.
                         */
                        if (ao_config.apogee_lockout) {
-                               if ((ao_sample_tick - ao_boost_tick) <
+                               if ((int16_t) (ao_sample_tick - ao_launch_tick) <
                                    AO_SEC_TO_TICKS(ao_config.apogee_lockout))
                                        break;
                        }
@@ -281,9 +283,11 @@ ao_flight(void)
                         * the measured altitude reasonably closely; otherwise
                         * we're probably transsonic.
                         */
+#define AO_ERROR_BOUND 100
+
                        if (ao_speed < 0
 #if !HAS_ACCEL
-                           && (ao_sample_alt >= AO_MAX_BARO_HEIGHT || ao_error_h_sq_avg < 100)
+                           && (ao_sample_alt >= AO_MAX_BARO_HEIGHT || ao_error_h_sq_avg < AO_ERROR_BOUND)
 #endif
                                )
                        {
@@ -302,16 +306,16 @@ ao_flight(void)
 
                                /* and enter drogue state */
                                ao_flight_state = ao_flight_drogue;
-                               ao_wakeup(DATA_TO_XDATA(&ao_flight_state));
+                               ao_wakeup(&ao_flight_state);
                        }
 #if HAS_ACCEL
                        else {
                        check_re_boost:
-                               ao_coast_avg_accel = ao_coast_avg_accel - (ao_coast_avg_accel >> 6) + (ao_accel >> 6);
+                               ao_coast_avg_accel = ao_coast_avg_accel + ((ao_accel - ao_coast_avg_accel) >> 5);
                                if (ao_coast_avg_accel > AO_MSS_TO_ACCEL(20)) {
                                        ao_boost_tick = ao_sample_tick;
                                        ao_flight_state = ao_flight_boost;
-                                       ao_wakeup(DATA_TO_XDATA(&ao_flight_state));
+                                       ao_wakeup(&ao_flight_state);
                                }
                        }
 #endif
@@ -348,7 +352,7 @@ ao_flight(void)
                                ao_interval_min_height = ao_interval_max_height = ao_avg_height;
 
                                ao_flight_state = ao_flight_main;
-                               ao_wakeup(DATA_TO_XDATA(&ao_flight_state));
+                               ao_wakeup(&ao_flight_state);
                        }
                        break;
 
@@ -375,7 +379,7 @@ ao_flight(void)
                                        ao_timer_set_adc_interval(0);
 #endif
 
-                                       ao_wakeup(DATA_TO_XDATA(&ao_flight_state));
+                                       ao_wakeup(&ao_flight_state);
                                }
                                ao_interval_min_height = ao_interval_max_height = ao_avg_height;
                                ao_interval_end = ao_sample_tick + AO_INTERVAL_TICKS;
@@ -459,7 +463,7 @@ ao_orient_test_select(void)
        ao_orient_test = !ao_orient_test;
 }
 
-__code struct ao_cmds ao_flight_cmds[] = {
+const struct ao_cmds ao_flight_cmds[] = {
        { ao_flight_dump,       "F\0Dump flight status" },
        { ao_gyro_test,         "G\0Test gyro code" },
        { ao_orient_test_select,"O\0Test orientation code" },
@@ -467,7 +471,7 @@ __code struct ao_cmds ao_flight_cmds[] = {
 };
 #endif
 
-static __xdata struct ao_task  flight_task;
+static struct ao_task  flight_task;
 
 void
 ao_flight_init(void)