return ((count / 16.0) / 2047.0 + 0.095) / 0.009 * 1000.0;
}
+ static double
+ thermometer_to_temperature(double thermo)
+ {
+ return (thermo - 19791.268) / 32728.0 * 1.25 / 0.00247;
+ }
+
+ static double mega_adc(int raw) {
+ return raw / 4095.0;
+ }
+
+ static public double mega_battery_voltage(int v_batt) {
+ if (v_batt != AltosRecord.MISSING)
+ return 3.3 * mega_adc(v_batt) * (15.0 + 27.0) / 27.0;
+ return AltosRecord.MISSING;
+ }
+
+ static double mega_pyro_voltage(int raw) {
+ if (raw != AltosRecord.MISSING)
+ return 3.3 * mega_adc(raw) * (100.0 + 27.0) / 27.0;
+ return AltosRecord.MISSING;
+ }
+
public static double radio_to_frequency(int freq, int setting, int cal, int channel) {
double f;
public int data8[];
public boolean valid;
+ public int data8(int i) {
+ return data8[i];
+ }
+
+ public int data16(int i) {
+ return ((data8[i] | (data8[i+1] << 8)) << 16) >> 16;
+ }
+
+ public int data24(int i) {
+ return data8[i] | (data8[i+1] << 8) | (data8[i+2] << 16);
+ }
+
+ public int data32(int i) {
+ return data8[i] | (data8[i+1] << 8) | (data8[i+2] << 16) | (data8[i+3] << 24);
+ }
+
public final static int header_length = 4;
+ public abstract int record_length();
+
public abstract void update_state(AltosState state);
public void write(PrintStream out) {
out.printf ("\n");
}
- void parse_chunk(AltosEepromChunk chunk, int start, int record_length) throws ParseException {
+ public String string() {
+ String s;
+
+ s = String.format("%c %04x", cmd, tick);
+ if (data8 != null) {
+ for (int i = 0; i < data8.length; i++) {
+ String d = String.format(" %02x", data8[i]);
+ s = s.concat(d);
+ }
+ }
+ s = s.concat("\n");
+ return s;
+ }
+
+ void parse_chunk(AltosEepromChunk chunk, int start) throws ParseException {
cmd = chunk.data(start);
- int data_length = record_length - header_length;
+ int data_length = record_length() - header_length;
- valid = !chunk.erased(start, record_length);
+ valid = !chunk.erased(start, record_length());
if (valid) {
- if (AltosConvert.checksum(chunk.data, start, record_length) != 0)
+ if (AltosConvert.checksum(chunk.data, start, record_length()) != 0)
throw new ParseException(String.format("invalid checksum at 0x%x",
chunk.address + start), 0);
} else {
data8[i] = chunk.data(start + header_length + i);
}
- void parse_string(String line, int record_length) {
+ void parse_string(String line) {
valid = false;
tick = 0;
cmd = AltosLib.AO_LOG_INVALID;
- int data_length = record_length - header_length;
+ int data_length = record_length() - header_length;
if (line == null)
return;
tick = Integer.parseInt(tokens[1],16);
valid = true;
data8 = new int[data_length];
+
for (int i = 0; i < data_length; i++)
data8[i] = Integer.parseInt(tokens[2 + i],16);
}
return true;
}
+ public AltosEeprom eeprom(int offset, int log_format) {
+ AltosEeprom eeprom = null;
+ try {
+ switch (log_format) {
+ case AltosLib.AO_LOG_FORMAT_FULL:
+ eeprom = new AltosEepromTM(this, offset);
+ break;
+ case AltosLib.AO_LOG_FORMAT_TINY:
+ case AltosLib.AO_LOG_FORMAT_TELEMETRY:
+ case AltosLib.AO_LOG_FORMAT_TELESCIENCE:
+ case AltosLib.AO_LOG_FORMAT_TELEMEGA:
+ eeprom = new AltosEepromMega(this, offset);
+ break;
+ case AltosLib.AO_LOG_FORMAT_TELEMETRUM:
+ eeprom = new AltosEepromMetrum2(this, offset);
+ break;
+ case AltosLib.AO_LOG_FORMAT_TELEMINI:
+ case AltosLib.AO_LOG_FORMAT_EASYMINI:
+ eeprom = new AltosEepromMini(this, offset);
+ break;
+ }
+ } catch (ParseException e) {
+ }
+ return eeprom;
+ }
+
public AltosEepromChunk(AltosLink link, int block, boolean flush)
throws TimeoutException, InterruptedException {
headers = new AltosEepromIterable(AltosEepromHeader.read(input));
start = headers.state();
+ start.set_state(AltosLib.ao_flight_pad);
switch (start.log_format) {
case AltosLib.AO_LOG_FORMAT_FULL:
case AltosLib.AO_LOG_FORMAT_TELEMETRY:
case AltosLib.AO_LOG_FORMAT_TELESCIENCE:
case AltosLib.AO_LOG_FORMAT_TELEMEGA:
+ body = new AltosEepromIterable(AltosEepromMega.read(input));
+ break;
+ case AltosLib.AO_LOG_FORMAT_TELEMETRUM:
+ body = new AltosEepromIterable(AltosEepromMetrum2.read(input));
break;
case AltosLib.AO_LOG_FORMAT_TELEMINI:
case AltosLib.AO_LOG_FORMAT_EASYMINI:
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+import java.io.*;
+import java.util.*;
+import java.text.*;
+
+public class AltosEepromGPS extends AltosEeprom {
+ public static final int record_length = 16;
+
+ public int record_length() { return record_length; }
+
+ /* AO_LOG_FLIGHT elements */
+ public int flight() { return data16(0); }
+ public int ground_accel() { return data16(2); }
+ public int ground_pres() { return data32(4); }
+ public int ground_temp() { return data32(8); }
+
+ /* AO_LOG_STATE elements */
+ public int state() { return data16(0); }
+ public int reason() { return data16(2); }
+
+ /* AO_LOG_SENSOR elements */
+ public int pres() { return data32(0); }
+ public int temp() { return data32(4); }
+ public int accel() { return data16(8); }
+
+ /* AO_LOG_TEMP_VOLT elements */
+ public int v_batt() { return data16(0); }
+ public int sense_a() { return data16(2); }
+ public int sense_m() { return data16(4); }
+
+ /* AO_LOG_GPS_POS elements */
+ public int latitude() { return data32(0); }
+ public int longitude() { return data32(4); }
+ public int altitude() { return data16(8); }
+
+ /* AO_LOG_GPS_TIME elements */
+ public int hour() { return data8(0); }
+ public int minute() { return data8(1); }
+ public int second() { return data8(2); }
+ public int flags() { return data8(3); }
+ public int year() { return data8(4); }
+ public int month() { return data8(5); }
+ public int day() { return data8(6); }
+
+ /* AO_LOG_GPS_SAT elements */
+ public int nsat() { return data8(0); }
+ public int more() { return data8(1); }
+ public int svid(int n) { return data8(2 + n * 2); }
+ public int c_n(int n) { return data8(2 + n * 2 + 1); }
+
+ public AltosEepromMetrum2 (AltosEepromChunk chunk, int start) throws ParseException {
+ parse_chunk(chunk, start);
+ }
+
+ public void update_state(AltosState state) {
+ AltosGPS gps;
+
+ /* Flush any pending GPS changes */
+ if (state.gps_pending) {
+ switch (cmd) {
+ case AltosLib.AO_LOG_GPS_POS:
+ case AltosLib.AO_LOG_GPS_LAT:
+ case AltosLib.AO_LOG_GPS_LON:
+ case AltosLib.AO_LOG_GPS_ALT:
+ case AltosLib.AO_LOG_GPS_SAT:
+ case AltosLib.AO_LOG_GPS_DATE:
+ break;
+ default:
+ state.set_temp_gps();
+ break;
+ }
+ }
+
+ if (cmd != AltosLib.AO_LOG_FLIGHT)
+ state.set_tick(tick);
+ switch (cmd) {
+ case AltosLib.AO_LOG_FLIGHT:
+ state.set_boost_tick(tick);
+ state.set_flight(flight());
+ state.set_ground_accel(ground_accel());
+ state.set_ground_pressure(ground_pres());
+// state.set_temperature(ground_temp() / 100.0);
+ break;
+ case AltosLib.AO_LOG_STATE:
+ state.set_state(state());
+ break;
+ case AltosLib.AO_LOG_SENSOR:
+ state.set_ms5607(pres(), temp());
+ state.set_accel(accel());
+
+ break;
+ case AltosLib.AO_LOG_TEMP_VOLT:
+ state.set_battery_voltage(AltosConvert.mega_battery_voltage(v_batt()));
+
+ state.set_apogee_voltage(AltosConvert.mega_pyro_voltage(sense_a()));
+ state.set_main_voltage(AltosConvert.mega_pyro_voltage(sense_m()));
+
+ break;
+ case AltosLib.AO_LOG_GPS_POS:
+ gps = state.make_temp_gps();
+ gps.lat = latitude() / 1e7;
+ gps.lon = longitude() / 1e7;
+ gps.alt = altitude();
+ break;
+ case AltosLib.AO_LOG_GPS_TIME:
+ gps = state.make_temp_gps();
+
+ gps.hour = hour();
+ gps.minute = minute();
+ gps.second = second();
+
+ int flags = flags();
+
+ gps.connected = (flags & AltosLib.AO_GPS_RUNNING) != 0;
+ gps.locked = (flags & AltosLib.AO_GPS_VALID) != 0;
+ gps.nsat = (flags & AltosLib.AO_GPS_NUM_SAT_MASK) >>
+ AltosLib.AO_GPS_NUM_SAT_SHIFT;
+
+ gps.year = year();
+ gps.month = month();
+ gps.day = day();
+ break;
+ case AltosLib.AO_LOG_GPS_SAT:
+ state.set_tick(tick);
+ gps = state.make_temp_gps();
+
+ int n = nsat();
+ for (int i = 0; i < n; i++)
+ gps.add_sat(svid(i), c_n(i));
+ break;
+ }
+ }
+
+ public AltosEepromMetrum2 (String line) {
+ parse_string(line);
+ }
+
+ static public LinkedList<AltosEeprom> read(FileInputStream input) {
+ LinkedList<AltosEeprom> megas = new LinkedList<AltosEeprom>();
+
+ for (;;) {
+ try {
+ String line = AltosLib.gets(input);
+ if (line == null)
+ break;
+ try {
+ AltosEepromMetrum2 mega = new AltosEepromMetrum2(line);
+ if (mega.cmd != AltosLib.AO_LOG_INVALID)
+ megas.add(mega);
+ } catch (Exception e) {
+ System.out.printf ("exception\n");
+ }
+ } catch (IOException ie) {
+ break;
+ }
+ }
+
+ return megas;
+ }
+}
public boolean last;
public boolean valid;
+ public int record_length () { return 0; }
+
+ /* XXX pull rest of config data to state */
public void update_state(AltosState state) {
switch (cmd) {
case AltosLib.AO_LOG_CONFIG_VERSION:
case AltosLib.AO_LOG_RADIO_CHANNEL:
break;
case AltosLib.AO_LOG_CALLSIGN:
- state.callsign = data;
+ state.set_callsign(data);
break;
case AltosLib.AO_LOG_ACCEL_CAL:
state.set_accel_g(config_a, config_b);
state.baro.crc = config_a;
break;
case AltosLib.AO_LOG_SOFTWARE_VERSION:
+ state.set_firmware_version(data);
break;
}
}
package org.altusmetrum.altoslib_1;
+import java.io.*;
+import java.util.*;
import java.text.*;
-public class AltosEepromMega {
- public int cmd;
- public int tick;
- public boolean valid;
- public String data;
- public int config_a, config_b;
-
- public int data8[];
-
+public class AltosEepromMega extends AltosEeprom {
public static final int record_length = 32;
- static final int header_length = 4;
- static final int data_length = record_length - header_length;
-
- public int data8(int i) {
- return data8[i];
- }
- public int data16(int i) {
- return ((data8[i] | (data8[i+1] << 8)) << 16) >> 16;
- }
-
- public int data32(int i) {
- return data8[i] | (data8[i+1] << 8) | (data8[i+2] << 16) | (data8[i+3] << 24);
- }
+ public int record_length() { return record_length; }
/* AO_LOG_FLIGHT elements */
public int flight() { return data16(0); }
public int mag_z() { return data16(24); }
public int accel() { return data16(26); }
- /* AO_LOG_VOLT elements */
+ /* AO_LOG_TEMP_VOLT elements */
public int v_batt() { return data16(0); }
public int v_pbatt() { return data16(2); }
public int nsense() { return data16(4); }
public int nsat() { return data16(0); }
public int svid(int n) { return data8(2 + n * 2); }
public int c_n(int n) { return data8(2 + n * 2 + 1); }
+
public AltosEepromMega (AltosEepromChunk chunk, int start) throws ParseException {
- cmd = chunk.data(start);
-
- valid = !chunk.erased(start, record_length);
- if (valid) {
- if (AltosConvert.checksum(chunk.data, start, record_length) != 0)
- throw new ParseException(String.format("invalid checksum at 0x%x",
- chunk.address + start), 0);
- } else {
- cmd = AltosLib.AO_LOG_INVALID;
- }
+ parse_chunk(chunk, start);
+ }
- tick = chunk.data16(start+2);
+ public void update_state(AltosState state) {
+ AltosGPS gps;
+
+ /* Flush any pending GPS changes */
+ if (state.gps_pending) {
+ switch (cmd) {
+ case AltosLib.AO_LOG_GPS_LAT:
+ case AltosLib.AO_LOG_GPS_LON:
+ case AltosLib.AO_LOG_GPS_ALT:
+ case AltosLib.AO_LOG_GPS_SAT:
+ case AltosLib.AO_LOG_GPS_DATE:
+ break;
+ default:
+ state.set_temp_gps();
+ break;
+ }
+ }
- data8 = new int[data_length];
- for (int i = 0; i < data_length; i++)
- data8[i] = chunk.data(start + header_length + i);
+ switch (cmd) {
+ case AltosLib.AO_LOG_FLIGHT:
+ state.set_boost_tick(tick);
+ state.set_flight(flight());
+ state.set_ground_accel(ground_accel());
+ state.set_ground_pressure(ground_pres());
+ state.set_temperature(ground_temp() / 100.0);
+ break;
+ case AltosLib.AO_LOG_STATE:
+ state.set_tick(tick);
+ state.set_state(state());
+ break;
+ case AltosLib.AO_LOG_SENSOR:
+ state.set_tick(tick);
+ state.set_ms5607(pres(), temp());
+
+ AltosIMU imu = new AltosIMU();
+ imu.accel_x = accel_x();
+ imu.accel_y = accel_y();
+ imu.accel_z = accel_z();
+
+ imu.gyro_x = gyro_x();
+ imu.gyro_y = gyro_y();
+ imu.gyro_z = gyro_z();
+ state.imu = imu;
+
+ AltosMag mag = new AltosMag();
+ mag.x = mag_x();
+ mag.y = mag_y();
+ mag.z = mag_z();
+
+ state.mag = mag;
+
+ state.set_accel(accel());
+
+ break;
+ case AltosLib.AO_LOG_TEMP_VOLT:
+ state.set_battery_voltage(AltosConvert.mega_battery_voltage(v_batt()));
+ state.set_pyro_voltage(AltosConvert.mega_pyro_voltage(v_pbatt()));
+
+ int nsense = nsense();
+
+ state.set_apogee_voltage(AltosConvert.mega_pyro_voltage(sense(nsense-2)));
+ state.set_main_voltage(AltosConvert.mega_pyro_voltage(sense(nsense-1)));
+
+ double voltages[] = new double[nsense-2];
+ for (int i = 0; i < nsense-2; i++)
+ voltages[i] = AltosConvert.mega_pyro_voltage(sense(i));
+
+ state.set_ignitor_voltage(voltages);
+ break;
+ case AltosLib.AO_LOG_GPS_TIME:
+ state.set_tick(tick);
+ gps = state.make_temp_gps();
+ gps.lat = latitude() / 1e7;
+ gps.lon = longitude() / 1e7;
+ gps.alt = altitude();
+
+ gps.hour = hour();
+ gps.minute = minute();
+ gps.second = second();
+
+ int flags = flags();
+
+ gps.connected = (flags & AltosLib.AO_GPS_RUNNING) != 0;
+ gps.locked = (flags & AltosLib.AO_GPS_VALID) != 0;
+ gps.nsat = (flags & AltosLib.AO_GPS_NUM_SAT_MASK) >>
+ AltosLib.AO_GPS_NUM_SAT_SHIFT;
+
+ gps.year = year();
+ gps.month = month();
+ gps.day = day();
+ break;
+ case AltosLib.AO_LOG_GPS_SAT:
+ state.set_tick(tick);
+ gps = state.make_temp_gps();
+
+ int n = nsat();
+ for (int i = 0; i < n; i++)
+ gps.add_sat(svid(i), c_n(i));
+ break;
+ }
}
public AltosEepromMega (String line) {
- valid = false;
- tick = 0;
+ parse_string(line);
+ }
- if (line == null) {
- cmd = AltosLib.AO_LOG_INVALID;
- line = "";
- } else {
+ static public LinkedList<AltosEeprom> read(FileInputStream input) {
+ LinkedList<AltosEeprom> megas = new LinkedList<AltosEeprom>();
+
+ for (;;) {
try {
- String[] tokens = line.split("\\s+");
-
- if (tokens[0].length() == 1) {
- if (tokens.length != 2 + data_length) {
- cmd = AltosLib.AO_LOG_INVALID;
- data = line;
- } else {
- cmd = tokens[0].codePointAt(0);
- tick = Integer.parseInt(tokens[1],16);
- valid = true;
- data8 = new int[data_length];
- for (int i = 0; i < data_length; i++)
- data8[i] = Integer.parseInt(tokens[2 + i],16);
- }
- } else if (tokens[0].equals("Config") && tokens[1].equals("version:")) {
- cmd = AltosLib.AO_LOG_CONFIG_VERSION;
- data = tokens[2];
- } else if (tokens[0].equals("Main") && tokens[1].equals("deploy:")) {
- cmd = AltosLib.AO_LOG_MAIN_DEPLOY;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[0].equals("Apogee") && tokens[1].equals("delay:")) {
- cmd = AltosLib.AO_LOG_APOGEE_DELAY;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[0].equals("Radio") && tokens[1].equals("channel:")) {
- cmd = AltosLib.AO_LOG_RADIO_CHANNEL;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[0].equals("Callsign:")) {
- cmd = AltosLib.AO_LOG_CALLSIGN;
- data = tokens[1].replaceAll("\"","");
- } else if (tokens[0].equals("Accel") && tokens[1].equals("cal")) {
- cmd = AltosLib.AO_LOG_ACCEL_CAL;
- config_a = Integer.parseInt(tokens[3]);
- config_b = Integer.parseInt(tokens[5]);
- } else if (tokens[0].equals("Radio") && tokens[1].equals("cal:")) {
- cmd = AltosLib.AO_LOG_RADIO_CAL;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[0].equals("Max") && tokens[1].equals("flight") && tokens[2].equals("log:")) {
- cmd = AltosLib.AO_LOG_MAX_FLIGHT_LOG;
- config_a = Integer.parseInt(tokens[3]);
- } else if (tokens[0].equals("manufacturer")) {
- cmd = AltosLib.AO_LOG_MANUFACTURER;
- data = tokens[1];
- } else if (tokens[0].equals("product")) {
- cmd = AltosLib.AO_LOG_PRODUCT;
- data = tokens[1];
- } else if (tokens[0].equals("serial-number")) {
- cmd = AltosLib.AO_LOG_SERIAL_NUMBER;
- config_a = Integer.parseInt(tokens[1]);
- } else if (tokens[0].equals("log-format")) {
- cmd = AltosLib.AO_LOG_LOG_FORMAT;
- config_a = Integer.parseInt(tokens[1]);
- } else if (tokens[0].equals("software-version")) {
- cmd = AltosLib.AO_LOG_SOFTWARE_VERSION;
- data = tokens[1];
- } else if (tokens[0].equals("ms5607")) {
- if (tokens[1].equals("reserved:")) {
- cmd = AltosLib.AO_LOG_BARO_RESERVED;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[1].equals("sens:")) {
- cmd = AltosLib.AO_LOG_BARO_SENS;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[1].equals("off:")) {
- cmd = AltosLib.AO_LOG_BARO_OFF;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[1].equals("tcs:")) {
- cmd = AltosLib.AO_LOG_BARO_TCS;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[1].equals("tco:")) {
- cmd = AltosLib.AO_LOG_BARO_TCO;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[1].equals("tref:")) {
- cmd = AltosLib.AO_LOG_BARO_TREF;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[1].equals("tempsens:")) {
- cmd = AltosLib.AO_LOG_BARO_TEMPSENS;
- config_a = Integer.parseInt(tokens[2]);
- } else if (tokens[1].equals("crc:")) {
- cmd = AltosLib.AO_LOG_BARO_CRC;
- config_a = Integer.parseInt(tokens[2]);
- } else {
- cmd = AltosLib.AO_LOG_INVALID;
- data = line;
- }
- } else {
- cmd = AltosLib.AO_LOG_INVALID;
- data = line;
+ String line = AltosLib.gets(input);
+ if (line == null)
+ break;
+ try {
+ AltosEepromMega mega = new AltosEepromMega(line);
+ if (mega.cmd != AltosLib.AO_LOG_INVALID)
+ megas.add(mega);
+ } catch (Exception e) {
+ System.out.printf ("exception\n");
}
- } catch (NumberFormatException ne) {
- cmd = AltosLib.AO_LOG_INVALID;
- data = line;
+ } catch (IOException ie) {
+ break;
}
}
- }
- public AltosEepromMega(int in_cmd, int in_tick) {
- cmd = in_cmd;
- tick = in_tick;
- valid = true;
+ return megas;
}
}
static final int header_length = 4;
static final int data_length = record_length - header_length;
+ public int record_length() { return record_length; }
+
public int data8(int i) {
return data8[i];
}
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+import java.io.*;
+import java.util.*;
+import java.text.*;
+
+public class AltosEepromMetrum2 extends AltosEeprom {
+ public static final int record_length = 16;
+
+ public int record_length() { return record_length; }
+
+ /* AO_LOG_FLIGHT elements */
+ public int flight() { return data16(0); }
+ public int ground_accel() { return data16(2); }
+ public int ground_pres() { return data32(4); }
+ public int ground_temp() { return data32(8); }
+
+ /* AO_LOG_STATE elements */
+ public int state() { return data16(0); }
+ public int reason() { return data16(2); }
+
+ /* AO_LOG_SENSOR elements */
+ public int pres() { return data32(0); }
+ public int temp() { return data32(4); }
+ public int accel() { return data16(8); }
+
+ /* AO_LOG_TEMP_VOLT elements */
+ public int v_batt() { return data16(0); }
+ public int sense_a() { return data16(2); }
+ public int sense_m() { return data16(4); }
+
+ /* AO_LOG_GPS_POS elements */
+ public int latitude() { return data32(0); }
+ public int longitude() { return data32(4); }
+ public int altitude() { return data16(8); }
+
+ /* AO_LOG_GPS_TIME elements */
+ public int hour() { return data8(0); }
+ public int minute() { return data8(1); }
+ public int second() { return data8(2); }
+ public int flags() { return data8(3); }
+ public int year() { return data8(4); }
+ public int month() { return data8(5); }
+ public int day() { return data8(6); }
+
+ /* AO_LOG_GPS_SAT elements */
+ public int nsat() { return data8(0); }
+ public int more() { return data8(1); }
+ public int svid(int n) { return data8(2 + n * 2); }
+ public int c_n(int n) { return data8(2 + n * 2 + 1); }
+
+ public AltosEepromMetrum2 (AltosEepromChunk chunk, int start) throws ParseException {
+ parse_chunk(chunk, start);
+ }
+
+ public void update_state(AltosState state) {
+ AltosGPS gps;
+
+ /* Flush any pending GPS changes */
+ if (state.gps_pending) {
+ switch (cmd) {
+ case AltosLib.AO_LOG_GPS_POS:
+ case AltosLib.AO_LOG_GPS_LAT:
+ case AltosLib.AO_LOG_GPS_LON:
+ case AltosLib.AO_LOG_GPS_ALT:
+ case AltosLib.AO_LOG_GPS_SAT:
+ case AltosLib.AO_LOG_GPS_DATE:
+ break;
+ default:
+ state.set_temp_gps();
+ break;
+ }
+ }
+
+ if (cmd != AltosLib.AO_LOG_FLIGHT)
+ state.set_tick(tick);
+ switch (cmd) {
+ case AltosLib.AO_LOG_FLIGHT:
+ state.set_boost_tick(tick);
+ state.set_flight(flight());
+ state.set_ground_accel(ground_accel());
+ state.set_ground_pressure(ground_pres());
+// state.set_temperature(ground_temp() / 100.0);
+ break;
+ case AltosLib.AO_LOG_STATE:
+ state.set_state(state());
+ break;
+ case AltosLib.AO_LOG_SENSOR:
+ state.set_ms5607(pres(), temp());
+ state.set_accel(accel());
+
+ break;
+ case AltosLib.AO_LOG_TEMP_VOLT:
+ state.set_battery_voltage(AltosConvert.mega_battery_voltage(v_batt()));
+
+ state.set_apogee_voltage(AltosConvert.mega_pyro_voltage(sense_a()));
+ state.set_main_voltage(AltosConvert.mega_pyro_voltage(sense_m()));
+
+ break;
+ case AltosLib.AO_LOG_GPS_POS:
+ gps = state.make_temp_gps();
+ gps.lat = latitude() / 1e7;
+ gps.lon = longitude() / 1e7;
+ gps.alt = altitude();
+ break;
+ case AltosLib.AO_LOG_GPS_TIME:
+ gps = state.make_temp_gps();
+
+ gps.hour = hour();
+ gps.minute = minute();
+ gps.second = second();
+
+ int flags = flags();
+
+ gps.connected = (flags & AltosLib.AO_GPS_RUNNING) != 0;
+ gps.locked = (flags & AltosLib.AO_GPS_VALID) != 0;
+ gps.nsat = (flags & AltosLib.AO_GPS_NUM_SAT_MASK) >>
+ AltosLib.AO_GPS_NUM_SAT_SHIFT;
+
+ gps.year = year();
+ gps.month = month();
+ gps.day = day();
+ break;
+ case AltosLib.AO_LOG_GPS_SAT:
+ state.set_tick(tick);
+ gps = state.make_temp_gps();
+
+ int n = nsat();
+ for (int i = 0; i < n; i++)
+ gps.add_sat(svid(i), c_n(i));
+ break;
+ }
+ }
+
+ public AltosEepromMetrum2 (String line) {
+ parse_string(line);
+ }
+
+ static public LinkedList<AltosEeprom> read(FileInputStream input) {
+ LinkedList<AltosEeprom> megas = new LinkedList<AltosEeprom>();
+
+ for (;;) {
+ try {
+ String line = AltosLib.gets(input);
+ if (line == null)
+ break;
+ try {
+ AltosEepromMetrum2 mega = new AltosEepromMetrum2(line);
+ if (mega.cmd != AltosLib.AO_LOG_INVALID)
+ megas.add(mega);
+ } catch (Exception e) {
+ System.out.printf ("exception\n");
+ }
+ } catch (IOException ie) {
+ break;
+ }
+ }
+
+ return megas;
+ }
+}
public class AltosEepromMini extends AltosEeprom {
public static final int record_length = 16;
- public int data8(int i) {
- return data8[i];
- }
-
- public int data16(int i) {
- return ((data8[i] | (data8[i+1] << 8)) << 16) >> 16;
- }
-
- public int data24(int i) {
- return data8[i] | (data8[i+1] << 8) | (data8[i+2] << 16);
- }
-
- public int data32(int i) {
- return data8[i] | (data8[i+1] << 8) | (data8[i+2] << 16) | (data8[i+3] << 24);
- }
+ public int record_length() { return record_length; }
/* AO_LOG_FLIGHT elements */
public int flight() { return data16(0); }
}
public AltosEepromMini (AltosEepromChunk chunk, int start) throws ParseException {
- parse_chunk(chunk, start, record_length);
+ parse_chunk(chunk, start);
}
public AltosEepromMini (String line) {
- parse_string(line, record_length);
+ parse_string(line);
}
public AltosEepromMini(int in_cmd, int in_tick) {
public static final int record_length = 8;
- static double
- thermometer_to_temperature(double thermo)
- {
- return (thermo - 19791.268) / 32728.0 * 1.25 / 0.00247;
- }
-
public void write(PrintStream out) {
out.printf("%c %4x %4x %4x\n", cmd, tick, a, b);
}
+ public int record_length() { return record_length; }
+
+ public String string() {
+ return String.format("%c %4x %4x %4x\n", cmd, tick, a, b);
+ }
+
public void update_state(AltosState state) {
AltosGPS gps;
break;
case AltosLib.AO_LOG_TEMP_VOLT:
state.set_tick(tick);
- state.set_temperature(thermometer_to_temperature(a));
+ state.set_temperature(AltosConvert.thermometer_to_temperature(a));
state.set_battery_voltage(AltosConvert.cc_battery_to_voltage(b));
break;
case AltosLib.AO_LOG_DEPLOY:
static final int max_data = 12;
public static final int record_length = 32;
+ public int record_length() { return record_length; }
+
public AltosEepromTeleScience (AltosEepromChunk chunk, int start) throws ParseException {
type = chunk.data(start);
}
public void ClearGPSTime() {
- year = month = day = 0;
- hour = minute = second = 0;
+ year = month = day = AltosRecord.MISSING;
+ hour = minute = second = AltosRecord.MISSING;
}
public AltosGPS(AltosTelemetryMap map) throws ParseException {
}
public AltosGPS() {
+ lat = AltosRecord.MISSING;
+ lon = AltosRecord.MISSING;
+ alt = AltosRecord.MISSING;
ClearGPSTime();
cc_gps_sat = null;
}
}
}
} else {
+ lat = AltosRecord.MISSING;
+ lon = AltosRecord.MISSING;
+ alt = AltosRecord.MISSING;
ClearGPSTime();
cc_gps_sat = null;
}
public static final int AO_LOG_TEMP_VOLT = 'T';
public static final int AO_LOG_DEPLOY = 'D';
public static final int AO_LOG_STATE = 'S';
+ public static final int AO_LOG_GPS_POS = 'P';
public static final int AO_LOG_GPS_TIME = 'G';
public static final int AO_LOG_GPS_LAT = 'N';
public static final int AO_LOG_GPS_LON = 'W';
/* derived data */
- public long report_time;
+ public long received_time;
public double time;
public double prev_time;
public boolean boost; /* under power */
public int rssi;
public int status;
+ public int device_type;
+ public int config_major;
+ public int config_minor;
+ public int apogee_delay;
+ public int main_deploy;
+ public int flight_log_max;
public double ground_altitude;
public double ground_pressure;
public double apogee_voltage;
public double main_voltage;
public double speed;
+ public double ignitor_voltage[];
public double prev_height;
public double prev_speed;
public double prev_acceleration;
+ public double prev_max_height;
+ public double prev_max_acceleration;
+ public double prev_max_speed;
+
public double max_height;
public double max_acceleration;
public double max_speed;
public double speak_altitude;
public String callsign;
+ public String firmware_version;
+
public double accel_plus_g;
public double accel_minus_g;
public double accel;
set = 0;
- report_time = System.currentTimeMillis();
+ received_time = System.currentTimeMillis();
time = AltosRecord.MISSING;
time_change = AltosRecord.MISSING;
prev_time = AltosRecord.MISSING;
boost = false;
rssi = AltosRecord.MISSING;
status = 0;
+ device_type = AltosRecord.MISSING;
+ config_major = AltosRecord.MISSING;
+ config_minor = AltosRecord.MISSING;
+ apogee_delay = AltosRecord.MISSING;
+ main_deploy = AltosRecord.MISSING;
+ flight_log_max = AltosRecord.MISSING;
ground_altitude = AltosRecord.MISSING;
ground_pressure = AltosRecord.MISSING;
prev_speed = AltosRecord.MISSING;
prev_acceleration = AltosRecord.MISSING;
+ prev_max_height = 0;
+ prev_max_speed = 0;
+ prev_max_acceleration = 0;
+
battery_voltage = AltosRecord.MISSING;
pyro_voltage = AltosRecord.MISSING;
apogee_voltage = AltosRecord.MISSING;
main_voltage = AltosRecord.MISSING;
+ ignitor_voltage = null;
speed = AltosRecord.MISSING;
return;
}
- report_time = old.report_time;
+ received_time = old.received_time;
time = old.time;
time_change = 0;
tick = old.tick;
boost = old.boost;
rssi = old.rssi;
status = old.status;
+ device_type = old.device_type;
+ config_major = old.config_major;
+ config_minor = old.config_minor;
+ apogee_delay = old.apogee_delay;
+ main_deploy = old.main_deploy;
+ flight_log_max = old.flight_log_max;
set = 0;
temperature = old.temperature;
apogee_voltage = old.apogee_voltage;
main_voltage = old.main_voltage;
+ ignitor_voltage = old.ignitor_voltage;
speed = old.speed;
prev_height = old.height;
prev_speed = old.speed;
prev_acceleration = old.acceleration;
+
+ prev_max_height = old.max_height;
+ prev_max_speed = old.max_speed;
+ prev_max_acceleration = old.max_acceleration;
prev_time = old.time;
max_height = old.max_height;
else
height = AltosRecord.MISSING;
- if (height != AltosRecord.MISSING && height > max_height)
+ if (height != AltosRecord.MISSING && height > prev_max_height)
max_height = height;
update_speed();
}
}
}
- if (boost && speed != AltosRecord.MISSING && speed > max_speed)
+ if (boost && speed != AltosRecord.MISSING && speed > prev_max_speed)
max_speed = speed;
}
void update_accel() {
- double ground = ground_accel;
-
- if (ground == AltosRecord.MISSING)
- ground = ground_accel_avg;
- if (accel == AltosRecord.MISSING)
- return;
- if (ground == AltosRecord.MISSING)
- return;
- if (accel_plus_g == AltosRecord.MISSING)
- return;
- if (accel_minus_g == AltosRecord.MISSING)
- return;
-
- double counts_per_g = (accel_minus_g - accel_plus_g) / 2.0;
- double counts_per_mss = counts_per_g / 9.80665;
-
- acceleration = (ground - accel) / counts_per_mss;
+ if (kalman_acceleration != AltosRecord.MISSING) {
+ acceleration = kalman_acceleration;
+ } else {
+ double ground = ground_accel;
+
+ if (ground == AltosRecord.MISSING)
+ ground = ground_accel_avg;
+ if (accel == AltosRecord.MISSING)
+ return;
+ if (ground == AltosRecord.MISSING)
+ return;
+ if (accel_plus_g == AltosRecord.MISSING)
+ return;
+ if (accel_minus_g == AltosRecord.MISSING)
+ return;
+
+ double counts_per_g = (accel_minus_g - accel_plus_g) / 2.0;
+ double counts_per_mss = counts_per_g / 9.80665;
+ acceleration = (ground - accel) / counts_per_mss;
+ }
/* Only look at accelerometer data under boost */
- if (boost && acceleration != AltosRecord.MISSING && (max_acceleration == AltosRecord.MISSING || acceleration > max_acceleration))
+ if (boost && acceleration != AltosRecord.MISSING && acceleration > prev_max_acceleration)
max_acceleration = acceleration;
update_speed();
}
}
+ public void set_device_type(int device_type) {
+ this.device_type = device_type;
+ }
+
+ public void set_config(int major, int minor, int apogee_delay, int main_deploy, int flight_log_max) {
+ config_major = major;
+ config_minor = minor;
+ this.apogee_delay = apogee_delay;
+ this.main_deploy = main_deploy;
+ this.flight_log_max = flight_log_max;
+ }
+
+ public void set_callsign(String callsign) {
+ this.callsign = callsign;
+ }
+
+ public void set_firmware_version(String version) {
+ firmware_version = version;
+ }
+
public void set_flight(int flight) {
/* When the flight changes, reset the state */
}
}
+ public void set_received_time(long ms) {
+ received_time = ms;
+ }
+
public void set_altitude(double altitude) {
if (altitude != AltosRecord.MISSING) {
this.altitude = altitude;
kalman_speed = speed;
kalman_acceleration = acceleration;
update_vertical_pos();
+ update_speed();
+ update_accel();
}
}
}
}
+ public void set_ignitor_voltage(double[] voltage) {
+ this.ignitor_voltage = voltage;
+ }
public double time_since_boost() {
if (tick == AltosRecord.MISSING)
temp_gps = null;
}
+ public AltosState clone() {
+ AltosState s = new AltosState();
+ s.copy(this);
+ return s;
+ }
+
+
public void init (AltosRecord cur, AltosState prev_state) {
System.out.printf ("init\n");
set_kalman(cur.kalman_height, cur.kalman_speed, cur.kalman_acceleration);
- report_time = System.currentTimeMillis();
+ received_time = System.currentTimeMillis();
set_temperature(cur.temperature());
set_apogee_voltage(cur.drogue_voltage());
}
- public AltosState clone() {
- AltosState s = new AltosState();
- s.copy(this);
- return s;
- }
-
public AltosState(AltosRecord cur) {
init(cur, null);
}
init(cur, prev);
}
+
public AltosState () {
init();
}
}
public void update_state(AltosState state) {
+ state.set_serial(serial);
+ state.set_tick(tick);
+ state.set_rssi(rssi, status);
+ state.set_received_time(received_time);
}
final static int PKT_APPEND_STATUS_1_CRC_OK = (1 << 7);
final static int packet_type_location = 0x05;
final static int packet_type_satellite = 0x06;
final static int packet_type_companion = 0x07;
- final static int packet_type_MM_sensor = 0x08;
- final static int packet_type_MM_data = 0x09;
- final static int packet_type_Mini = 0x10;
+ final static int packet_type_mega_sensor = 0x08;
+ final static int packet_type_mega_data = 0x09;
+ final static int packet_type_metrum_sensor = 0x0a;
+ final static int packet_type_metrum_data = 0x0b;
+ final static int packet_type_mini = 0x10;
static AltosTelemetry parse_hex(String hex) throws ParseException, AltosCRCException {
AltosTelemetry telem = null;
/* length, data ..., rssi, status, checksum -- 4 bytes extra */
switch (bytes.length) {
case AltosLib.ao_telemetry_standard_len + 4:
- int type = AltosLib.uint8(bytes, 4 + 1);
-/*
- switch (type) {
- case packet_type_TM_sensor:
- case packet_type_Tm_sensor:
- case packet_type_Tn_sensor:
- telem = new AltosTelemetrySensor(bytes);
- break;
- case packet_type_configuration:
- telem = new AltosTelemetryConfiguration(bytes);
- break;
- case packet_type_location:
- telem = new AltosTelemetryLocation(bytes);
- break;
- case packet_type_satellite:
- telem = new AltosTelemetrySatellite(bytes);
- break;
- case packet_type_companion:
- telem = new AltosTelemetryCompanion(bytes);
- break;
- case packet_type_MM_sensor:
- telem = new AltosTelemetryMegaSensor(bytes);
- break;
- case packet_type_MM_data:
- telem = new AltosTelemetryMegaData(bytes);
- break;
- default:
- telem = new AltosTelemetryRaw(bytes);
- break;
- }
-*/
+ telem = AltosTelemetryStandard.parse_hex(bytes);
break;
case AltosLib.ao_telemetry_0_9_len + 4:
telem = new AltosTelemetryLegacy(bytes);
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+
+public class AltosTelemetryConfiguration extends AltosTelemetryStandard {
+ int device_type;
+ int flight;
+ int config_major;
+ int config_minor;
+ int apogee_delay;
+ int main_deploy;
+ int flight_log_max;
+ String callsign;
+ String version;
+
+ public AltosTelemetryConfiguration(int[] bytes) {
+ super(bytes);
+
+ device_type = uint8(5);
+ flight = uint16(6);
+ config_major = uint8(8);
+ config_minor = uint8(9);
+ apogee_delay = uint16(10);
+ main_deploy = uint16(12);
+ flight_log_max = uint16(14);
+ callsign = string(16, 8);
+ version = string(24, 8);
+ }
+
+ public void update_state(AltosState state) {
+ super.update_state(state);
+ state.set_device_type(device_type);
+ state.set_flight(flight);
+ state.set_config(config_major, config_minor, apogee_delay, main_deploy, flight_log_max);
+
+ state.set_callsign(callsign);
+ state.set_firmware_version(version);
+ }
+}
state.set_accel(accel);
if (kalman_height != AltosRecord.MISSING)
state.set_kalman(kalman_height, kalman_speed, kalman_acceleration);
- state.set_temperature(AltosEepromTM.thermometer_to_temperature(temp));
+ state.set_temperature(AltosConvert.thermometer_to_temperature(temp));
state.set_battery_voltage(AltosConvert.cc_battery_to_voltage(batt));
state.set_apogee_voltage(AltosConvert.cc_ignitor_to_voltage(apogee));
state.set_main_voltage(AltosConvert.cc_ignitor_to_voltage(main));
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+
+public class AltosTelemetryLocation extends AltosTelemetryStandard {
+ int flags;
+ int altitude;
+ int latitude;
+ int longitude;
+ int year;
+ int month;
+ int day;
+ int hour;
+ int minute;
+ int second;
+ int pdop;
+ int hdop;
+ int vdop;
+ int mode;
+ int ground_speed;
+ int climb_rate;
+ int course;
+
+ public AltosTelemetryLocation(int[] bytes) {
+ super(bytes);
+
+ flags = uint8(5);
+ altitude = int16(6);
+ latitude = uint32(8);
+ longitude = uint32(12);
+ year = uint8(16);
+ month = uint8(17);
+ day = uint8(18);
+ hour = uint8(19);
+ minute = uint8(20);
+ second = uint8(21);
+ pdop = uint8(22);
+ hdop = uint8(23);
+ vdop = uint8(24);
+ mode = uint8(25);
+ ground_speed = uint16(26);
+ climb_rate = int16(28);
+ course = uint8(30);
+ }
+
+ public void update_state(AltosState state) {
+ super.update_state(state);
+ AltosGPS gps = state.make_temp_gps();
+
+ gps.nsat = flags & 0xf;
+ gps.locked = (flags & (1 << 4)) != 0;
+ gps.connected = (flags & (1 << 5)) != 0;
+
+ if (gps.locked) {
+ gps.lat = latitude * 1.0e-7;
+ gps.lon = longitude * 1.0e-7;
+ gps.alt = altitude;
+ gps.year = 2000 + year;
+ gps.month = month;
+ gps.day = day;
+ gps.hour = hour;
+ gps.minute = minute;
+ gps.second = second;
+ gps.ground_speed = ground_speed * 1.0e-2;
+ gps.course = course * 2;
+ gps.climb_rate = climb_rate * 1.0e-2;
+ gps.hdop = hdop;
+ gps.vdop = vdop;
+ }
+ state.set_temp_gps();
+ }
+}
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+public class AltosTelemetryMegaData extends AltosTelemetryStandard {
+ int state;
+
+ int v_batt;
+ int v_pyro;
+ int sense[];
+
+ int ground_pres;
+ int ground_accel;
+ int accel_plus_g;
+ int accel_minus_g;
+
+ int acceleration;
+ int speed;
+ int height;
+
+ public AltosTelemetryMegaData(int[] bytes) {
+ super(bytes);
+
+ state = int8(5);
+
+ v_batt = int16(6);
+ v_pyro = int16(8);
+
+ sense = new int[6];
+
+ for (int i = 0; i < 6; i++) {
+ sense[i] = int8(10 + i) << 4;
+ sense[i] |= sense[i] >> 8;
+ }
+
+ ground_pres = int32(16);
+ ground_accel = int16(20);
+ accel_plus_g = int16(22);
+ accel_minus_g = int16(24);
+
+ acceleration = int16(26);
+ speed = int16(28);
+ height = int16(30);
+ }
+
+ public void update_state(AltosState state) {
+ super.update_state(state);
+
+ state.set_state(this.state);
+
+ state.set_battery_voltage(AltosConvert.mega_battery_voltage(v_batt));
+ state.set_pyro_voltage(AltosConvert.mega_pyro_voltage(v_pyro));
+
+ state.set_apogee_voltage(AltosConvert.mega_pyro_voltage(sense[4]));
+ state.set_main_voltage(AltosConvert.mega_pyro_voltage(sense[5]));
+
+ double voltages[] = new double[4];
+ for (int i = 0; i < 4; i++)
+ voltages[i] = AltosConvert.mega_pyro_voltage(sense[i]);
+
+ state.set_ignitor_voltage(voltages);
+
+ state.set_ground_accel(ground_accel);
+ state.set_ground_pressure(ground_pres);
+ state.set_accel_g(accel_plus_g, accel_minus_g);
+
+ state.set_kalman(height, speed/16.0, acceleration / 16.0);
+ }
+}
+
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+public class AltosTelemetryMegaSensor extends AltosTelemetryStandard {
+ int accel;
+ int pres;
+ int temp;
+
+ int accel_x;
+ int accel_y;
+ int accel_z;
+
+ int gyro_x;
+ int gyro_y;
+ int gyro_z;
+
+ int mag_x;
+ int mag_y;
+ int mag_z;
+
+ public AltosTelemetryMegaSensor(int[] bytes) {
+ super(bytes);
+
+ accel = int16(6);
+ pres = int32(8);
+ temp = int16(12);
+
+ accel_x = int16(14);
+ accel_y = int16(16);
+ accel_z = int16(18);
+
+ gyro_x = int16(20);
+ gyro_y = int16(22);
+ gyro_z = int16(24);
+
+ mag_x = int16(26);
+ mag_y = int16(28);
+ mag_z = int16(30);
+ }
+
+ public void update_state(AltosState state) {
+ super.update_state(state);
+
+ state.set_accel(accel);
+ state.set_pressure(pres);
+ state.set_temperature(temp / 100.0);
+
+ AltosIMU imu = new AltosIMU();
+
+ imu.accel_x = accel_x;
+ imu.accel_y = accel_y;
+ imu.accel_z = accel_z;
+
+ imu.gyro_x = gyro_x;
+ imu.gyro_y = gyro_y;
+ imu.gyro_z = gyro_z;
+
+ state.imu = imu;
+
+ AltosMag mag = new AltosMag();
+
+ mag.x = mag_x;
+ mag.y = mag_y;
+ mag.z = mag_z;
+
+ state.mag = mag;
+ }
+}
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+
+public class AltosTelemetryMetrumData extends AltosTelemetryStandard {
+
+ int ground_pres;
+ int ground_accel;
+ int accel_plus_g;
+ int accel_minus_g;
+
+ public AltosTelemetryMetrumData(int[] bytes) {
+ super(bytes);
+
+ ground_pres = int32(8);
+ ground_accel = int16(12);
+ accel_plus_g = int16(14);
+ accel_minus_g = int16(16);
+ }
+
+ public void update_state(AltosState state) {
+ state.set_ground_accel(ground_accel);
+ state.set_accel_g(accel_plus_g, accel_minus_g);
+ state.set_ground_pressure(ground_pres);
+ }
+}
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+
+public class AltosTelemetryMetrumSensor extends AltosTelemetryStandard {
+ int state;
+
+ int accel;
+ int pres;
+ int temp;
+
+ int acceleration;
+ int speed;
+ int height;
+
+ int v_batt;
+ int sense_a;
+ int sense_m;
+
+ public AltosTelemetryMetrumSensor(int[] bytes) {
+ super(bytes);
+
+ state = int8(5);
+ accel = int16(6);
+ pres = int32(8);
+ temp = int16(12);
+
+ acceleration = int16(14);
+ speed = int16(16);
+ height = int16(18);
+
+ v_batt = int16(20);
+ sense_a = int16(22);
+ sense_m = int16(24);
+ }
+
+ public void update_state(AltosState state) {
+ super.update_state(state);
+
+ state.set_state(this.state);
+
+ state.set_accel(accel);
+ state.set_ms5607(pres, temp);
+
+ state.set_kalman(height, speed/16.0, acceleration/16.0);
+
+ state.set_battery_voltage(AltosConvert.mega_battery_voltage(v_batt));
+
+ state.set_apogee_voltage(AltosConvert.mega_pyro_voltage(sense_a));
+ state.set_main_voltage(AltosConvert.mega_pyro_voltage(sense_m));
+ System.out.printf ("sense_a %d apogee voltage %g\n", sense_a, state.apogee_voltage);
+ }
+}
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+public class AltosTelemetryRaw extends AltosTelemetryStandard {
+ public AltosTelemetryRaw(int[] bytes) {
+ super(bytes);
+ }
+
+ public void update_state(AltosState state) {
+ super.update_state(state);
+ }
+}
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+public class AltosTelemetrySatellite extends AltosTelemetryStandard {
+ int channels;
+ AltosGPSSat[] sats;
+
+ public AltosTelemetrySatellite(int[] bytes) {
+ super(bytes);
+
+ channels = uint8(5);
+ if (channels > 12)
+ channels = 12;
+ if (channels == 0)
+ sats = null;
+ else {
+ sats = new AltosGPSSat[channels];
+ for (int i = 0; i < channels; i++) {
+ int svid = uint8(6 + i * 2 + 0);
+ int c_n_1 = uint8(6 + i * 2 + 1);
+ sats[i] = new AltosGPSSat(svid, c_n_1);
+ }
+ }
+ }
+
+ public void update_state(AltosState state) {
+ super.update_state(state);
+
+ AltosGPS gps = state.make_temp_gps();
+
+ gps.cc_gps_sat = sats;
+ state.set_temp_gps();
+ }
+}
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+
+public class AltosTelemetrySensor extends AltosTelemetryStandard {
+ int state;
+ int accel;
+ int pres;
+ int temp;
+ int v_batt;
+ int sense_d;
+ int sense_m;
+
+ int acceleration;
+ int speed;
+ int height;
+
+ int ground_accel;
+ int ground_pres;
+ int accel_plus_g;
+ int accel_minus_g;
+
+ public AltosTelemetrySensor(int[] bytes) {
+ super(bytes);
+ state = uint8(5);
+
+ accel = int16(6);
+ pres = int16(8);
+ temp = int16(10);
+ v_batt = int16(12);
+ sense_d = int16(14);
+ sense_m = int16(16);
+
+ acceleration = int16(18);
+ speed = int16(20);
+ height = int16(22);
+
+ ground_pres = int16(24);
+ ground_accel = int16(26);
+ accel_plus_g = int16(28);
+ accel_minus_g = int16(30);
+ }
+
+ public void update_state(AltosState state) {
+ super.update_state(state);
+
+ state.set_state(this.state);
+ if (type == packet_type_TM_sensor) {
+ state.set_ground_accel(ground_accel);
+ state.set_accel_g(accel_plus_g, accel_minus_g);
+ state.set_accel(accel);
+ }
+ state.set_ground_pressure(AltosConvert.barometer_to_pressure(ground_pres));
+ state.set_pressure(AltosConvert.barometer_to_pressure(pres));
+ state.set_temperature(AltosConvert.thermometer_to_temperature(temp));
+ state.set_battery_voltage(AltosConvert.cc_battery_to_voltage(v_batt));
+ if (type == packet_type_TM_sensor || type == packet_type_Tm_sensor) {
+ state.set_apogee_voltage(AltosConvert.cc_ignitor_to_voltage(sense_d));
+ state.set_main_voltage(AltosConvert.cc_ignitor_to_voltage(sense_m));
+ }
+
+ state.set_kalman(height, speed/16.0, acceleration / 16.0);
+ }
+}
--- /dev/null
+/*
+ * Copyright © 2011 Keith Packard <keithp@keithp.com>
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
+ */
+
+package org.altusmetrum.altoslib_1;
+
+public abstract class AltosTelemetryStandard extends AltosTelemetry {
+ int[] bytes;
+ int type;
+
+ public int int8(int off) {
+ return AltosLib.int8(bytes, off + 1);
+ }
+
+ public int uint8(int off) {
+ return AltosLib.uint8(bytes, off + 1);
+ }
+
+ public int int16(int off) {
+ return AltosLib.int16(bytes, off + 1);
+ }
+
+ public int uint16(int off) {
+ return AltosLib.uint16(bytes, off + 1);
+ }
+
+ public int uint32(int off) {
+ return AltosLib.uint32(bytes, off + 1);
+ }
+
+ public int int32(int off) {
+ return AltosLib.int32(bytes, off + 1);
+ }
+
+ public String string(int off, int l) {
+ return AltosLib.string(bytes, off + 1, l);
+ }
+
+ public static AltosTelemetry parse_hex(int[] bytes) {
+ int type = AltosLib.uint8(bytes, 4 + 1);
+
+ AltosTelemetry telem;
+ switch (type) {
+ case packet_type_TM_sensor:
+ case packet_type_Tm_sensor:
+ case packet_type_Tn_sensor:
+ telem = new AltosTelemetrySensor(bytes);
+ break;
+ case packet_type_configuration:
+ telem = new AltosTelemetryConfiguration(bytes);
+ break;
+ case packet_type_location:
+ telem = new AltosTelemetryLocation(bytes);
+ break;
+ case packet_type_satellite:
+ telem = new AltosTelemetrySatellite(bytes);
+ break;
+/*
+ case packet_type_companion:
+ telem = new AltosTelemetryCompanion(bytes);
+ break;
+*/
+ case packet_type_mega_sensor:
+ telem = new AltosTelemetryMegaSensor(bytes);
+ break;
+ case packet_type_mega_data:
+ telem = new AltosTelemetryMegaData(bytes);
+ break;
+ case packet_type_metrum_sensor:
+ telem = new AltosTelemetryMetrumSensor(bytes);
+ break;
+ case packet_type_metrum_data:
+ telem = new AltosTelemetryMetrumData(bytes);
+ break;
+ default:
+ telem = new AltosTelemetryRaw(bytes);
+ break;
+ }
+ return telem;
+ }
+
+ public AltosTelemetryStandard(int[] bytes) {
+ this.bytes = bytes;
+
+ serial = uint16(0);
+ tick = uint16(2);
+ type = uint8(4);
+ }
+
+ public void update_state(AltosState state) {
+ super.update_state(state);
+ }
+}
altoslibdir = $(datadir)/java
+record_files = \
+ AltosEepromRecord.java \
+ AltosEepromTeleScience.java \
+ AltosRecordCompanion.java \
+ AltosRecordIterable.java \
+ AltosRecord.java \
+ AltosRecordNone.java \
+ AltosRecordTM.java \
+ AltosRecordMM.java \
+ AltosRecordMini.java
+
altoslib_JAVA = \
+ $(record_files) \
AltosLib.java \
AltosConfigData.java \
AltosConfigValues.java \
AltosEepromIterable.java \
AltosEepromLog.java \
AltosEepromMega.java \
- AltosEepromMegaIterable.java \
- AltosEepromRecord.java \
- AltosEepromTeleScience.java \
+ AltosEepromMetrum2.java \
AltosEepromMini.java \
- AltosEepromOldIterable.java \
AltosFile.java \
AltosFlash.java \
AltosFlashListener.java \
AltosParse.java \
AltosPreferences.java \
AltosPreferencesBackend.java \
- AltosRecordCompanion.java \
- AltosRecordIterable.java \
- AltosRecord.java \
- AltosRecordNone.java \
- AltosRecordTM.java \
- AltosRecordMM.java \
- AltosRecordMini.java \
AltosReplayReader.java \
AltosRomconfig.java \
AltosSensorMM.java \
AltosStateIterable.java \
AltosStateUpdate.java \
AltosTelemetry.java \
+ AltosTelemetryConfiguration.java \
AltosTelemetryFile.java \
AltosTelemetryIterable.java \
AltosTelemetryLegacy.java \
+ AltosTelemetryLocation.java \
AltosTelemetryMap.java \
+ AltosTelemetryMegaSensor.java \
+ AltosTelemetryMegaData.java \
+ AltosTelemetryMetrumSensor.java \
+ AltosTelemetryMetrumData.java \
AltosTelemetryReader.java \
+ AltosTelemetryRaw.java \
+ AltosTelemetrySensor.java \
+ AltosTelemetrySatellite.java \
+ AltosTelemetryStandard.java \
AltosUnitsListener.java \
AltosMs5607.java \
AltosIMU.java \
class Lat extends AscentValue {
void show (AltosState state, AltosListenerState listener_state) {
- if (state.gps != null)
+ if (state.gps != null && state.gps.connected && state.gps.lat != AltosRecord.MISSING)
show(pos(state.gps.lat,"N", "S"));
else
show("???");
class Lon extends AscentValue {
void show (AltosState state, AltosListenerState listener_state) {
- if (state.gps != null)
+ if (state.gps != null && state.gps.connected && state.gps.lon != AltosRecord.MISSING)
show(pos(state.gps.lon,"E", "W"));
else
show("???");
class Lat extends DescentValue {
void show (AltosState state, AltosListenerState listener_state) {
- if (state.gps != null && state.gps.connected)
+ if (state.gps != null && state.gps.connected && state.gps.lat != AltosRecord.MISSING)
show(pos(state.gps.lat,"N", "S"));
else
show("???");
class Lon extends DescentValue {
void show (AltosState state, AltosListenerState listener_state) {
- if (state.gps != null && state.gps.connected)
+ if (state.gps != null && state.gps.connected && state.gps.lon != AltosRecord.MISSING)
show(pos(state.gps.lon,"W", "E"));
else
show("???");
*/
if (state.state >= Altos.ao_flight_drogue &&
(last ||
- System.currentTimeMillis() - state.report_time >= 15000 ||
+ System.currentTimeMillis() - state.received_time >= 15000 ||
state.state == Altos.ao_flight_landed))
{
if (Math.abs(state.speed) < 20 && state.height < 100)
Thread eeprom_thread;
AltosEepromMonitor monitor;
- int flight;
- int serial;
- int year, month, day;
boolean want_file;
FileWriter eeprom_file;
LinkedList<String> eeprom_pending;
ActionListener listener;
boolean success;
ParseException parse_exception;
- String extension;
+ AltosState state;
private void FlushPending() throws IOException {
for (String s : flights.config_data) {
private void CheckFile(boolean force) throws IOException {
if (eeprom_file != null)
return;
- if (force || (flight != 0 && want_file)) {
+ if (force || (state.flight != 0 && want_file)) {
AltosFile eeprom_name;
-
- if (extension == null)
- extension = "data";
- if (year != 0 && month != 0 && day != 0)
- eeprom_name = new AltosFile(year, month, day, serial, flight, extension);
- else
- eeprom_name = new AltosFile(serial, flight, extension);
+ AltosGPS gps = state.gps;
+
+ if (gps != null &&
+ gps.year != AltosRecord.MISSING &&
+ gps.month != AltosRecord.MISSING &&
+ gps.day != AltosRecord.MISSING)
+ {
+ eeprom_name = new AltosFile(gps.year, gps.month, gps.day,
+ state.serial, state.flight, "eeprom");
+ } else
+ eeprom_name = new AltosFile(state.serial, state.flight, "eeprom");
eeprom_file = new FileWriter(eeprom_name);
if (eeprom_file != null) {
}
}
- void Log(AltosEepromRecord r) throws IOException {
+ boolean done;
+ boolean start;
+
+ void LogEeprom(AltosEeprom r) throws IOException {
if (r.cmd != Altos.AO_LOG_INVALID) {
- String log_line = String.format("%c %4x %4x %4x\n",
- r.cmd, r.tick, r.a, r.b);
+ String line = r.string();
if (eeprom_file != null)
- eeprom_file.write(log_line);
+ eeprom_file.write(line);
else
- eeprom_pending.add(log_line);
+ eeprom_pending.add(line);
}
}
- void set_serial(int in_serial) {
- serial = in_serial;
- monitor.set_serial(serial);
- }
-
- void set_flight(int in_flight) {
- flight = in_flight;
- monitor.set_flight(flight);
- }
-
- boolean done;
- int state;
-
- void CaptureFull(AltosEepromChunk eechunk) throws IOException {
- boolean any_valid = false;
-
- extension = "eeprom";
- set_serial(flights.config_data.serial);
- for (int i = 0; i < AltosEepromChunk.chunk_size && !done; i += AltosEepromRecord.record_length) {
- try {
- AltosEepromRecord r = new AltosEepromRecord(eechunk, i);
- if (r.cmd == Altos.AO_LOG_FLIGHT)
- set_flight(r.b);
-
- /* Monitor state transitions to update display */
- if (r.cmd == Altos.AO_LOG_STATE && r.a <= Altos.ao_flight_landed) {
- state = r.a;
- if (state > Altos.ao_flight_pad)
- want_file = true;
- }
-
- if (r.cmd == Altos.AO_LOG_GPS_DATE) {
- year = 2000 + (r.a & 0xff);
- month = (r.a >> 8) & 0xff;
- day = (r.b & 0xff);
- want_file = true;
- }
- if (r.cmd == Altos.AO_LOG_STATE && r.a == Altos.ao_flight_landed)
- done = true;
- if (r.cmd != AltosLib.AO_LOG_INVALID)
- any_valid = true;
- Log(r);
- } catch (ParseException pe) {
- if (parse_exception == null)
- parse_exception = pe;
- }
- }
-
- if (!any_valid)
- done = true;
-
- CheckFile(false);
- }
-
- boolean start;
- int tiny_tick;
-
- void CaptureTiny (AltosEepromChunk eechunk) throws IOException {
+ void CaptureEeprom(AltosEepromChunk eechunk, int log_format) throws IOException {
boolean any_valid = false;
- extension = "eeprom";
- set_serial(flights.config_data.serial);
- for (int i = 0; i < eechunk.data.length && !done; i += 2) {
- int v = eechunk.data16(i);
- AltosEepromRecord r;
-
- if (i == 0 && start) {
- tiny_tick = 0;
- start = false;
- set_flight(v);
- r = new AltosEepromRecord(Altos.AO_LOG_FLIGHT, tiny_tick, 0, v);
- any_valid = true;
- } else {
- int s = v ^ 0x8000;
-
- if (Altos.ao_flight_startup <= s && s <= Altos.ao_flight_invalid) {
- state = s;
- r = new AltosEepromRecord(Altos.AO_LOG_STATE, tiny_tick, state, 0);
- if (state == Altos.ao_flight_landed)
- done = true;
- state = s;
- any_valid = true;
- } else {
- if (v != 0xffff)
- any_valid = true;
-
- r = new AltosEepromRecord(Altos.AO_LOG_PRESSURE, tiny_tick, 0, v);
-
- /*
- * The flight software records ascent data every 100ms, and descent
- * data every 1s.
- */
- if (state < Altos.ao_flight_drogue)
- tiny_tick += 10;
- else
- tiny_tick += 100;
- }
- }
- Log(r);
- }
- CheckFile(false);
- if (!any_valid)
- done = true;
- }
-
- void LogTeleScience(AltosEepromTeleScience r) throws IOException {
- if (r.type != Altos.AO_LOG_INVALID) {
- String log_line = String.format("%c %4x %4x %d %5d %5d %5d %5d %5d %5d %5d %5d %5d %5d %5d %5d\n",
- r.type, r.tick, r.tm_tick, r.tm_state,
- r.data[0], r.data[1], r.data[2], r.data[3],
- r.data[4], r.data[5], r.data[6], r.data[7],
- r.data[8], r.data[9], r.data[10], r.data[11]);
- if (eeprom_file != null)
- eeprom_file.write(log_line);
- else
- eeprom_pending.add(log_line);
- }
- }
-
- boolean telescience_start;
-
- void CaptureTeleScience (AltosEepromChunk eechunk) throws IOException {
- boolean any_valid = false;
-
- extension = "science";
- for (int i = 0; i < AltosEepromChunk.chunk_size && !done; i += AltosEepromTeleScience.record_length) {
- try {
- AltosEepromTeleScience r = new AltosEepromTeleScience(eechunk, i);
- if (r.type == AltosEepromTeleScience.AO_LOG_TELESCIENCE_START) {
- if (telescience_start) {
- done = true;
- break;
- }
- set_serial(r.data[0]);
- set_flight(r.data[1]);
- telescience_start = true;
- } else {
- if (!telescience_start)
- break;
- }
- state = r.tm_state;
- want_file =true;
- any_valid = true;
- LogTeleScience(r);
- } catch (ParseException pe) {
- if (parse_exception == null)
- parse_exception = pe;
- }
- }
+ int record_length = 8;
- CheckFile(false);
- if (!any_valid)
- done = true;
- }
+ state.set_serial(flights.config_data.serial);
- void LogMega(AltosEepromMega r) throws IOException {
- if (r.cmd != Altos.AO_LOG_INVALID) {
- String log_line = String.format("%c %4x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x\n",
- r.cmd, r.tick,
- r.data8[0], r.data8[1], r.data8[2], r.data8[3],
- r.data8[4], r.data8[5], r.data8[6], r.data8[7],
- r.data8[8], r.data8[9], r.data8[10], r.data8[11],
- r.data8[12], r.data8[13], r.data8[14], r.data8[15],
- r.data8[16], r.data8[17], r.data8[18], r.data8[19],
- r.data8[20], r.data8[21], r.data8[22], r.data8[23],
- r.data8[24], r.data8[25], r.data8[26], r.data8[27]);
- if (eeprom_file != null)
- eeprom_file.write(log_line);
- else
- eeprom_pending.add(log_line);
- }
- }
+ for (int i = 0; i < AltosEepromChunk.chunk_size && !done; i += record_length) {
+ AltosEeprom r = eechunk.eeprom(i, log_format);
- void CaptureMega(AltosEepromChunk eechunk) throws IOException {
- boolean any_valid = false;
+ record_length = r.record_length();
- extension = "mega";
- set_serial(flights.config_data.serial);
- for (int i = 0; i < AltosEepromChunk.chunk_size && !done; i += AltosEepromMega.record_length) {
- try {
- AltosEepromMega r = new AltosEepromMega(eechunk, i);
- if (r.cmd == Altos.AO_LOG_FLIGHT)
- set_flight(r.data16(0));
-
- /* Monitor state transitions to update display */
- if (r.cmd == Altos.AO_LOG_STATE && r.data16(0) <= Altos.ao_flight_landed) {
- state = r.data16(0);
- if (state > Altos.ao_flight_pad)
- want_file = true;
- }
+ r.update_state(state);
- if (r.cmd == Altos.AO_LOG_GPS_TIME) {
- year = 2000 + r.data8(14);
- month = r.data8(15);
- day = r.data8(16);
+ /* Monitor state transitions to update display */
+ if (state.state != AltosLib.ao_flight_invalid &&
+ state.state <= AltosLib.ao_flight_landed)
+ {
+ if (state.state > Altos.ao_flight_pad)
want_file = true;
- }
-
- if (r.cmd == Altos.AO_LOG_STATE && r.data16(0) == Altos.ao_flight_landed)
+ if (state.state == AltosLib.ao_flight_landed)
done = true;
- if (r.cmd != AltosLib.AO_LOG_INVALID)
- any_valid = true;
- LogMega(r);
- } catch (ParseException pe) {
- if (parse_exception == null)
- parse_exception = pe;
}
- }
- if (!any_valid)
- done = true;
- CheckFile(false);
- }
-
- void LogMini(AltosEepromMini r) throws IOException {
- if (r.cmd != Altos.AO_LOG_INVALID) {
- String log_line = String.format("%c %4x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x %2x\n",
- r.cmd, r.tick,
- r.data8[0], r.data8[1], r.data8[2], r.data8[3],
- r.data8[4], r.data8[5], r.data8[6], r.data8[7],
- r.data8[8], r.data8[9], r.data8[10], r.data8[11]);
- if (eeprom_file != null)
- eeprom_file.write(log_line);
- else
- eeprom_pending.add(log_line);
- }
- }
+ if (state.gps != null)
+ want_file = true;
- void CaptureMini(AltosEepromChunk eechunk) throws IOException {
- boolean any_valid = false;
-
- extension = "mini";
- set_serial(flights.config_data.serial);
- for (int i = 0; i < AltosEepromChunk.chunk_size && !done; i += AltosEepromMini.record_length) {
- try {
- AltosEepromMini r = new AltosEepromMini(eechunk, i);
- if (r.cmd == Altos.AO_LOG_FLIGHT)
- set_flight(r.data16(0));
-
- /* Monitor state transitions to update display */
- if (r.cmd == Altos.AO_LOG_STATE && r.data16(0) <= Altos.ao_flight_landed) {
- state = r.data16(0);
- if (state > Altos.ao_flight_pad)
- want_file = true;
- }
-
- if (r.cmd == Altos.AO_LOG_STATE && r.data16(0) == Altos.ao_flight_landed)
- done = true;
+ if (r.valid) {
any_valid = true;
- LogMini(r);
- } catch (ParseException pe) {
- if (parse_exception == null)
- parse_exception = pe;
+ LogEeprom(r);
}
}
if (!any_valid)
CheckFile(false);
}
- void CaptureTelemetry(AltosEepromChunk eechunk) throws IOException {
-
- }
-
void CaptureLog(AltosEepromLog log) throws IOException, InterruptedException, TimeoutException {
int block, state_block = 0;
int log_format = flights.config_data.log_format;
- state = 0;
+ state = new AltosState();
+
done = false;
start = true;
throw new IOException("no serial number found");
/* Reset per-capture variables */
- flight = 0;
- year = 0;
- month = 0;
- day = 0;
want_file = false;
eeprom_file = null;
eeprom_pending = new LinkedList<String>();
/* Set serial number in the monitor dialog window */
/* Now scan the eeprom, reading blocks of data and converting to .eeprom file form */
- state = 0; state_block = log.start_block;
+ state_block = log.start_block;
for (block = log.start_block; !done && block < log.end_block; block++) {
- monitor.set_value(AltosLib.state_name(state), state, block - state_block, block - log.start_block);
+ monitor.set_value(state.state_name(),
+ state.state,
+ block - state_block,
+ block - log.start_block);
AltosEepromChunk eechunk = new AltosEepromChunk(serial_line, block, block == log.start_block);
}
}
- switch (log_format) {
- case AltosLib.AO_LOG_FORMAT_FULL:
- extension = "eeprom";
- CaptureFull(eechunk);
- break;
- case AltosLib.AO_LOG_FORMAT_TINY:
- extension = "eeprom";
- CaptureTiny(eechunk);
- break;
- case AltosLib.AO_LOG_FORMAT_TELEMETRY:
- extension = "telem";
- CaptureTelemetry(eechunk);
- break;
- case AltosLib.AO_LOG_FORMAT_TELESCIENCE:
- extension = "science";
- CaptureTeleScience(eechunk);
- break;
- case AltosLib.AO_LOG_FORMAT_TELEMEGA:
- extension = "mega";
- CaptureMega(eechunk);
- break;
- case AltosLib.AO_LOG_FORMAT_EASYMINI:
- case AltosLib.AO_LOG_FORMAT_TELEMINI:
- extension = "eeprom";
- CaptureMini(eechunk);
- break;
- }
+ CaptureEeprom (eechunk, log_format);
}
CheckFile(true);
if (eeprom_file != null) {
class LastPacket extends FlightValue {
void show(AltosState state, AltosListenerState listener_state) {
- long secs = (System.currentTimeMillis() - state.report_time + 500) / 1000;
+ long secs = (System.currentTimeMillis() - state.received_time + 500) / 1000;
value.setText(String.format("%d", secs));
}
public LastPacket(GridBagLayout layout, int x) {
status_update.saved_state = state;
if (state == null)
- state = new AltosState(new AltosRecord());
+ state = new AltosState();
pad.show(state, listener_state);
public void show(AltosState state, AltosListenerState listener_state) {
status_update.saved_state = state;
- try {
+// try {
pad.show(state, listener_state);
flightStatus.show(state, listener_state);
flightInfo.show(state, listener_state);
- } catch (Exception e) {
- System.out.print("Show exception" + e);
- }
+// } catch (Exception e) {
+// System.out.print("Show exception " + e);
+// }
}
public void update(final AltosState state, final AltosListenerState listener_state) {
else
info_add_row(1, "GPS", " missing");
info_add_row(1, "Satellites", "%6d", state.gps.nsat);
- info_add_deg(1, "Latitude", state.gps.lat, 'N', 'S');
- info_add_deg(1, "Longitude", state.gps.lon, 'E', 'W');
- info_add_row(1, "GPS altitude", "%6d", state.gps.alt);
- info_add_row(1, "GPS height", "%6.0f", state.gps_height);
+ if (state.gps.lat != AltosRecord.MISSING)
+ info_add_deg(1, "Latitude", state.gps.lat, 'N', 'S');
+ if (state.gps.lon != AltosRecord.MISSING)
+ info_add_deg(1, "Longitude", state.gps.lon, 'E', 'W');
+ if (state.gps.alt != AltosRecord.MISSING)
+ info_add_row(1, "GPS altitude", "%8.1f", state.gps.alt);
+ if (state.gps_height != AltosRecord.MISSING)
+ info_add_row(1, "GPS height", "%8.1f", state.gps_height);
/* The SkyTraq GPS doesn't report these values */
/*
info_add_deg(1, "Pad longitude", state.pad_lon, 'E', 'W');
info_add_row(1, "Pad GPS alt", "%6.0f m", state.pad_alt);
}
- info_add_row(1, "GPS date", "%04d-%02d-%02d",
- state.gps.year,
- state.gps.month,
- state.gps.day);
- info_add_row(1, "GPS time", " %02d:%02d:%02d",
- state.gps.hour,
- state.gps.minute,
- state.gps.second);
+ if (state.gps.year != AltosRecord.MISSING)
+ info_add_row(1, "GPS date", "%04d-%02d-%02d",
+ state.gps.year,
+ state.gps.month,
+ state.gps.day);
+ if (state.gps.hour != AltosRecord.MISSING)
+ info_add_row(1, "GPS time", " %02d:%02d:%02d",
+ state.gps.hour,
+ state.gps.minute,
+ state.gps.second);
//int nsat_vis = 0;
int c;
class Lat extends LandedValue {
void show (AltosState state, AltosListenerState listener_state) {
- if (state.gps != null && state.gps.connected)
+ show();
+ if (state.gps != null && state.gps.connected && state.gps.lat != AltosRecord.MISSING)
show(pos(state.gps.lat,"N", "S"));
else
show("???");
class Lon extends LandedValue {
void show (AltosState state, AltosListenerState listener_state) {
show();
- if (state.gps != null && state.gps.connected)
+ if (state.gps != null && state.gps.connected && state.gps.lon != AltosRecord.MISSING)
show(pos(state.gps.lon,"E", "W"));
else
show("???");
class PadLat extends LaunchValue {
void show (AltosState state, AltosListenerState listener_state) {
- if (state == null || state.gps == null) {
- hide();
- } else {
- if (state.state < AltosLib.ao_flight_pad) {
- show(pos(state.gps.lat,"N", "S"));
- set_label("Latitude");
- } else {
- show(pos(state.pad_lat,"N", "S"));
- set_label("Pad Latitude");
+ double lat = AltosRecord.MISSING;
+ String label = null;
+
+ if (state != null) {
+ if (state.state < AltosLib.ao_flight_pad && state.gps != null && state.gps.lat != AltosRecord.MISSING) {
+ lat = state.gps.lat;
+ label = "Latitude";
+ } else {
+ lat = state.pad_lat;
+ label = "Pad Latitude";
}
}
+ if (lat != AltosRecord.MISSING) {
+ show(pos(lat,"E", "W"));
+ set_label(label);
+ } else
+ hide();
}
public PadLat (GridBagLayout layout, int y) {
super (layout, y, "Pad Latitude");
class PadLon extends LaunchValue {
void show (AltosState state, AltosListenerState listener_state) {
- if (state == null || state.gps == null) {
- hide();
- } else {
- if (state.state < AltosLib.ao_flight_pad) {
- show(pos(state.gps.lon,"E", "W"));
- set_label("Longitude");
- } else {
- show(pos(state.pad_lon,"E", "W"));
- set_label("Pad Longitude");
+ double lon = AltosRecord.MISSING;
+ String label = null;
+
+ if (state != null) {
+ if (state.state < AltosLib.ao_flight_pad && state.gps != null && state.gps.lon != AltosRecord.MISSING) {
+ lon = state.gps.lon;
+ label = "Longitude";
+ } else {
+ lon = state.pad_lon;
+ label = "Pad Longitude";
}
}
+ if (lon != AltosRecord.MISSING) {
+ show(pos(lon,"E", "W"));
+ set_label(label);
+ } else
+ hide();
}
public PadLon (GridBagLayout layout, int y) {
super (layout, y, "Pad Longitude");
class PadAlt extends LaunchValue {
void show (AltosState state, AltosListenerState listener_state) {
- if (state == null)
- hide();
- else {
- if (state.state < AltosLib.ao_flight_pad && state.gps != null) {
- show("%4.0f m", state.gps.alt);
- set_label("Altitude");
+ double alt = AltosRecord.MISSING;
+ String label = null;
+
+ if (state != null) {
+ if (state.state < AltosLib.ao_flight_pad && state.gps != null && state.gps.alt != AltosRecord.MISSING) {
+ alt = state.gps.alt;
+ label = "Altitude";
} else {
- if (state.pad_alt == AltosRecord.MISSING)
- hide();
- else {
- show("%4.0f m", state.pad_alt);
- set_label("Pad Altitude");
- }
+ alt = state.pad_alt;
+ label = "Pad Altitude";
}
}
+ if (alt != AltosRecord.MISSING) {
+ show("%4.0f m", state.gps.alt);
+ set_label(label);
+ } else
+ hide();
}
public PadAlt (GridBagLayout layout, int y) {
super (layout, y, "Pad Altitude");
FileInputStream in;
in = new FileInputStream(file);
- if (file.getName().endsWith("eeprom"))
- return new AltosEepromFile(in);
- else
+ if (file.getName().endsWith("telem"))
return new AltosTelemetryFile(in);
+ else
+ return new AltosEepromFile(in);
} catch (FileNotFoundException fe) {
System.out.printf("%s\n", fe.getMessage());
return null;
System.out.printf("Failed to open file '%s'\n", file);
return null;
}
- if (file.getName().endsWith("eeprom")) {
- return new AltosEepromFile(in);
- } else {
+ if (file.getName().endsWith("telem"))
return new AltosTelemetryFile(in);
- }
+ else
+ return new AltosEepromFile(in);
}
static AltosReplayReader replay_file(File file) {
System.out.printf ("process cat\n");
for (AltosState state : eef) {
+ System.out.printf ("tick %d state %d height %g\n",
+ state.tick, state.state, state.height);
if ((state.set & AltosState.set_gps) != 0)
System.out.printf ("time %g lat %g lon %g alt %g\n",
state.time_since_boost(),
uint16_t flight; /* 4 */
int16_t ground_accel; /* 6 */
uint32_t ground_pres; /* 8 */
- } flight; /* 12 */
+ uint32_t ground_temp; /* 12 */
+ } flight; /* 16 */
/* AO_LOG_STATE */
struct {
uint16_t state; /* 4 */