summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/drivers/ao_pad.c128
-rw-r--r--src/telefire-v0.1/ao_pins.h15
-rw-r--r--src/telefire-v0.2/ao_pins.h17
-rw-r--r--src/telefireeight-v1.0/ao_pins.h17
-rw-r--r--src/telefiretwo-v0.1/ao_pins.h13
5 files changed, 118 insertions, 72 deletions
diff --git a/src/drivers/ao_pad.c b/src/drivers/ao_pad.c
index b0ec2161..ed749d1c 100644
--- a/src/drivers/ao_pad.c
+++ b/src/drivers/ao_pad.c
@@ -153,13 +153,36 @@ ao_pad_run(void)
#define AO_PAD_ARM_SIREN_INTERVAL 200
-#ifndef AO_PYRO_R_PYRO_SENSE
-#define AO_PYRO_R_PYRO_SENSE 100
-#define AO_PYRO_R_SENSE_GND 27
-#define AO_FIRE_R_POWER_FET 100
-#define AO_FIRE_R_FET_SENSE 100
-#define AO_FIRE_R_SENSE_GND 27
-#endif
+/* Resistor values needed for various voltage test ratios:
+ *
+ * Net names involved:
+ *
+ * V_BATT Battery power, after the initial power switch
+ * V_PYRO Pyro power, after the pyro power switch (and initial power switch)
+ * PYRO_SENSE ADC input to sense V_PYRO voltage
+ * BATT_SENSE ADC input to sense V_BATT voltage
+ * IGNITER FET output to pad (the other pad lead hooks to V_PYRO)
+ * IGNITER_SENSE ADC input to sense igniter voltage
+ *
+ * AO_PAD_R_V_BATT_BATT_SENSE Resistor from battery rail to battery sense input
+ * AO_PAD_R_BATT_SENSE_GND Resistor from battery sense input to ground
+ *
+ * AO_PAD_R_V_BATT_V_PYRO Resistor from battery rail to pyro rail
+ * AO_PAD_R_V_PYRO_PYRO_SENSE Resistor from pyro rail to pyro sense input
+ * AO_PAD_R_PYRO_SENSE_GND Resistor from pyro sense input to ground
+ *
+ * AO_PAD_R_V_PYRO_IGNITER Optional resistors from pyro rail to FET igniter output
+ * AO_PAD_R_IGNITER_IGNITER_SENSE Resistors from FET igniter output to igniter sense ADC inputs
+ * AO_PAD_R_IGNITER_SENSE_GND Resistors from igniter sense ADC inputs to ground
+ */
+
+int16_t
+ao_pad_decivolt(int16_t adc, int16_t r_plus, int16_t r_minus)
+{
+ int32_t mul = (int32_t) AO_ADC_REFERENCE_DV * (r_plus + r_minus);
+ int32_t div = (int32_t) AO_ADC_MAX * r_minus;
+ return ((int32_t) adc * mul + mul/2) / div;
+}
static void
ao_pad_monitor(void)
@@ -174,6 +197,7 @@ ao_pad_monitor(void)
sample = ao_data_head;
for (;;) {
__pdata int16_t pyro;
+
ao_arch_critical(
while (sample == ao_data_head)
ao_sleep((void *) DATA_TO_XDATA(&ao_data_head));
@@ -183,28 +207,18 @@ ao_pad_monitor(void)
packet = &ao_data_ring[sample];
sample = ao_data_ring_next(sample);
- pyro = packet->adc.pyro;
+ /* Reply battery voltage */
+ query.battery = ao_pad_decivolt(packet->adc.batt, AO_PAD_R_V_BATT_BATT_SENSE, AO_PAD_R_BATT_SENSE_GND);
-#define VOLTS_TO_PYRO(x) ((int16_t) ((x) * ((1.0 * AO_PYRO_R_SENSE_GND) / \
- (1.0 * (AO_PYRO_R_SENSE_GND + AO_PYRO_R_PYRO_SENSE)) / 3.3 * AO_ADC_MAX)))
+ /* Current pyro voltage */
+ pyro = ao_pad_decivolt(packet->adc.pyro,
+ AO_PAD_R_V_PYRO_PYRO_SENSE,
+ AO_PAD_R_PYRO_SENSE_GND);
-
-#define VOLTS_TO_FIRE(x) ((int16_t) ((x) * ((1.0 * AO_FIRE_R_SENSE_GND) / \
- (1.0 * (AO_FIRE_R_SENSE_GND + AO_FIRE_R_FET_SENSE)) / 3.3 * AO_ADC_MAX)))
-
- /* convert ADC value to voltage in tenths, then add .2 for the diode drop */
- query.battery = (packet->adc.batt + 96) / 192 + 2;
cur = 0;
- if (pyro > VOLTS_TO_PYRO(10)) {
+ if (pyro > query.battery * 7 / 8) {
query.arm_status = AO_PAD_ARM_STATUS_ARMED;
cur |= AO_LED_ARMED;
-#if AO_FIRE_R_POWER_FET
- } else if (pyro > VOLTS_TO_PYRO(5)) {
- if ((ao_time() % 100) < 50)
- cur |= AO_LED_ARMED;
- query.arm_status = AO_PAD_ARM_STATUS_UNKNOWN;
- arm_beep_time = 0;
-#endif
} else {
query.arm_status = AO_PAD_ARM_STATUS_DISARMED;
arm_beep_time = 0;
@@ -217,54 +231,50 @@ ao_pad_monitor(void)
cur |= AO_LED_GREEN;
for (c = 0; c < AO_PAD_NUM; c++) {
- int16_t sense = packet->adc.sense[c];
+ int16_t sense = ao_pad_decivolt(packet->adc.sense[c],
+ AO_PAD_R_IGNITER_IGNITER_SENSE,
+ AO_PAD_R_IGNITER_SENSE_GND);
uint8_t status = AO_PAD_IGNITER_STATUS_UNKNOWN;
/*
- * pyro is run through a divider, so pyro = v_pyro * 27 / 127 ~= v_pyro / 20
- * v_pyro = pyro * 127 / 27
- *
- * v_pyro \
- * 100k igniter
- * output /
- * 100k \
- * sense relay
- * 27k /
- * gnd ---
+ * Here's the resistor stack on each
+ * igniter channel. Note that
+ * AO_PAD_R_V_PYRO_IGNITER is optional
*
- * v_pyro \
- * 200k igniter
- * output /
- * 200k \
- * sense relay
- * 22k /
- * gnd ---
+ * v_pyro \
+ * AO_PAD_R_V_PYRO_IGNITER igniter
+ * output /
+ * AO_PAD_R_IGNITER_IGNITER_SENSE \
+ * sense relay
+ * AO_PAD_R_IGNITER_SENSE_GND /
+ * gnd ---
*
- * If the relay is closed, then sense will be 0
- * If no igniter is present, then sense will be v_pyro * 27k/227k = pyro * 127 / 227 ~= pyro/2
- * If igniter is present, then sense will be v_pyro * 27k/127k ~= v_pyro / 20 = pyro
*/
-#if AO_FIRE_R_POWER_FET
+#ifdef AO_PAD_R_V_PYRO_IGNITER
if (sense <= pyro / 8) {
+ /* close to zero → relay is closed */
status = AO_PAD_IGNITER_STATUS_NO_IGNITER_RELAY_CLOSED;
if ((ao_time() % 100) < 50)
cur |= AO_LED_CONTINUITY(c);
- } else
- if (pyro / 8 * 3 <= sense && sense <= pyro / 8 * 5)
- status = AO_PAD_IGNITER_STATUS_NO_IGNITER_RELAY_OPEN;
- else if (pyro / 8 * 7 <= sense) {
- status = AO_PAD_IGNITER_STATUS_GOOD_IGNITER_RELAY_OPEN;
- cur |= AO_LED_CONTINUITY(c);
- }
-#else
- if (sense >= pyro / 8 * 5) {
- status = AO_PAD_IGNITER_STATUS_GOOD_IGNITER_RELAY_OPEN;
- cur |= AO_LED_CONTINUITY(c);
- } else {
- status = AO_PAD_IGNITER_STATUS_NO_IGNITER_RELAY_OPEN;
}
+ else
#endif
+ {
+ if (sense >= (pyro * 7) / 8) {
+
+ /* sense close to pyro voltage; igniter is good
+ */
+ status = AO_PAD_IGNITER_STATUS_GOOD_IGNITER_RELAY_OPEN;
+ cur |= AO_LED_CONTINUITY(c);
+ } else {
+
+ /* relay not shorted (if we can tell),
+ * and igniter not obviously present
+ */
+ status = AO_PAD_IGNITER_STATUS_NO_IGNITER_RELAY_OPEN;
+ }
+ }
query.igniter_status[c] = status;
}
if (cur != prev) {
diff --git a/src/telefire-v0.1/ao_pins.h b/src/telefire-v0.1/ao_pins.h
index ee0ca716..8266589e 100644
--- a/src/telefire-v0.1/ao_pins.h
+++ b/src/telefire-v0.1/ao_pins.h
@@ -100,10 +100,17 @@
#define AO_STROBE_PIN 1
#define AO_STROBE P1_1
-/* test these values with real igniters */
-#define AO_PAD_RELAY_CLOSED 3524
-#define AO_PAD_NO_IGNITER 16904
-#define AO_PAD_GOOD_IGNITER 22514
+#define AO_ADC_REFERENCE_DV 33
+#define AO_PAD_R_V_BATT_BATT_SENSE 100
+#define AO_PAD_R_BATT_SENSE_GND 27
+
+#define AO_PAD_R_V_BATT_V_PYRO 100
+#define AO_PAD_R_V_PYRO_PYRO_SENSE 100
+#define AO_PAD_R_PYRO_SENSE_GND 27
+
+#define AO_PAD_R_V_PYRO_IGNITER 100
+#define AO_PAD_R_IGNITER_IGNITER_SENSE 100
+#define AO_PAD_R_IGNITER_SENSE_GND 27
#define AO_PAD_ADC_PYRO 4
#define AO_PAD_ADC_BATT 5
diff --git a/src/telefire-v0.2/ao_pins.h b/src/telefire-v0.2/ao_pins.h
index 4faeb65f..65f5bdcc 100644
--- a/src/telefire-v0.2/ao_pins.h
+++ b/src/telefire-v0.2/ao_pins.h
@@ -111,15 +111,24 @@
#define AO_STROBE P2_4
/* test these values with real igniters */
-#define AO_PAD_RELAY_CLOSED 3524
-#define AO_PAD_NO_IGNITER 16904
-#define AO_PAD_GOOD_IGNITER 22514
-
#define AO_PAD_ADC_PYRO 4
#define AO_PAD_ADC_BATT 5
#define AO_ADC_FIRST_PIN 0
+#define AO_ADC_REFERENCE_DV 33
+#define AO_PAD_R_V_BATT_BATT_SENSE 100
+#define AO_PAD_R_BATT_SENSE_GND 27
+
+#define AO_PAD_R_V_BATT_V_PYRO 100
+#define AO_PAD_R_V_PYRO_PYRO_SENSE 100
+#define AO_PAD_R_PYRO_SENSE_GND 27
+
+#define AO_PAD_R_V_PYRO_IGNITER 100
+#define AO_PAD_R_IGNITER_IGNITER_SENSE 100
+#define AO_PAD_R_IGNITER_SENSE_GND 27
+
+
struct ao_adc {
int16_t sense[AO_PAD_NUM];
int16_t pyro;
diff --git a/src/telefireeight-v1.0/ao_pins.h b/src/telefireeight-v1.0/ao_pins.h
index 271d2cbe..15e1fa11 100644
--- a/src/telefireeight-v1.0/ao_pins.h
+++ b/src/telefireeight-v1.0/ao_pins.h
@@ -295,16 +295,23 @@
#define AO_ADC_SQ9 AO_ADC_PYRO
#define AO_ADC_SQ10 AO_ADC_BATT
+#define AO_ADC_REFERENCE_DV 33
+
#define AO_ADC_RCC_AHBENR ((1 << STM_RCC_AHBENR_GPIOAEN) | \
(1 << STM_RCC_AHBENR_GPIOBEN) | \
(1 << STM_RCC_AHBENR_GPIOCEN))
-#define AO_PYRO_R_PYRO_SENSE 200
-#define AO_PYRO_R_SENSE_GND 22
-#define AO_FIRE_R_POWER_FET 0
-#define AO_FIRE_R_FET_SENSE 200
-#define AO_FIRE_R_SENSE_GND 22
+#define AO_PAD_R_V_BATT_BATT_SENSE 200
+#define AO_PAD_R_BATT_SENSE_GND 22
+
+#define AO_PAD_R_V_BATT_V_PYRO 200
+#define AO_PAD_R_V_PYRO_PYRO_SENSE 200
+#define AO_PAD_R_PYRO_SENSE_GND 22
+
+#undef AO_PAD_R_V_PYRO_IGNITER
+#define AO_PAD_R_IGNITER_IGNITER_SENSE 200
+#define AO_PAD_R_IGNITER_SENSE_GND 22
#define HAS_ADC_TEMP 0
diff --git a/src/telefiretwo-v0.1/ao_pins.h b/src/telefiretwo-v0.1/ao_pins.h
index 1e5c0d09..dedd0fad 100644
--- a/src/telefiretwo-v0.1/ao_pins.h
+++ b/src/telefiretwo-v0.1/ao_pins.h
@@ -191,6 +191,19 @@
#define HAS_ADC_TEMP 0
+#define AO_ADC_REFERENCE_DV 33
+
+#define AO_PAD_R_V_BATT_BATT_SENSE 200
+#define AO_PAD_R_BATT_SENSE_GND 22
+
+#define AO_PAD_R_V_BATT_V_PYRO 200
+#define AO_PAD_R_V_PYRO_PYRO_SENSE 200
+#define AO_PAD_R_PYRO_SENSE_GND 22
+
+#undef AO_PAD_R_V_PYRO_IGNITER
+#define AO_PAD_R_IGNITER_IGNITER_SENSE 200
+#define AO_PAD_R_IGNITER_SENSE_GND 22
+
struct ao_adc {
int16_t sense[AO_PAD_NUM];
int16_t pyro;