Arianna autonomous DAQ firmware

Dependencies:   mbed SDFileSystemFilinfo AriSnProtocol NetServicesMin AriSnComm MODSERIAL PowerControlClkPatch DS1820OW

Committer:
uci1
Date:
Tue Nov 17 04:36:52 2015 +0000
Revision:
97:9f3fe603e8b5
Parent:
84:80b15993944e
Child:
98:ce72ef143b9b
S14 with conf name. Update clock set at trig start/stop. no interface chip. safety nets.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
uci1 0:664899e0b988 1 #include "mbed.h"
uci1 56:0bba0ef15697 2
uci1 56:0bba0ef15697 3 const uint32_t gPowerOnTime( time(0) );
uci1 56:0bba0ef15697 4
uci1 22:f957c4f840ad 5 // start a watchdog as soon as possible
uci1 22:f957c4f840ad 6 #include "Watchdog.h"
uci1 22:f957c4f840ad 7 Watchdog::SnKickStarter gKickStarter(WDFAILSAFE);
uci1 0:664899e0b988 8
uci1 84:80b15993944e 9 // CHIPBOARD is defined in SnPreCompOptions.h
uci1 56:0bba0ef15697 10
uci1 0:664899e0b988 11 #include <stdint.h>
uci1 37:ff95e7070f26 12 #include "SnConstants.h"
uci1 37:ff95e7070f26 13
uci1 67:ec999336fcd1 14 #ifndef USE_INTERFACE_CHIP
uci1 67:ec999336fcd1 15 // to avoid calling the interface chip,
uci1 67:ec999336fcd1 16 // the mac address is hard coded (ugh!)
uci1 67:ec999336fcd1 17 extern "C" void mbed_mac_address(char * mac) {
uci1 67:ec999336fcd1 18 #ifdef DEBUG
uci1 67:ec999336fcd1 19 printf("calling MY mbed_mac_address\r\n");
uci1 67:ec999336fcd1 20 #endif
uci1 67:ec999336fcd1 21 memmove(mac, kDefaultMacAdress, sizeof(kDefaultMacAdress));
uci1 67:ec999336fcd1 22 };
uci1 67:ec999336fcd1 23 #endif
uci1 67:ec999336fcd1 24
uci1 84:80b15993944e 25 #ifdef DEBUG
uci1 84:80b15993944e 26 #include "SnMemMonitor.h"
uci1 84:80b15993944e 27 #endif
uci1 84:80b15993944e 28
uci1 0:664899e0b988 29 #include "SDFileSystem.h"
uci1 15:f2569d8e4176 30 #ifdef USE_MODSERIAL
uci1 41:d6f5e2f09e07 31 #define MODSERIAL_RX_BUF_SIZE 512
uci1 41:d6f5e2f09e07 32 #define MODSERIAL_TX_BUF_SIZE 512
uci1 0:664899e0b988 33 #include "MODSERIAL.h"
uci1 56:0bba0ef15697 34 #endif // USE_MODSERIAL
uci1 21:ce51bb0ba4a5 35 #include "FATDirHandle.h"
uci1 21:ce51bb0ba4a5 36 #include "EthernetPowerControl.h"
uci1 0:664899e0b988 37 #include "SnBitUtils.h"
uci1 0:664899e0b988 38 #include "SnSDUtils.h"
uci1 0:664899e0b988 39 #include "SnConfigFrame.h"
uci1 0:664899e0b988 40 #include "SnEventFrame.h"
uci1 0:664899e0b988 41 #include "SnStatusFrame.h"
uci1 2:e67f7c158087 42 #include "SnHeaderFrame.h"
uci1 22:f957c4f840ad 43 #include "SnHeartbeatFrame.h"
uci1 40:1324da35afd4 44 #include "SnClockSetFrame.h"
uci1 41:d6f5e2f09e07 45 #include "SnSignalStrengthFrame.h"
uci1 0:664899e0b988 46 #include "SnCommWin.h"
uci1 41:d6f5e2f09e07 47 #ifdef ENABLE_AFAR_COMM
uci1 18:55f1581f2ee4 48 #ifdef USE_ETH_INTERFACE
uci1 7:079617408fec 49 #include "SnCommAfarTCP.h"
uci1 18:55f1581f2ee4 50 #else
uci1 37:ff95e7070f26 51 #include "SnCommWinAfar.h"
uci1 28:484943132bb0 52 #ifdef ENABLE_AFAR_TWITTER
uci1 37:ff95e7070f26 53 #include "SnCommWinTwitter.h"
uci1 41:d6f5e2f09e07 54 #endif // ENABLE_AFAR_TWITTER
uci1 41:d6f5e2f09e07 55 #endif // USE_ETH_INTERFACE
uci1 41:d6f5e2f09e07 56 #endif // ENABLE_AFAR_COMM
uci1 41:d6f5e2f09e07 57 #ifdef ENABLE_USB_COMM
uci1 41:d6f5e2f09e07 58 #include "SnCommWinUsb.h"
uci1 56:0bba0ef15697 59 #endif // ENABLE_USB_COMM
uci1 41:d6f5e2f09e07 60 #ifdef ENABLE_SBD_COMM
uci1 37:ff95e7070f26 61 #include "SnCommWinSBD.h"
uci1 56:0bba0ef15697 62 #endif // ENABLE_SBD_COMM
uci1 41:d6f5e2f09e07 63 //#include "SnBase64.h"
uci1 8:95a325df1f6b 64 #ifdef USE_RTOS_TIMER
uci1 8:95a325df1f6b 65 #include "RtosTimer.h"
uci1 56:0bba0ef15697 66 #endif // USE_RTOS_TIMER
uci1 56:0bba0ef15697 67 #include "DS1820.h"
uci1 84:80b15993944e 68 #include "SnL1SingleFreqSupp.h"
uci1 0:664899e0b988 69
uci1 40:1324da35afd4 70 extern "C" void mbed_reset();
uci1 31:b5bd3b189150 71
uci1 0:664899e0b988 72 //
uci1 0:664899e0b988 73 // MBED PINS (ordered by number)
uci1 0:664899e0b988 74 //
uci1 0:664899e0b988 75 // leds (for debugging)
uci1 67:ec999336fcd1 76 DigitalOut led1(LED1,1);
uci1 67:ec999336fcd1 77 DigitalOut led2(LED2,1);
uci1 67:ec999336fcd1 78 DigitalOut led3(LED3,1);
uci1 67:ec999336fcd1 79 DigitalOut led4(LED4,1);
uci1 56:0bba0ef15697 80
uci1 56:0bba0ef15697 81 // Set up power pins - Note that it's Zero for "on" in ATWD2013, but high for "on" in SST2014
uci1 56:0bba0ef15697 82 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 83 DigitalOut PIN_turn_on_system(p17,1); // this turns off the system
uci1 56:0bba0ef15697 84 DigitalOut PIN_turn_on_amps(p25,1); // this turns off the amps
uci1 56:0bba0ef15697 85 #else
uci1 56:0bba0ef15697 86 DigitalOut PIN_turn_on_system(p17,0); // this turns off the system
uci1 56:0bba0ef15697 87 DigitalOut PIN_turn_on_amps(p25,0); // this turns off the amps
uci1 56:0bba0ef15697 88 #endif // ATWD4CH
uci1 15:f2569d8e4176 89 // SD card select
uci1 56:0bba0ef15697 90 DigitalOut PIN_SD_CS(p8,0);
uci1 56:0bba0ef15697 91 #if CHIPBOARD==ATWD4CH
uci1 0:664899e0b988 92 // Activate/select chip by falling edge
uci1 56:0bba0ef15697 93 DigitalOut PIN_ADC_CS(p9,0);
uci1 0:664899e0b988 94 // clock signal to activate PLA setting
uci1 56:0bba0ef15697 95 DigitalOut PIN_PLA_cs(p10,0);
uci1 56:0bba0ef15697 96 #else
uci1 56:0bba0ef15697 97 I2C PIN_i2c(p9, p10);
uci1 56:0bba0ef15697 98 #endif // ATWD4CH
uci1 0:664899e0b988 99 // To force a trigger
uci1 56:0bba0ef15697 100 DigitalOut PIN_forceTrigger(p11,0); //modification
uci1 0:664899e0b988 101 // To suppress thermal triggers
uci1 56:0bba0ef15697 102 DigitalOut PIN_enableThermTrig(p12,0);
uci1 56:0bba0ef15697 103 #if CHIPBOARD==ATWD4CH
uci1 0:664899e0b988 104 // Restart clock on all FPGAs.
uci1 56:0bba0ef15697 105 DigitalOut PIN_DoNotRestartAllClocks(p13,0);
uci1 56:0bba0ef15697 106 #else
uci1 56:0bba0ef15697 107 DigitalOut PIN_ResetChips(p13,0);
uci1 56:0bba0ef15697 108 #endif // ATWD4CH
uci1 56:0bba0ef15697 109 #if CHIPBOARD==ATWD4CH
uci1 0:664899e0b988 110 // This tells the DFPGAs to store the data on motherboard FPGA and
uci1 0:664899e0b988 111 // read it out.
uci1 56:0bba0ef15697 112 DigitalIn PIN_a_sf_clk(p14);
uci1 0:664899e0b988 113 DigitalIn PIN_rst_a_sf(p15);
uci1 56:0bba0ef15697 114 #else
uci1 56:0bba0ef15697 115 DigitalIn PIN_dataReady(p14); // when triggered data is stored in the mb FPGA and ready for readout by mbed
uci1 56:0bba0ef15697 116 #endif // ATWD4CH
uci1 1:e392595b4b76 117 // afar power
uci1 56:0bba0ef15697 118 DigitalOut PIN_afar_power(p16,0);
uci1 4:a91682e19d6b 119 // batter voltage/current measurement
uci1 4:a91682e19d6b 120 AnalogIn PIN_vADC1(p19);
uci1 4:a91682e19d6b 121 AnalogIn PIN_vADC2(p18);
uci1 56:0bba0ef15697 122 #if CHIPBOARD==ATWD4CH
uci1 0:664899e0b988 123 // Lock daughter card registeres (during data readout).
uci1 56:0bba0ef15697 124 DigitalOut PIN_lockRegisters(p20,0);
uci1 56:0bba0ef15697 125 #else
uci1 56:0bba0ef15697 126 DigitalOut PIN_readingData(p20,0);
uci1 56:0bba0ef15697 127 #endif // ATWD4CH
uci1 1:e392595b4b76 128 // iridium (SBD) power
uci1 56:0bba0ef15697 129 DigitalOut PIN_iridSbd_power(p21,0);
uci1 0:664899e0b988 130 // Majority logic pins
uci1 56:0bba0ef15697 131 DigitalOut PIN_MajLogHiBit(p22,0);
uci1 56:0bba0ef15697 132 DigitalOut PIN_MajLogLoBit(p23,0);
uci1 56:0bba0ef15697 133 // To launch a heartbeat pulse
uci1 56:0bba0ef15697 134 DigitalOut PIN_heartbeat(p24,0);
uci1 56:0bba0ef15697 135 #if CHIPBOARD==ATWD4CH
uci1 0:664899e0b988 136 // Tell FPGA to be ready to accept DAC values
uci1 56:0bba0ef15697 137 DigitalOut PIN_start_fpga(p26,0);
uci1 56:0bba0ef15697 138 #else
uci1 56:0bba0ef15697 139 DigitalIn PIN_unused26(p26);
uci1 56:0bba0ef15697 140 #endif // ATWD4CH
uci1 56:0bba0ef15697 141 #if CHIPBOARD==ATWD4CH
uci1 0:664899e0b988 142 // Two bits to the select the daughter card for readout
uci1 56:0bba0ef15697 143 DigitalOut PIN_selCardHiBit(p29,0);
uci1 56:0bba0ef15697 144 DigitalOut PIN_selCardLoBit(p30,0);
uci1 56:0bba0ef15697 145 #else
uci1 56:0bba0ef15697 146 DigitalOut PIN_dualOrSingleThresholds(p29, 1); // 1 = dual (hi AND lo thresh crossings)
uci1 56:0bba0ef15697 147 DigitalOut PIN_differentialTrigSignal(p30, 1); // 1 = chip sends one trigger signal per channel with reduced noise, 0 = chip sends each comparator signal separately
uci1 56:0bba0ef15697 148 #endif // ATWD4CH
uci1 0:664899e0b988 149 // Setup SPI pins
uci1 0:664899e0b988 150 SPI PIN_spi( p5, p6, p7 );
uci1 3:24c5f0f50bf1 151
uci1 56:0bba0ef15697 152 #if CHIPBOARD==SST4CH
uci1 56:0bba0ef15697 153 PinName gThermPinName(p15);
uci1 56:0bba0ef15697 154 DS1820 PIN_therm(gThermPinName, gThermPinName, false); // be default, on external power
uci1 56:0bba0ef15697 155 #endif
uci1 41:d6f5e2f09e07 156
uci1 41:d6f5e2f09e07 157 // we have to do this shit because Serial and MODSERIAL don't have virtual functions
uci1 41:d6f5e2f09e07 158 // so calling, e.g. readable from a Serial* will call Serial::readable instead of MODSERIAL::readable
uci1 41:d6f5e2f09e07 159 // and the comms will wait forever
uci1 15:f2569d8e4176 160 #ifdef USE_MODSERIAL
uci1 41:d6f5e2f09e07 161 #define MAIN_SERIALTYPE AjK::MODSERIAL
uci1 15:f2569d8e4176 162 #else
uci1 41:d6f5e2f09e07 163 #define MAIN_SERIALTYPE Serial
uci1 56:0bba0ef15697 164 #endif // USE_MODSERIAL
uci1 41:d6f5e2f09e07 165
uci1 41:d6f5e2f09e07 166 // this needs to be first in case some other global uses a print statement
uci1 41:d6f5e2f09e07 167 static MAIN_SERIALTYPE gCpu( USBTX, USBRX ); // defined here so it might be used for debugging output
uci1 41:d6f5e2f09e07 168
uci1 41:d6f5e2f09e07 169 static MAIN_SERIALTYPE gSBDport(p28, p27,
uci1 16:744ce85aede2 170 #ifdef USE_MODSERIAL
uci1 41:d6f5e2f09e07 171 MODSERIAL_TX_BUF_SIZE, MODSERIAL_RX_BUF_SIZE,
uci1 56:0bba0ef15697 172 #endif // USE_MODSERIAL
uci1 41:d6f5e2f09e07 173 "sbd");
uci1 41:d6f5e2f09e07 174
uci1 56:0bba0ef15697 175 // The SD card
uci1 21:ce51bb0ba4a5 176 static SDFileSystem sd(p5, p6, p7, p8, SnSDUtils::kSDdir+1); // no leading '/'
uci1 67:ec999336fcd1 177
uci1 67:ec999336fcd1 178 // local file system is still created even if USE_INTERFACE_CHIP is not defined
uci1 67:ec999336fcd1 179 // this is done to allow the mbed to be reprogrammed remotely
uci1 25:57b2627fe756 180 static LocalFileSystem local((SnCommWin::kLocalDir)+1); // no leading '/'
uci1 0:664899e0b988 181
uci1 0:664899e0b988 182 //
uci1 0:664899e0b988 183 // fwd declare fcns
uci1 0:664899e0b988 184 //
uci1 0:664899e0b988 185 void ReadAllRegisters();
uci1 0:664899e0b988 186 void ReadRegister(const uint8_t chan, int16_t* dev);
uci1 22:f957c4f840ad 187 void SaveHeartbeat();
uci1 0:664899e0b988 188 void SaveEvent(const int32_t etms);
uci1 0:664899e0b988 189 void WaitTrigAndSendClock();
uci1 1:e392595b4b76 190 void SetConfigAndMakeOutputFile();
uci1 40:1324da35afd4 191 SnCommWin::ECommWinResult OpenCommWin(const bool forceReconfig=false,
uci1 40:1324da35afd4 192 const bool isStartupWin=false);
uci1 3:24c5f0f50bf1 193 void MakeOutputFile(const bool stopRunning=false);
uci1 84:80b15993944e 194 bool IsPowerAllowedFor(const bool isCommWin,
uci1 84:80b15993944e 195 const uint8_t devicesInUse,
uci1 84:80b15993944e 196 const SnConfigFrame::EDatPackBit b);
uci1 84:80b15993944e 197 void SetPower(const bool isCommWin,
uci1 84:80b15993944e 198 const uint8_t devicesInUse);
uci1 84:80b15993944e 199 void CheckPower(const bool isCommWin,
uci1 84:80b15993944e 200 const bool saveReading=true,
uci1 84:80b15993944e 201 const uint8_t devicesInUse=
uci1 84:80b15993944e 202 SnConfigFrame::kIrid |
uci1 84:80b15993944e 203 SnConfigFrame::kAfar);
uci1 84:80b15993944e 204 void CheckTemp();
uci1 84:80b15993944e 205 void UpdateTemperature();
uci1 84:80b15993944e 206 bool AreCardsPowered(const bool checkPin);
uci1 84:80b15993944e 207 void GetAvePowerReading();
uci1 84:80b15993944e 208 #if CHIPBOARD==SST4CH
uci1 84:80b15993944e 209 void InitTempProbe();
uci1 84:80b15993944e 210 #endif
uci1 84:80b15993944e 211 void ResetCountersClearEvt();
uci1 84:80b15993944e 212 void CalcRate(const uint32_t numtrgs,
uci1 84:80b15993944e 213 const double tottime_ms,
uci1 84:80b15993944e 214 float& rate);
uci1 84:80b15993944e 215 void GetRates(float& thmrate, float& evtrate);
uci1 84:80b15993944e 216 void AddToRate(const double dt, const bool isThm);
uci1 84:80b15993944e 217 bool IsSeqComplete();
uci1 8:95a325df1f6b 218 void procForceTrigger();
uci1 8:95a325df1f6b 219 void procHeartbeat();
uci1 8:95a325df1f6b 220 void procPowerCheck();
uci1 56:0bba0ef15697 221 void procTempCheck();
uci1 8:95a325df1f6b 222 void procCommWin();
uci1 40:1324da35afd4 223 #ifdef USE_RTOS
uci1 8:95a325df1f6b 224 void procForceTrigger(void const *) { return procForceTrigger(); }
uci1 8:95a325df1f6b 225 void procHeartbeat(void const *) { return procHeartbeat(); }
uci1 8:95a325df1f6b 226 void procPowerCheck(void const *) { return procPowerCheck(); }
uci1 8:95a325df1f6b 227 void procCommWin(void const *) { return procCommWin(); }
uci1 56:0bba0ef15697 228 void procTempCheck(void const *) { return procTempCheck(); }
uci1 56:0bba0ef15697 229 #endif // USE_RTOS
uci1 0:664899e0b988 230
uci1 0:664899e0b988 231 //
uci1 0:664899e0b988 232 // globals
uci1 0:664899e0b988 233 //
uci1 0:664899e0b988 234 // readout objs
uci1 8:95a325df1f6b 235 // TODO: use RtosTimer instead of Ticker?
uci1 40:1324da35afd4 236 #ifdef USE_RTOS
uci1 8:95a325df1f6b 237 static rtos::RtosTimer* gForceTicker;
uci1 8:95a325df1f6b 238 static rtos::RtosTimer* gHeartbeatTicker;
uci1 8:95a325df1f6b 239 static rtos::RtosTimer* gCommWinTicker;
uci1 8:95a325df1f6b 240 static rtos::RtosTimer* gPowerCheckTicker;
uci1 56:0bba0ef15697 241 static rtos::RtosTimer* gTempCheckTicker;
uci1 8:95a325df1f6b 242 #else
uci1 0:664899e0b988 243 static Ticker gForceTicker;
uci1 3:24c5f0f50bf1 244 static Ticker gHeartbeatTicker;
uci1 1:e392595b4b76 245 static Ticker gCommWinTicker;
uci1 8:95a325df1f6b 246 static Ticker gPowerCheckTicker;
uci1 56:0bba0ef15697 247 static Ticker gTempCheckTicker;
uci1 56:0bba0ef15697 248 #endif // USE_RTOS
uci1 40:1324da35afd4 249 static Timer gAllTrgTimer;
uci1 40:1324da35afd4 250 static Timer gThmTrgTimer;
uci1 16:744ce85aede2 251 static Timer gAdcToMBtimer;
uci1 67:ec999336fcd1 252
uci1 84:80b15993944e 253 static Timer gSinceClkSet;
uci1 41:d6f5e2f09e07 254 static SnClockSetFrame gClkSet;
uci1 41:d6f5e2f09e07 255 static SnSignalStrengthFrame gSigStr;
uci1 31:b5bd3b189150 256 #ifdef DISABLE_CONFIG_SAFETYNETS
uci1 31:b5bd3b189150 257 static SnConfigFrame gConf(false);
uci1 31:b5bd3b189150 258 #else
uci1 0:664899e0b988 259 static SnConfigFrame gConf;
uci1 56:0bba0ef15697 260 #endif // DISABLE_CONFIG_SAFETYNETS
uci1 0:664899e0b988 261 static SnEventFrame gEvent;
uci1 84:80b15993944e 262 //static SnEventFrame gLastEvent;
uci1 8:95a325df1f6b 263 static SnPowerFrame gPower;
uci1 56:0bba0ef15697 264 static SnTempFrame gTemperature;
uci1 0:664899e0b988 265 // parameters
uci1 21:ce51bb0ba4a5 266 static bool gCardsPowered = false;
uci1 0:664899e0b988 267 static bool gFirstEvt = true;
uci1 56:0bba0ef15697 268 static volatile bool gReadingOut = false; // if data is being read from the FPGA
uci1 15:f2569d8e4176 269 static volatile bool gCommWinOpen = false; // if it's open
uci1 1:e392595b4b76 270 static volatile bool gOpenCommWin = false; // if it should be opened
uci1 8:95a325df1f6b 271 static volatile bool gCheckPower = false; // if it should be checked
uci1 56:0bba0ef15697 272 static volatile bool gCheckTemp = false; // if it should be checked
uci1 8:95a325df1f6b 273 static uint32_t gPowNum = 0;
uci1 8:95a325df1f6b 274 static uint32_t gEvtNum = 0; // num of evt written
uci1 84:80b15993944e 275 static volatile bool gForcedTrig = false; // forced trigger bit
uci1 84:80b15993944e 276 static volatile bool gAdcToMBflag = false; // flag in case getting the ADC values took too long
uci1 84:80b15993944e 277 //static uint32_t gTrgNum[kNumTrgs] = {0}; // num of this type of trg received
uci1 84:80b15993944e 278 static uint32_t gNumThmTrigs = 0; // number of thermal triggers counted
uci1 84:80b15993944e 279 static uint32_t gNumFrcTrigs = 0; // number of forced triggers counted
uci1 84:80b15993944e 280 static uint8_t gL1ScaledownCount = 0; // write an event every X L1 failures
uci1 0:664899e0b988 281 // i/o
uci1 21:ce51bb0ba4a5 282 static time_t gLastCommWin = 0; // time
uci1 22:f957c4f840ad 283 static uint32_t gCommWinChecks = 0;
uci1 22:f957c4f840ad 284 static uint32_t gNcommWinChecks = 0;
uci1 40:1324da35afd4 285 static uint16_t gConsecCommFails = 0;
uci1 22:f957c4f840ad 286 // heartbeat
uci1 84:80b15993944e 287 static SnHeartbeatFrame gHrtbt;
uci1 22:f957c4f840ad 288 static time_t gLastHrtbt = 0;
uci1 23:ccf39298f205 289 static volatile bool gHrtbtFired = false;
uci1 22:f957c4f840ad 290 static uint32_t gHrtbtNum = 0;
uci1 22:f957c4f840ad 291 // rates
uci1 22:f957c4f840ad 292 static double gThmDtSum = 0; // sum of all time diffs between thermal trigs
uci1 22:f957c4f840ad 293 static double gEvtDtSum = 0; // sum of all time diffs between events
uci1 22:f957c4f840ad 294 static uint32_t gThmNumDt = 0; // number of thermal trig time diffs added up
uci1 22:f957c4f840ad 295 static uint32_t gEvtNumDt = 0; // number of event time diffs added up
uci1 10:3c93db1cfb12 296 // this should be bigger than anything that will actually be used
uci1 40:1324da35afd4 297 static const uint32_t gBufSize=SnStatusFrame::kMaxSizeOf + (2u*SnHeaderFrame::kMaxSizeOf) + SnPowerFrame::kMaxSizeOf
uci1 61:42cbfc02e0e0 298 + SnEventFrame::kMaxSizeOf // (this is redundant and could be removed if mem is sparse)
uci1 84:80b15993944e 299 + 256; // breathing room
uci1 3:24c5f0f50bf1 300 static char gGenBuf[gBufSize]; // must be big enough for event or status or config!
uci1 11:de443350ec4a 301 static SnCommWin* gComms[kNcomms] = { 0 }; // order => priority. afar uses RTOS, and must be made inside main
uci1 28:484943132bb0 302 #if defined(ENABLE_AFAR_TWITTER) && defined(ENABLE_AFAR_COMM)
uci1 28:484943132bb0 303 static SnCommAfarNetIfTwitter* gTwit = 0;
uci1 28:484943132bb0 304 #endif
uci1 84:80b15993944e 305 static float gChanFFT[kNsamps] = { 0 }; // only one chan at a time to save RAM
uci1 84:80b15993944e 306 // status update data cache and flags
uci1 84:80b15993944e 307 static SnClockSetFrame gStTrgStartClk;
uci1 84:80b15993944e 308 static SnClockSetFrame gStTrgStopClk;
uci1 84:80b15993944e 309 static SnPowerFrame gStPower;
uci1 84:80b15993944e 310 static SnTempFrame gStTemperature;
uci1 84:80b15993944e 311 static volatile bool gStNewPower(false);
uci1 84:80b15993944e 312 static volatile bool gStNewEvent(false);
uci1 84:80b15993944e 313 static volatile bool gStNewHeartbeat(false);
uci1 84:80b15993944e 314 static volatile bool gStNewTemperature(false);
uci1 0:664899e0b988 315
uci1 84:80b15993944e 316 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 317 Timer gProfiler;
uci1 84:80b15993944e 318 #endif
uci1 67:ec999336fcd1 319
uci1 0:664899e0b988 320 void procForceTrigger() {
uci1 0:664899e0b988 321 if (gReadingOut==false && gCommWinOpen==false) {
uci1 15:f2569d8e4176 322 led3=!led3;
uci1 12:d472f9811262 323 #ifdef DEBUG
uci1 8:95a325df1f6b 324 printf("proc force\r\n");
uci1 56:0bba0ef15697 325 #if CHIPBOARD==ATWD4CH
uci1 47:fbe956b10a91 326 printf("PIN_forceTrigge=%d, PIN_turn_on_system=%d, "
uci1 47:fbe956b10a91 327 "PIN_a_sf_clk=%d\r\n",
uci1 47:fbe956b10a91 328 PIN_forceTrigger.read(), PIN_turn_on_system.read(),
uci1 47:fbe956b10a91 329 PIN_a_sf_clk.read());
uci1 56:0bba0ef15697 330 #else
uci1 56:0bba0ef15697 331 printf("PIN_forceTrigge=%d, PIN_turn_on_system=%d, "
uci1 56:0bba0ef15697 332 "PIN_dataReady=%d\r\n",
uci1 56:0bba0ef15697 333 PIN_forceTrigger.read(), PIN_turn_on_system.read(),
uci1 56:0bba0ef15697 334 PIN_dataReady.read());
uci1 56:0bba0ef15697 335 #endif // ATWD4CH
uci1 12:d472f9811262 336 #endif
uci1 84:80b15993944e 337 gForcedTrig = true;
uci1 84:80b15993944e 338 ++gNumFrcTrigs;
uci1 84:80b15993944e 339 // ++(gTrgNum[kFrcTrg]);
uci1 84:80b15993944e 340 // gEvent.SetTrgBit(kFrcTrg);
uci1 84:80b15993944e 341 // gEvent.SetTrgNum(++(gTrgNum[kFrcTrg]));
uci1 23:ccf39298f205 342 //PIN_forceTrigger = 0;
uci1 0:664899e0b988 343 PIN_forceTrigger = 1; // force a trigger
uci1 21:ce51bb0ba4a5 344 PIN_forceTrigger = 0;
uci1 0:664899e0b988 345 }
uci1 0:664899e0b988 346 }
uci1 0:664899e0b988 347
uci1 3:24c5f0f50bf1 348 void procHeartbeat() {
uci1 3:24c5f0f50bf1 349 if (gReadingOut==false && gCommWinOpen==false) {
uci1 12:d472f9811262 350 #ifdef DEBUG
uci1 8:95a325df1f6b 351 printf("proc heartbeat\r\n");
uci1 12:d472f9811262 352 #endif
uci1 67:ec999336fcd1 353 led3=!led3;
uci1 23:ccf39298f205 354 //PIN_heartbeat = 0;
uci1 3:24c5f0f50bf1 355 PIN_heartbeat = 1; // heartbeat pulse
uci1 3:24c5f0f50bf1 356 PIN_heartbeat = 0;
uci1 22:f957c4f840ad 357 gLastHrtbt = time(0);
uci1 22:f957c4f840ad 358 gHrtbtFired = true;
uci1 22:f957c4f840ad 359 ++gHrtbtNum;
uci1 3:24c5f0f50bf1 360 }
uci1 3:24c5f0f50bf1 361 }
uci1 3:24c5f0f50bf1 362
uci1 8:95a325df1f6b 363 void procPowerCheck() {
uci1 12:d472f9811262 364 #ifdef DEBUG
uci1 8:95a325df1f6b 365 printf("proc power\r\n");
uci1 12:d472f9811262 366 #endif
uci1 67:ec999336fcd1 367 led3=!led3;
uci1 8:95a325df1f6b 368 gCheckPower=true;
uci1 8:95a325df1f6b 369 }
uci1 8:95a325df1f6b 370
uci1 56:0bba0ef15697 371 void procTempCheck() {
uci1 56:0bba0ef15697 372 #ifdef DEBUG
uci1 56:0bba0ef15697 373 printf("proc temp check\r\n");
uci1 56:0bba0ef15697 374 #endif
uci1 67:ec999336fcd1 375 led3=!led3;
uci1 56:0bba0ef15697 376 gCheckTemp=true;
uci1 56:0bba0ef15697 377 }
uci1 56:0bba0ef15697 378
uci1 0:664899e0b988 379 void procCommWin() {
uci1 22:f957c4f840ad 380 ++gCommWinChecks;
uci1 27:efc4d654b139 381 //if ( (time(0) - gLastCommWin) > gConf.GetCommWinPeriod() ) {
uci1 22:f957c4f840ad 382 #ifdef DEBUG
uci1 27:efc4d654b139 383 printf("<><><><><><> gCommWinChecks=%u, gNcommWinChecks=%u\r\n",
uci1 27:efc4d654b139 384 gCommWinChecks, gNcommWinChecks);
uci1 22:f957c4f840ad 385 #endif
uci1 27:efc4d654b139 386 if ( gCommWinChecks >= gNcommWinChecks ) {
uci1 12:d472f9811262 387 #ifdef DEBUG
uci1 27:efc4d654b139 388 printf("proc comm win.\r\n");
uci1 12:d472f9811262 389 #endif
uci1 27:efc4d654b139 390 led3=!led3;
uci1 27:efc4d654b139 391 gOpenCommWin = true;
uci1 0:664899e0b988 392 }
uci1 0:664899e0b988 393 }
uci1 0:664899e0b988 394
uci1 21:ce51bb0ba4a5 395 bool AreCardsPowered(const bool checkPin) {
uci1 21:ce51bb0ba4a5 396 #ifdef DEBUG
uci1 56:0bba0ef15697 397 printf("acp call: PIN_turn_on_system=%d, gCardsPowered=%d\r\n",
uci1 21:ce51bb0ba4a5 398 PIN_turn_on_system.read(), gCardsPowered);
uci1 21:ce51bb0ba4a5 399 #endif
uci1 21:ce51bb0ba4a5 400 if (checkPin) {
uci1 56:0bba0ef15697 401 #if CHIPBOARD==ATWD4CH
uci1 21:ce51bb0ba4a5 402 gCardsPowered = (PIN_turn_on_system.read()==0);
uci1 56:0bba0ef15697 403 #else
uci1 56:0bba0ef15697 404 gCardsPowered = (PIN_turn_on_system.read()==1);
uci1 56:0bba0ef15697 405 #endif // ATWD4CH
uci1 16:744ce85aede2 406 }
uci1 56:0bba0ef15697 407 #ifdef DEBUG
uci1 56:0bba0ef15697 408 printf("acp return: PIN_turn_on_system=%d, gCardsPowered=%d\r\n",
uci1 56:0bba0ef15697 409 PIN_turn_on_system.read(), gCardsPowered);
uci1 56:0bba0ef15697 410 #endif
uci1 21:ce51bb0ba4a5 411 return gCardsPowered;
uci1 8:95a325df1f6b 412 }
uci1 0:664899e0b988 413
uci1 8:95a325df1f6b 414 void GetAvePowerReading() {
uci1 8:95a325df1f6b 415 // use one measurement as the assumed average
uci1 8:95a325df1f6b 416 // in order to reduce computational errors
uci1 8:95a325df1f6b 417 int32_t v1, v2;
uci1 8:95a325df1f6b 418 const uint16_t aaveV1 = PIN_vADC1.read_u16();
uci1 8:95a325df1f6b 419 const uint16_t aaveV2 = PIN_vADC2.read_u16();
uci1 8:95a325df1f6b 420 float n=0, ave1=0, ave2=0, rms1=0, rms2=0;
uci1 56:0bba0ef15697 421 for (uint16_t i=0; i<kNvoltsAve; ++i) {
uci1 8:95a325df1f6b 422 v1 = PIN_vADC1.read_u16() - aaveV1;
uci1 8:95a325df1f6b 423 v2 = PIN_vADC2.read_u16() - aaveV2;
uci1 8:95a325df1f6b 424 n += 1;
uci1 8:95a325df1f6b 425 ave1 += v1;
uci1 8:95a325df1f6b 426 rms1 += v1*v1;
uci1 8:95a325df1f6b 427 ave2 += v2;
uci1 8:95a325df1f6b 428 rms2 += v2*v2;
uci1 8:95a325df1f6b 429 }
uci1 8:95a325df1f6b 430 rms1 -= (ave1*ave1)/n;
uci1 8:95a325df1f6b 431 rms2 -= (ave2*ave2)/n;
uci1 8:95a325df1f6b 432 rms1 /= n-1;
uci1 8:95a325df1f6b 433 rms2 /= n-1;
uci1 9:a1a39573dd43 434 rms1 = sqrt(rms1);
uci1 9:a1a39573dd43 435 rms2 = sqrt(rms2);
uci1 8:95a325df1f6b 436 ave1 /= n;
uci1 8:95a325df1f6b 437 ave2 /= n;
uci1 8:95a325df1f6b 438 ave1 += aaveV1;
uci1 8:95a325df1f6b 439 ave2 += aaveV2;
uci1 8:95a325df1f6b 440 gPower.Set(ave1, ave2, rms1, rms2, time(0));
uci1 56:0bba0ef15697 441 #ifdef DEBUG
uci1 56:0bba0ef15697 442 printf("ave power. v1=%g, v2=%g, r1=%g, r2=%g, t=%u\r\n",
uci1 56:0bba0ef15697 443 gPower.GetAveV1(), gPower.GetAveV2(),
uci1 56:0bba0ef15697 444 gPower.GetRmsV1(), gPower.GetRmsV2(), gPower.GetTime());
uci1 56:0bba0ef15697 445 #endif
uci1 8:95a325df1f6b 446 }
uci1 0:664899e0b988 447
uci1 56:0bba0ef15697 448 #if CHIPBOARD==SST4CH
uci1 56:0bba0ef15697 449 void InitTempProbe() {
uci1 56:0bba0ef15697 450 #ifdef DEBUG
uci1 56:0bba0ef15697 451 printf("setting temp probe power mode\r\n");
uci1 56:0bba0ef15697 452 #endif
uci1 56:0bba0ef15697 453 // set power style for temperature probe
uci1 56:0bba0ef15697 454 PIN_therm.set_use_parasite_power( gConf.IsTempUsingParasitePower() );
uci1 56:0bba0ef15697 455 // setup the probe
uci1 56:0bba0ef15697 456 #ifdef DEBUG
uci1 56:0bba0ef15697 457 printf("calling therm probe search_ROM_setup\r\n");
uci1 56:0bba0ef15697 458 #endif
uci1 56:0bba0ef15697 459 PIN_therm.search_ROM_setup();
uci1 56:0bba0ef15697 460 const int tsr = PIN_therm.search_ROM(); // this is necessary for some reason
uci1 56:0bba0ef15697 461 #ifdef DEBUG
uci1 56:0bba0ef15697 462 printf("search ROM = %d\r\n", tsr);
uci1 56:0bba0ef15697 463 #endif
uci1 56:0bba0ef15697 464 }
uci1 56:0bba0ef15697 465 #endif
uci1 56:0bba0ef15697 466
uci1 56:0bba0ef15697 467 void UpdateTemperature() {
uci1 56:0bba0ef15697 468 // ask chip to convert temperature
uci1 67:ec999336fcd1 469 #if CHIPBOARD==SST4CH
uci1 56:0bba0ef15697 470 PIN_therm.convert_temperature(true, DS1820::all_devices);
uci1 56:0bba0ef15697 471 gTemperature.SetTempAndTime( PIN_therm.temperature('c'), time(0) );
uci1 56:0bba0ef15697 472 #ifdef DEBUG
uci1 56:0bba0ef15697 473 printf("TTTTTTTT temp = %g at %u\r\n", gTemperature.GetTemperature(),
uci1 56:0bba0ef15697 474 gTemperature.GetTime());
uci1 56:0bba0ef15697 475 #endif
uci1 67:ec999336fcd1 476 #else
uci1 67:ec999336fcd1 477 return; // do nothing
uci1 67:ec999336fcd1 478 #endif
uci1 56:0bba0ef15697 479 }
uci1 56:0bba0ef15697 480
uci1 56:0bba0ef15697 481 void CheckTemp() {
uci1 56:0bba0ef15697 482 #ifdef DEBUG
uci1 56:0bba0ef15697 483 printf("CheckTemp\r\n");
uci1 56:0bba0ef15697 484 #endif
uci1 56:0bba0ef15697 485 UpdateTemperature();
uci1 56:0bba0ef15697 486 // save to disk
uci1 56:0bba0ef15697 487 FILE* cf = SnSDUtils::GetCurFile();
uci1 56:0bba0ef15697 488 if (cf!=0) {
uci1 56:0bba0ef15697 489 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 490 PIN_lockRegisters = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 491 #else
uci1 56:0bba0ef15697 492 PIN_readingData = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 493 #endif // ATWD4CH
uci1 56:0bba0ef15697 494 #ifdef DEBUG
uci1 56:0bba0ef15697 495 printf("writing temp. temp = %g at %u\r\n",
uci1 56:0bba0ef15697 496 gTemperature.GetTemperature(),
uci1 56:0bba0ef15697 497 gTemperature.GetTime());
uci1 56:0bba0ef15697 498 #endif
uci1 56:0bba0ef15697 499 SnSDUtils::WriteTempTo(cf, gTemperature);
uci1 56:0bba0ef15697 500 }
uci1 56:0bba0ef15697 501 gCheckTemp = false;
uci1 56:0bba0ef15697 502 }
uci1 56:0bba0ef15697 503
uci1 56:0bba0ef15697 504 void CheckPower(const bool isCommWin,
uci1 84:80b15993944e 505 const bool saveReading,
uci1 84:80b15993944e 506 const uint8_t devicesInUse) {
uci1 12:d472f9811262 507 #ifdef DEBUG
uci1 8:95a325df1f6b 508 printf("CheckPower\r\n");
uci1 12:d472f9811262 509 #endif
uci1 8:95a325df1f6b 510 // read power
uci1 8:95a325df1f6b 511 GetAvePowerReading();
uci1 56:0bba0ef15697 512 if (saveReading) {
uci1 56:0bba0ef15697 513 // save to disk
uci1 56:0bba0ef15697 514 FILE* cf = SnSDUtils::GetCurFile();
uci1 56:0bba0ef15697 515 if (cf!=0) {
uci1 56:0bba0ef15697 516 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 517 PIN_lockRegisters = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 518 #else
uci1 56:0bba0ef15697 519 PIN_readingData = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 520 #endif // ATWD4CH
uci1 12:d472f9811262 521 #ifdef DEBUG
uci1 56:0bba0ef15697 522 printf("writing power. v1=%g, v2=%g, r1=%g, r2=%g, t=%u, pownum=%u\r\n",
uci1 56:0bba0ef15697 523 gPower.GetAveV1(), gPower.GetAveV2(),
uci1 56:0bba0ef15697 524 gPower.GetRmsV1(), gPower.GetRmsV2(), gPower.GetTime(),
uci1 56:0bba0ef15697 525 gPowNum);
uci1 12:d472f9811262 526 #endif
uci1 56:0bba0ef15697 527 SnSDUtils::WritePowerTo(cf, gPower, gPowNum);
uci1 56:0bba0ef15697 528 }
uci1 8:95a325df1f6b 529 }
uci1 8:95a325df1f6b 530 // do we need to change modes?
uci1 8:95a325df1f6b 531 bool changed = false;
uci1 8:95a325df1f6b 532 if (gConf.IsLowPowerMode()) {
uci1 56:0bba0ef15697 533 #ifdef DEBUG
uci1 56:0bba0ef15697 534 printf("in low pwr. v1=%g, fromLP=%hu\r\n",
uci1 56:0bba0ef15697 535 gPower.GetAveV1(), gConf.GetBatVoltFromLowPwr());
uci1 56:0bba0ef15697 536 #endif
uci1 39:2f17131d22a5 537 if (gPower.GetAveV1() > gConf.GetBatVoltFromLowPwr()) {
uci1 12:d472f9811262 538 #ifdef DEBUG
uci1 8:95a325df1f6b 539 printf("chaing to normal power!\r\n");
uci1 12:d472f9811262 540 #endif
uci1 8:95a325df1f6b 541 gConf.ChangeToNormPower();
uci1 8:95a325df1f6b 542 changed = true;
uci1 8:95a325df1f6b 543 }
uci1 8:95a325df1f6b 544 } else {
uci1 56:0bba0ef15697 545 #ifdef DEBUG
uci1 56:0bba0ef15697 546 printf("in normal pwr. v1=%g, toLP=%hu\r\n",
uci1 56:0bba0ef15697 547 gPower.GetAveV1(), gConf.GetBatVoltToLowPwr());
uci1 56:0bba0ef15697 548 #endif
uci1 39:2f17131d22a5 549 if (gPower.GetAveV1() < gConf.GetBatVoltToLowPwr()) {
uci1 12:d472f9811262 550 #ifdef DEBUG
uci1 8:95a325df1f6b 551 printf("chaing to low power!\r\n");
uci1 12:d472f9811262 552 #endif
uci1 8:95a325df1f6b 553 gConf.ChangeToLowPower();
uci1 8:95a325df1f6b 554 changed = true;
uci1 8:95a325df1f6b 555 }
uci1 8:95a325df1f6b 556 }
uci1 8:95a325df1f6b 557 if (changed) {
uci1 84:80b15993944e 558 SetPower(isCommWin, devicesInUse); // TODO: This will fail if isCommWin==false? (currently not possible, but..)
uci1 12:d472f9811262 559 #ifdef DEBUG
uci1 8:95a325df1f6b 560 printf("Using config %s\r\n",gConf.GetLabel());
uci1 12:d472f9811262 561 #endif
uci1 8:95a325df1f6b 562 SetConfigAndMakeOutputFile(); // setup defaults in case no communication
uci1 8:95a325df1f6b 563 }
uci1 8:95a325df1f6b 564 // checking done
uci1 8:95a325df1f6b 565 gCheckPower = false;
uci1 8:95a325df1f6b 566 }
uci1 8:95a325df1f6b 567
uci1 84:80b15993944e 568 void ResetCounters() {
uci1 12:d472f9811262 569 const uint32_t evtStartCurSeq = (SnSDUtils::GetCurSeqNum()) // no -1; start with seq=0
uci1 12:d472f9811262 570 * gConf.GetEvtsPerFile();
uci1 84:80b15993944e 571 // gEvent.ClearEvent();
uci1 40:1324da35afd4 572 gEvtNum = evtStartCurSeq;
uci1 12:d472f9811262 573 gPowNum = evtStartCurSeq;
uci1 84:80b15993944e 574 // memset(gTrgNum, 0, sizeof(uint32_t)*kNumTrgs);
uci1 84:80b15993944e 575 gNumThmTrigs = 0;
uci1 84:80b15993944e 576 gNumFrcTrigs = 0;
uci1 84:80b15993944e 577 gForcedTrig = false;
uci1 22:f957c4f840ad 578 // reset rate counters
uci1 22:f957c4f840ad 579 gThmDtSum = 0;
uci1 22:f957c4f840ad 580 gThmNumDt = 0;
uci1 22:f957c4f840ad 581 gEvtDtSum = 0;
uci1 22:f957c4f840ad 582 gEvtNumDt = 0;
uci1 22:f957c4f840ad 583 // reset heartbeat counters
uci1 22:f957c4f840ad 584 gLastHrtbt = 0;
uci1 22:f957c4f840ad 585 gHrtbtFired = false;
uci1 22:f957c4f840ad 586 gHrtbtNum = 0;
uci1 84:80b15993944e 587 // reset status data caches
uci1 84:80b15993944e 588 gStNewPower = false;
uci1 84:80b15993944e 589 gStNewEvent = false;
uci1 84:80b15993944e 590 gStNewHeartbeat = false;
uci1 84:80b15993944e 591 gStNewTemperature = false;
uci1 84:80b15993944e 592
uci1 13:7a1fb885a8e4 593 #ifdef DEBUG
uci1 13:7a1fb885a8e4 594 printf("Reset: gEvtNum=%u, gPowNum=%u, evtStartCS=%u\r\n",
uci1 13:7a1fb885a8e4 595 gEvtNum, gPowNum, evtStartCurSeq);
uci1 13:7a1fb885a8e4 596 #endif
uci1 10:3c93db1cfb12 597 }
uci1 10:3c93db1cfb12 598
uci1 56:0bba0ef15697 599 void CalcRate(const uint32_t numtrgs,
uci1 56:0bba0ef15697 600 const double tottime_ms,
uci1 56:0bba0ef15697 601 float& rate) {
uci1 56:0bba0ef15697 602 rate = 0;
uci1 56:0bba0ef15697 603 if (numtrgs>1) {
uci1 56:0bba0ef15697 604 if (tottime_ms>0.0) {
uci1 56:0bba0ef15697 605 rate = static_cast<float>(numtrgs)
uci1 56:0bba0ef15697 606 / (tottime_ms/1e3);
uci1 56:0bba0ef15697 607 } else {
uci1 56:0bba0ef15697 608 // lots of triggers in 0 time
uci1 56:0bba0ef15697 609 rate = 1e6;
uci1 56:0bba0ef15697 610 }
uci1 56:0bba0ef15697 611 }
uci1 56:0bba0ef15697 612 }
uci1 56:0bba0ef15697 613
uci1 10:3c93db1cfb12 614 void GetRates(float& thmrate, float& evtrate) {
uci1 10:3c93db1cfb12 615 thmrate = evtrate = 0;
uci1 22:f957c4f840ad 616 #ifdef DEBUG
uci1 22:f957c4f840ad 617 printf("** Getting rates: gThmNumDt=%d, gThmDtSum=%g, "
uci1 22:f957c4f840ad 618 "gEvtNumDt=%d, gEvtDtSum=%g\r\n",
uci1 22:f957c4f840ad 619 gThmNumDt, gThmDtSum, gEvtNumDt, gEvtDtSum);
uci1 22:f957c4f840ad 620 #endif
uci1 22:f957c4f840ad 621
uci1 56:0bba0ef15697 622 CalcRate(gThmNumDt, gThmDtSum, thmrate);
uci1 56:0bba0ef15697 623 CalcRate(gEvtNumDt, gEvtDtSum, evtrate);
uci1 22:f957c4f840ad 624 }
uci1 22:f957c4f840ad 625
uci1 56:0bba0ef15697 626 void AddToRate(const double dt, const bool isThm) {
uci1 22:f957c4f840ad 627 if (isThm) {
uci1 22:f957c4f840ad 628 gThmDtSum += dt;
uci1 22:f957c4f840ad 629 gThmNumDt += 1u;
uci1 22:f957c4f840ad 630 } else {
uci1 22:f957c4f840ad 631 gEvtDtSum += dt;
uci1 22:f957c4f840ad 632 gEvtNumDt += 1u;
uci1 10:3c93db1cfb12 633 }
uci1 22:f957c4f840ad 634 #ifdef DEBUG
uci1 22:f957c4f840ad 635 printf("** AddToRate: dt=%g, isThm=%d\r\n",dt,(int)isThm);
uci1 22:f957c4f840ad 636 printf("** AddToRate: gThmNumDt=%d, gThmDtSum=%g, "
uci1 22:f957c4f840ad 637 "gEvtNumDt=%d, gEvtDtSum=%g\r\n",
uci1 22:f957c4f840ad 638 gThmNumDt, gThmDtSum, gEvtNumDt, gEvtDtSum);
uci1 22:f957c4f840ad 639 #endif
uci1 10:3c93db1cfb12 640 }
uci1 10:3c93db1cfb12 641
uci1 8:95a325df1f6b 642 bool IsSeqComplete() {
uci1 12:d472f9811262 643 #ifdef DEBUG
uci1 84:80b15993944e 644 printf("IsSeqComplete: eps=%hu, cntpow=%d, pow=%u, evt=%u, seq=%hu\r\n",
uci1 10:3c93db1cfb12 645 gConf.GetEvtsPerFile(), (int)gConf.IsCountingPowerReadings(),
uci1 40:1324da35afd4 646 gPowNum, gEvtNum, SnSDUtils::GetCurSeqNum());
uci1 12:d472f9811262 647 #endif
uci1 8:95a325df1f6b 648 if (gConf.GetEvtsPerFile()>0) {
uci1 12:d472f9811262 649 const uint32_t evtEndCurSeq = (SnSDUtils::GetCurSeqNum()+1) // account for seq=0
uci1 12:d472f9811262 650 * gConf.GetEvtsPerFile();
uci1 12:d472f9811262 651 #ifdef DEBUG
uci1 12:d472f9811262 652 printf("evtEndCurSeq=%u\r\n",evtEndCurSeq);
uci1 12:d472f9811262 653 #endif
uci1 8:95a325df1f6b 654 if (gConf.IsCountingPowerReadings()) {
uci1 12:d472f9811262 655 return (gPowNum>=evtEndCurSeq);
uci1 8:95a325df1f6b 656 } else {
uci1 12:d472f9811262 657 // first event num is a one-time per run offset, not one per sequence
uci1 40:1324da35afd4 658 return (gEvtNum>=evtEndCurSeq);
uci1 8:95a325df1f6b 659 }
uci1 12:d472f9811262 660 } else {
uci1 12:d472f9811262 661 return false;
uci1 8:95a325df1f6b 662 }
uci1 8:95a325df1f6b 663 }
uci1 1:e392595b4b76 664
uci1 40:1324da35afd4 665 #ifdef USE_RTOS
uci1 8:95a325df1f6b 666 void stopTicker(rtos::RtosTimer* tik) {
uci1 8:95a325df1f6b 667 if (tik!=0) {
uci1 8:95a325df1f6b 668 tik->stop();
uci1 8:95a325df1f6b 669 }
uci1 8:95a325df1f6b 670 }
uci1 8:95a325df1f6b 671 #else
uci1 8:95a325df1f6b 672 void stopTicker(Ticker& tik) {
uci1 8:95a325df1f6b 673 tik.detach();
uci1 8:95a325df1f6b 674 }
uci1 56:0bba0ef15697 675 #endif // USE_RTOS
uci1 8:95a325df1f6b 676
uci1 40:1324da35afd4 677 #ifdef USE_RTOS
uci1 18:55f1581f2ee4 678 float resetTicker(rtos::RtosTimer* tik, const float timSec,
uci1 18:55f1581f2ee4 679 const float maxTimSec) {
uci1 8:95a325df1f6b 680 if (tik!=0) {
uci1 8:95a325df1f6b 681 tik->stop();
uci1 8:95a325df1f6b 682 if (timSec>0) {
uci1 18:55f1581f2ee4 683 float tp = timSec > maxTimSec ? maxTimSec : timSec;
uci1 8:95a325df1f6b 684 tp *= 1000u; // ms
uci1 8:95a325df1f6b 685 tik->start(tp);
uci1 8:95a325df1f6b 686 return tp;
uci1 8:95a325df1f6b 687 }
uci1 8:95a325df1f6b 688 }
uci1 8:95a325df1f6b 689 return 0;
uci1 8:95a325df1f6b 690 }
uci1 8:95a325df1f6b 691 #else
uci1 18:55f1581f2ee4 692 float resetTicker(Ticker& tik, const float timSec,
uci1 18:55f1581f2ee4 693 const float maxTimSec, void (*fptr)(void)) {
uci1 8:95a325df1f6b 694 tik.detach();
uci1 8:95a325df1f6b 695 if (timSec>0) {
uci1 18:55f1581f2ee4 696 const float tp = timSec > maxTimSec ? maxTimSec : timSec;
uci1 8:95a325df1f6b 697 tik.attach(fptr, tp);
uci1 8:95a325df1f6b 698 return tp;
uci1 8:95a325df1f6b 699 }
uci1 8:95a325df1f6b 700 return 0;
uci1 8:95a325df1f6b 701 }
uci1 56:0bba0ef15697 702 #endif // USE_RTOS
uci1 8:95a325df1f6b 703
uci1 15:f2569d8e4176 704 void StopAllTickers() {
uci1 8:95a325df1f6b 705 stopTicker(gForceTicker);
uci1 8:95a325df1f6b 706 stopTicker(gHeartbeatTicker);
uci1 8:95a325df1f6b 707 stopTicker(gCommWinTicker);
uci1 8:95a325df1f6b 708 stopTicker(gPowerCheckTicker);
uci1 56:0bba0ef15697 709 stopTicker(gTempCheckTicker);
uci1 15:f2569d8e4176 710 }
uci1 15:f2569d8e4176 711
uci1 15:f2569d8e4176 712 void ResetAllTickers() {
uci1 40:1324da35afd4 713 #ifdef USE_RTOS
uci1 18:55f1581f2ee4 714 const float ftp = resetTicker(gForceTicker, gConf.GetForceTrigPeriod(),
uci1 18:55f1581f2ee4 715 kAbsMaxTimer);
uci1 40:1324da35afd4 716 Thread::wait(131); // make it less likely for multiple triggers to fire too close together
uci1 18:55f1581f2ee4 717 const float hbp = resetTicker(gHeartbeatTicker, gConf.GetHeartbeatPeriod(),
uci1 18:55f1581f2ee4 718 kAbsMaxTimer);
uci1 40:1324da35afd4 719 Thread::wait(173); // make it less likely for multiple triggers to fire too close together
uci1 18:55f1581f2ee4 720 const float cwp = resetTicker(gCommWinTicker, gConf.GetCommWinPeriod(),
uci1 18:55f1581f2ee4 721 kCommWinLongPrdTk);
uci1 40:1324da35afd4 722 Thread::wait(169); // make it less likely for multiple triggers to fire too close together
uci1 18:55f1581f2ee4 723 const float pcp = resetTicker(gPowerCheckTicker, gConf.GetVoltCheckPeriod(),
uci1 18:55f1581f2ee4 724 kAbsMaxTimer);
uci1 56:0bba0ef15697 725 Thread::wait(143); // make it less likely for multiple triggers to fire too close together
uci1 56:0bba0ef15697 726 const float ctp = resetTicker(gTempCheckTicker, gConf.GetTempCheckPeriod(),
uci1 56:0bba0ef15697 727 kAbsMaxTimer);
uci1 15:f2569d8e4176 728 #else
uci1 18:55f1581f2ee4 729 const float ftp = resetTicker(gForceTicker, gConf.GetForceTrigPeriod(),
uci1 18:55f1581f2ee4 730 kAbsMaxTimer, &procForceTrigger);
uci1 25:57b2627fe756 731 wait_ms(131); // make it less likely for multiple triggers to fire too close together
uci1 18:55f1581f2ee4 732 const float hbp = resetTicker(gHeartbeatTicker, gConf.GetHeartbeatPeriod(),
uci1 18:55f1581f2ee4 733 kAbsMaxTimer, &procHeartbeat);
uci1 25:57b2627fe756 734 wait_ms(173); // make it less likely for multiple triggers to fire too close together
uci1 18:55f1581f2ee4 735 const float cwp = resetTicker(gCommWinTicker, gConf.GetCommWinPeriod(),
uci1 18:55f1581f2ee4 736 kCommWinLongPrdTk, &procCommWin);
uci1 25:57b2627fe756 737 wait_ms(169); // make it less likely for multiple triggers to fire too close together
uci1 18:55f1581f2ee4 738 const float pcp = resetTicker(gPowerCheckTicker, gConf.GetVoltCheckPeriod(),
uci1 18:55f1581f2ee4 739 kAbsMaxTimer, &procPowerCheck);
uci1 56:0bba0ef15697 740 wait_ms(143); // make it less likely for multiple triggers to fire too close together
uci1 56:0bba0ef15697 741 const float ctp = resetTicker(gTempCheckTicker, gConf.GetTempCheckPeriod(),
uci1 56:0bba0ef15697 742 kAbsMaxTimer, &procTempCheck);
uci1 56:0bba0ef15697 743 #endif // USE_RTOS
uci1 15:f2569d8e4176 744 #ifdef DEBUG
uci1 18:55f1581f2ee4 745 printf("attach force trig %g\r\n",ftp);
uci1 18:55f1581f2ee4 746 printf("attach heart beat %g\r\n",hbp);
uci1 18:55f1581f2ee4 747 printf("attach comm win %g\r\n",cwp);
uci1 18:55f1581f2ee4 748 printf("attach power chk %g\r\n",pcp);
uci1 56:0bba0ef15697 749 printf("attach temp chk %g\r\n",ctp);
uci1 15:f2569d8e4176 750 #endif
uci1 15:f2569d8e4176 751 }
uci1 61:42cbfc02e0e0 752 /*
uci1 56:0bba0ef15697 753 void UponBrownout() {
uci1 56:0bba0ef15697 754 // signal brownout by all LEDs off
uci1 56:0bba0ef15697 755 led1 = led2 = led3 = led4 = 0;
uci1 56:0bba0ef15697 756 // note that debug printing here is pointless,
uci1 56:0bba0ef15697 757 // since power over USB will prevent brownout
uci1 56:0bba0ef15697 758
uci1 56:0bba0ef15697 759 // close the current file
uci1 56:0bba0ef15697 760 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 761 PIN_lockRegisters = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 762 #else
uci1 56:0bba0ef15697 763 PIN_readingData = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 764 #endif
uci1 56:0bba0ef15697 765 SnSDUtils::WriteTrigWaitWinTime(SnSDUtils::GetCurFile(),
uci1 56:0bba0ef15697 766 gClkSet,
uci1 56:0bba0ef15697 767 false);
uci1 56:0bba0ef15697 768 SnSDUtils::CloseOutputFile(SnSDUtils::GetCurFile());
uci1 56:0bba0ef15697 769
uci1 56:0bba0ef15697 770 // change to low power settings
uci1 56:0bba0ef15697 771 gConf.ChangeToLowPower();
uci1 56:0bba0ef15697 772 // actually power stuff down
uci1 56:0bba0ef15697 773 SetPower(gCommWinOpen);
uci1 56:0bba0ef15697 774
uci1 56:0bba0ef15697 775 // goodnight
uci1 56:0bba0ef15697 776 Sleep();
uci1 56:0bba0ef15697 777 }
uci1 61:42cbfc02e0e0 778 */
uci1 15:f2569d8e4176 779 void StopRunning() {
uci1 15:f2569d8e4176 780 #if defined(DEBUG) || defined(SSNOTIFY)
uci1 15:f2569d8e4176 781 printf("stop running\r\n");
uci1 15:f2569d8e4176 782 #endif
uci1 15:f2569d8e4176 783 StopAllTickers();
uci1 17:4687bf932b8c 784 OpenCommWin();
uci1 8:95a325df1f6b 785 while (true) {
uci1 8:95a325df1f6b 786 led3 = 1; led4=1;
uci1 40:1324da35afd4 787 #ifdef USE_RTOS
uci1 40:1324da35afd4 788 Thread::wait(500);
uci1 40:1324da35afd4 789 #else
uci1 8:95a325df1f6b 790 wait(0.5);
uci1 56:0bba0ef15697 791 #endif // USE_RTOS
uci1 8:95a325df1f6b 792 led3 = 0; led4=0;
uci1 40:1324da35afd4 793 #ifdef USE_RTOS
uci1 40:1324da35afd4 794 Thread::wait(500);
uci1 40:1324da35afd4 795 #else
uci1 8:95a325df1f6b 796 wait(0.5);
uci1 56:0bba0ef15697 797 #endif // USE_RTOS
uci1 22:f957c4f840ad 798 // don't kick the watchdog
uci1 22:f957c4f840ad 799 // if we do, the station is unrecoverable without physical access
uci1 8:95a325df1f6b 800 }
uci1 8:95a325df1f6b 801 }
uci1 1:e392595b4b76 802
uci1 40:1324da35afd4 803
uci1 56:0bba0ef15697 804 int InitSDCard() {
uci1 40:1324da35afd4 805 #ifdef DEBUG
uci1 40:1324da35afd4 806 printf("initializing SD card..\r\n");
uci1 40:1324da35afd4 807 #endif
uci1 76:f8383f0292c2 808 int ret = 1; // always fail if ignoring the SD card (1==fail)
uci1 76:f8383f0292c2 809 if (gConf.IsIgnoringSDcard()==false) {
uci1 76:f8383f0292c2 810 // initialize the SD card. this should prevent the issue with
uci1 76:f8383f0292c2 811 // seq 0 being overwritten upon power up or the SD card first
uci1 76:f8383f0292c2 812 // being insterted
uci1 63:4820a4460f00 813 ret = sd.disk_initialize();
uci1 76:f8383f0292c2 814 // may need to try a bunch of times to get it to init
uci1 76:f8383f0292c2 815 for (int i=0; i<25 && (ret!=0); ++i) {
uci1 76:f8383f0292c2 816 ret = sd.disk_initialize();
uci1 76:f8383f0292c2 817 #ifdef DEBUG
uci1 76:f8383f0292c2 818 printf("called disk_initialize (ret=%d)\r\n",ret);
uci1 76:f8383f0292c2 819 #endif
uci1 76:f8383f0292c2 820 }
uci1 76:f8383f0292c2 821 }
uci1 56:0bba0ef15697 822 #ifdef DEBUG
uci1 76:f8383f0292c2 823 printf("init SD card %d..\r\n", ret);
uci1 56:0bba0ef15697 824 #endif
uci1 56:0bba0ef15697 825 return ret;
uci1 40:1324da35afd4 826 }
uci1 40:1324da35afd4 827
uci1 0:664899e0b988 828 int main() {
uci1 22:f957c4f840ad 829 // a failsafe
uci1 62:4b59c1eb429f 830 //Watchdog::kick(WDFAILSAFE);
uci1 62:4b59c1eb429f 831 #ifdef DEBUG
uci1 63:4820a4460f00 832 printf("Restart watchdog with time [%u] at [%u]\r\n",
uci1 63:4820a4460f00 833 gConf.GetWatchdogPeriod(), time(0));
uci1 84:80b15993944e 834 printf("Free memory = %d\r\n", FreeMem());
uci1 62:4b59c1eb429f 835 #endif
uci1 62:4b59c1eb429f 836 Watchdog::kick(gConf.GetWatchdogPeriod());
uci1 56:0bba0ef15697 837
uci1 56:0bba0ef15697 838 gCpu.baud(CPUBAUD_SN);
uci1 56:0bba0ef15697 839
uci1 1:e392595b4b76 840 {
uci1 18:55f1581f2ee4 841 #if defined(SSNOTIFY) || defined(DEBUG)
uci1 41:d6f5e2f09e07 842 printf("\n\n\n\n\nmain: start\r\n");
uci1 15:f2569d8e4176 843 #endif
uci1 67:ec999336fcd1 844 led1=led2=led3=led4=0;
uci1 40:1324da35afd4 845 #ifdef USE_RTOS
uci1 40:1324da35afd4 846 led1=1; Thread::wait(200);
uci1 40:1324da35afd4 847 led1=0; led2=1; Thread::wait(200);
uci1 40:1324da35afd4 848 led2=0; led3=1; Thread::wait(200);
uci1 40:1324da35afd4 849 led3=0; led4=1; Thread::wait(200);
uci1 40:1324da35afd4 850 #else
uci1 2:e67f7c158087 851 led1=1; wait(0.2);
uci1 2:e67f7c158087 852 led1=0; led2=1; wait(0.2);
uci1 2:e67f7c158087 853 led2=0; led3=1; wait(0.2);
uci1 2:e67f7c158087 854 led3=0; led4=1; wait(0.2);
uci1 56:0bba0ef15697 855 #endif // USE_RTOS
uci1 1:e392595b4b76 856 led4=0;
uci1 1:e392595b4b76 857 }
uci1 67:ec999336fcd1 858
uci1 67:ec999336fcd1 859 // signal startup before first comm win
uci1 67:ec999336fcd1 860 led2 = led1 = 1;
uci1 25:57b2627fe756 861
uci1 56:0bba0ef15697 862 // don't initialize yet, but give SnSDUtils a pointer to
uci1 56:0bba0ef15697 863 // the function that initializes it, so it can call the fcn later
uci1 40:1324da35afd4 864 SnSDUtils::fgDoInit = &InitSDCard;
uci1 56:0bba0ef15697 865
uci1 63:4820a4460f00 866 // check in case we need to go to low power
uci1 63:4820a4460f00 867 //wait(4); // TODO: the vADCs read high for first ~4-5sec
uci1 63:4820a4460f00 868 CheckPower(false, false);
uci1 63:4820a4460f00 869 #ifdef DEBUG
uci1 63:4820a4460f00 870 printf("startup power: cards %d, amps %d, irid %d, afar %d\r\n",
uci1 63:4820a4460f00 871 PIN_turn_on_system.read(), PIN_turn_on_amps.read(),
uci1 63:4820a4460f00 872 PIN_iridSbd_power.read(), PIN_afar_power.read());
uci1 63:4820a4460f00 873 #endif
uci1 63:4820a4460f00 874
uci1 61:42cbfc02e0e0 875 /*
uci1 56:0bba0ef15697 876 // Note: the brownout isn't useful since it sees either 5V or nothing on our board
uci1 56:0bba0ef15697 877 // set up the brownout interrupt
uci1 56:0bba0ef15697 878 NVIC_SetVector(BOD_IRQn, (uint32_t)&UponBrownout);
uci1 56:0bba0ef15697 879 // Enable Brown Out Detect Interrupt
uci1 56:0bba0ef15697 880 NVIC_EnableIRQ(BOD_IRQn);
uci1 61:42cbfc02e0e0 881 */
uci1 56:0bba0ef15697 882
uci1 21:ce51bb0ba4a5 883 #ifdef DEBUG
uci1 18:55f1581f2ee4 884 printf("making comm objects\r\n");
uci1 18:55f1581f2ee4 885 #endif
uci1 25:57b2627fe756 886
uci1 25:57b2627fe756 887 uint8_t comi(0);
uci1 25:57b2627fe756 888 #ifdef ENABLE_AFAR_COMM
uci1 25:57b2627fe756 889 // RTOS stuff must be made inside main for some reason
uci1 18:55f1581f2ee4 890 #ifdef USE_ETH_INTERFACE
uci1 41:d6f5e2f09e07 891 #ifdef DEBUG
uci1 41:d6f5e2f09e07 892 printf("making SnCommAfarTCP\r\n");
uci1 41:d6f5e2f09e07 893 #endif
uci1 25:57b2627fe756 894 gComms[comi++] = new SnCommAfarTCP(gConf);
uci1 18:55f1581f2ee4 895 #else
uci1 41:d6f5e2f09e07 896 #ifdef DEBUG
uci1 41:d6f5e2f09e07 897 printf("making SnCommWinAfar\r\n");
uci1 41:d6f5e2f09e07 898 #endif
uci1 37:ff95e7070f26 899 //gComms[comi++] = new SnCommAfarNetIf(gConf);
uci1 37:ff95e7070f26 900 gComms[comi++] = new SnCommWinAfar(gConf);
uci1 28:484943132bb0 901 #ifdef ENABLE_AFAR_TWITTER
uci1 41:d6f5e2f09e07 902 #ifdef DEBUG
uci1 41:d6f5e2f09e07 903 printf("making SnCommAfarNetIfTwitter\r\n");
uci1 41:d6f5e2f09e07 904 #endif
uci1 28:484943132bb0 905 gTwit = new SnCommAfarNetIfTwitter(gConf);
uci1 56:0bba0ef15697 906 #endif // ENABLE_AFAR_TWITTER
uci1 56:0bba0ef15697 907 #endif // USE_ETH_INTERFACE
uci1 56:0bba0ef15697 908 #endif // ENABLE_AFAR_COMM
uci1 25:57b2627fe756 909 #ifdef ENABLE_SBD_COMM
uci1 41:d6f5e2f09e07 910 #ifdef DEBUG
uci1 41:d6f5e2f09e07 911 printf("making SnCommWinSBD\r\n");
uci1 41:d6f5e2f09e07 912 #endif
uci1 40:1324da35afd4 913 gComms[comi++] = new SnCommWinSBD(&gSBDport);
uci1 56:0bba0ef15697 914 #endif // ENABLE_SBD_COMM
uci1 25:57b2627fe756 915 #ifdef ENABLE_USB_COMM
uci1 41:d6f5e2f09e07 916 #ifdef DEBUG
uci1 41:d6f5e2f09e07 917 printf("makin SnCommWinUsb\r\n");
uci1 41:d6f5e2f09e07 918 #endif
uci1 37:ff95e7070f26 919 gComms[comi++] = new SnCommWinUsb(&gCpu);
uci1 56:0bba0ef15697 920 #endif // ENABLE_USB_COMM
uci1 18:55f1581f2ee4 921
uci1 18:55f1581f2ee4 922 #ifdef DEBUG
uci1 28:484943132bb0 923 printf("made comm objects\r\n");
uci1 41:d6f5e2f09e07 924 #ifdef USE_MODSERIAL
uci1 41:d6f5e2f09e07 925 printf("using MODSERIAL\r\n");
uci1 56:0bba0ef15697 926 #endif // USE_MODSERIAL
uci1 18:55f1581f2ee4 927 #endif
uci1 40:1324da35afd4 928
uci1 40:1324da35afd4 929 if (comi!=kNcomms) {
uci1 40:1324da35afd4 930 error("comi=[%hhu] != kNcomms=[%hhu]\r\n",
uci1 40:1324da35afd4 931 comi, kNcomms);
uci1 40:1324da35afd4 932 // will die here with blue lights of death
uci1 40:1324da35afd4 933 }
uci1 40:1324da35afd4 934
uci1 40:1324da35afd4 935 #ifdef USE_RTOS
uci1 8:95a325df1f6b 936 gForceTicker = new rtos::RtosTimer(&procForceTrigger);
uci1 8:95a325df1f6b 937 gHeartbeatTicker = new rtos::RtosTimer(&procHeartbeat);
uci1 8:95a325df1f6b 938 gCommWinTicker = new rtos::RtosTimer(&procCommWin);
uci1 8:95a325df1f6b 939 gPowerCheckTicker = new rtos::RtosTimer(&procPowerCheck);
uci1 56:0bba0ef15697 940 gTempCheckTicker = new rtos::RtosTimer(&procTempCheck);
uci1 56:0bba0ef15697 941 #endif // USE_RTOS
uci1 67:ec999336fcd1 942
uci1 1:e392595b4b76 943 // set the clock to the BS time, if it's not set
uci1 1:e392595b4b76 944 if ( (static_cast<int32_t>(time(0)))<0 ) {
uci1 1:e392595b4b76 945 set_time(kBStime);
uci1 1:e392595b4b76 946 }
uci1 12:d472f9811262 947 #ifdef DEBUG
uci1 1:e392595b4b76 948 printf("time = %d\r\n",(int32_t)time(0));
uci1 12:d472f9811262 949 #endif
uci1 1:e392595b4b76 950 gLastCommWin = time(0); // prevent comm win proc
uci1 0:664899e0b988 951
uci1 40:1324da35afd4 952 #ifdef USE_RTOS
uci1 8:95a325df1f6b 953 gForceTicker->stop();
uci1 8:95a325df1f6b 954 #else
uci1 0:664899e0b988 955 gForceTicker.detach();
uci1 56:0bba0ef15697 956 #endif // USE_RTOS
uci1 0:664899e0b988 957 gFirstEvt = true;
uci1 56:0bba0ef15697 958
uci1 67:ec999336fcd1 959
uci1 67:ec999336fcd1 960 #ifdef DEBUG
uci1 67:ec999336fcd1 961 printf("MAC=%012llX\r\n", (gConf.GetMacAddress())>>16); // 64 -> 48 bits
uci1 67:ec999336fcd1 962 printf("my ip = %s\r\n", gConf.GetMbedIP());
uci1 67:ec999336fcd1 963 printf("my mask = %s\r\n", gConf.GetMbedMask());
uci1 67:ec999336fcd1 964 printf("my gate = %s\r\n", gConf.GetMbedGate());
uci1 67:ec999336fcd1 965 printf("remote server = %s : %hu\r\n",
uci1 67:ec999336fcd1 966 gConf.GetRemoteServer(), gConf.GetRemotePort());
uci1 84:80b15993944e 967 for (uint8_t i=0; i<SnConfigFrame::kNumDatStreams; ++i) {
uci1 84:80b15993944e 968 printf("data stream %hhu (%s): connectTO=%hhu, listenTO=%hhu\r\n",
uci1 84:80b15993944e 969 i, SnConfigFrame::GetDataStreamNameOfIdx(i),
uci1 84:80b15993944e 970 gConf.GetCommWinConnectTOofIdx(i),
uci1 84:80b15993944e 971 gConf.GetCommWinListenTOofIdx(i));
uci1 84:80b15993944e 972 }
uci1 67:ec999336fcd1 973 #endif
uci1 67:ec999336fcd1 974
uci1 4:a91682e19d6b 975 // (probably) power down comms and power up cards,amps
uci1 84:80b15993944e 976 SetPower(false, SnConfigFrame::kIrid | SnConfigFrame::kAfar);
uci1 56:0bba0ef15697 977 // check power again to see if voltages drooped
uci1 56:0bba0ef15697 978 CheckPower(false, false);
uci1 4:a91682e19d6b 979
uci1 0:664899e0b988 980 //
uci1 0:664899e0b988 981 // get config
uci1 0:664899e0b988 982 //
uci1 12:d472f9811262 983 #ifdef DEBUG
uci1 84:80b15993944e 984 printf("run mode\r\n");
uci1 84:80b15993944e 985 printf("IsCountingPowerReadings=%d\r\n",(int)gConf.IsCountingPowerReadings());
uci1 84:80b15993944e 986 printf("IsSingleSeqRunMode=%d\r\n",(int)gConf.IsSingleSeqRunMode());
uci1 84:80b15993944e 987 printf("IsDualThresholdMode=%d\r\n",(int)gConf.IsDualThresholdMode());
uci1 84:80b15993944e 988 printf("IsDifferentialTrigMode=%d\r\n",(int)gConf.IsDifferentialTrigMode());
uci1 84:80b15993944e 989 printf("IsSBDonlyLowPwrMode=%d\r\n",(int)gConf.IsSBDonlyLowPwrMode());
uci1 84:80b15993944e 990 printf("IsRunSeqListOneCommWinOnly=%d\r\n",(int)gConf.IsRunSeqListOneCommWinOnly());
uci1 84:80b15993944e 991 printf("IsIgnoringSDcard=%d\r\n",(int)gConf.IsIgnoringSDcard());
uci1 84:80b15993944e 992 printf("IsCommPowerSimple=%d\r\n",(int)gConf.IsCommPowerSimple());
uci1 8:95a325df1f6b 993 printf("call OpenCommWin\r\n");
uci1 84:80b15993944e 994 printf("Free memory = %d\r\n", FreeMem());
uci1 12:d472f9811262 995 #endif
uci1 67:ec999336fcd1 996 led2 = led1 = 0; // back to "normal" for comm win
uci1 40:1324da35afd4 997 OpenCommWin(true, true); // alwasy configure, even if no new config
uci1 3:24c5f0f50bf1 998
uci1 0:664899e0b988 999 // get ready to trigger
uci1 0:664899e0b988 1000 PIN_spi.format( 16, 1 ); // change to data readout format
uci1 15:f2569d8e4176 1001 PIN_spi.frequency( 10000000 ); // Max is 12.5 MHz
uci1 0:664899e0b988 1002
uci1 41:d6f5e2f09e07 1003 // read and cache the dCard power pin setting,
uci1 41:d6f5e2f09e07 1004 // so we can use the cached value later
uci1 37:ff95e7070f26 1005 AreCardsPowered(true); // TODO: should this be an if?
uci1 56:0bba0ef15697 1006 register double etms=0; // time between written events
uci1 41:d6f5e2f09e07 1007
uci1 41:d6f5e2f09e07 1008 // the main event loop. wait for triggers in SendClock
uci1 41:d6f5e2f09e07 1009 while ( true ) {
uci1 0:664899e0b988 1010 // in here, we wait for triggers from the MB-FPGA
uci1 0:664899e0b988 1011 Watchdog::kick(); // don't reset!
uci1 1:e392595b4b76 1012
uci1 67:ec999336fcd1 1013 led1 = 1; // signal normal running (i.e. waiting)
uci1 1:e392595b4b76 1014
uci1 12:d472f9811262 1015 #ifdef DEBUG
uci1 1:e392595b4b76 1016 printf("calling wait trig\r\n");
uci1 1:e392595b4b76 1017 printf("gFirstEvt=%s\r\n",gFirstEvt?"true":"false");
uci1 5:9cea89700c66 1018 printf("readingout=%d\r\n",(int)gReadingOut);
uci1 84:80b15993944e 1019 printf("Free memory = %d\r\n", FreeMem());
uci1 12:d472f9811262 1020 #endif
uci1 40:1324da35afd4 1021 if (gFirstEvt) {
uci1 41:d6f5e2f09e07 1022 #ifdef DEBUG
uci1 41:d6f5e2f09e07 1023 printf("WriteTrigWaitWinTime (start)\r\n");
uci1 41:d6f5e2f09e07 1024 #endif
uci1 97:9f3fe603e8b5 1025 gClkSet.UpdateClock( gSinceClkSet );
uci1 40:1324da35afd4 1026 SnSDUtils::WriteTrigWaitWinTime(SnSDUtils::GetCurFile(),
uci1 40:1324da35afd4 1027 gClkSet,
uci1 40:1324da35afd4 1028 true);
uci1 40:1324da35afd4 1029 gThmTrgTimer.reset(); gThmTrgTimer.start();
uci1 40:1324da35afd4 1030 gAllTrgTimer.reset(); gAllTrgTimer.start();
uci1 84:80b15993944e 1031 gStTrgStartClk = gClkSet;
uci1 56:0bba0ef15697 1032 #if CHIPBOARD==SST4CH
uci1 56:0bba0ef15697 1033 // reset in case a trigger arrived before we were ready
uci1 56:0bba0ef15697 1034 // this is mostly to ensure that the chip gets reset on soft
uci1 56:0bba0ef15697 1035 // reboot, in case it got stopped prior to the reboot
uci1 56:0bba0ef15697 1036 PIN_ResetChips = 1;
uci1 56:0bba0ef15697 1037 PIN_ResetChips = 0;
uci1 56:0bba0ef15697 1038 #endif
uci1 40:1324da35afd4 1039 }
uci1 76:f8383f0292c2 1040
uci1 56:0bba0ef15697 1041 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 1042 PIN_lockRegisters = 0; // allow data to come from DFPGA
uci1 56:0bba0ef15697 1043 WaitTrigAndSendClock(); // wait for trigger and move data to MB. this returns immediately if cards are powered off
uci1 56:0bba0ef15697 1044 PIN_lockRegisters = 1; // block registers during readout
uci1 56:0bba0ef15697 1045 #else
uci1 56:0bba0ef15697 1046 PIN_readingData = 0; // not reading yet
uci1 56:0bba0ef15697 1047 WaitTrigAndSendClock(); // wait for trigger. this returns immediately if cards are powered off
uci1 56:0bba0ef15697 1048 // PIN_readingData will be set high by SnEventFrame::ReadWaveformsSST
uci1 56:0bba0ef15697 1049 #endif // ATWD4CH
uci1 12:d472f9811262 1050 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1051 gProfiler.start();
uci1 84:80b15993944e 1052 int befSaveEvt=0, aftSaveEvt=0,
uci1 12:d472f9811262 1053 befChkPow=0, aftChkPow=0, befNewSeq=0, aftNewSeq=0, endOfLoop=0;
uci1 56:0bba0ef15697 1054 #endif // EVT_TIME_PROFILE
uci1 12:d472f9811262 1055
uci1 1:e392595b4b76 1056 if (gReadingOut) {
uci1 67:ec999336fcd1 1057
uci1 67:ec999336fcd1 1058 led1 = 0; led4 = 1; // signal reading out
uci1 67:ec999336fcd1 1059
uci1 56:0bba0ef15697 1060 const double ttms = gThmTrgTimer.read_us() / 1e3; // for rate calculation
uci1 56:0bba0ef15697 1061 const double atms = gAllTrgTimer.read_us() / 1e3; // for throttle
uci1 84:80b15993944e 1062 // if (gEvent.IsForcedTrg()==false) {
uci1 84:80b15993944e 1063 if (gForcedTrig) {
uci1 40:1324da35afd4 1064 // don't reset if not a thermal trigger
uci1 40:1324da35afd4 1065 gThmTrgTimer.reset(); gThmTrgTimer.start();
uci1 40:1324da35afd4 1066 }
uci1 40:1324da35afd4 1067 gAllTrgTimer.reset(); gAllTrgTimer.start(); // restart trigger timer
uci1 40:1324da35afd4 1068 etms += atms; // time between events
uci1 8:95a325df1f6b 1069
uci1 8:95a325df1f6b 1070 Watchdog::kick(); // don't reset!
uci1 15:f2569d8e4176 1071
uci1 1:e392595b4b76 1072 //
uci1 1:e392595b4b76 1073 // got trigger. read registers to mbed and build the event
uci1 1:e392595b4b76 1074 //
uci1 1:e392595b4b76 1075
uci1 50:163ec8d88aa9 1076 // TODO: no way to check for external trigger?
uci1 84:80b15993944e 1077 if (gForcedTrig==false) {
uci1 84:80b15993944e 1078 // ++(gTrgNum[kThmTrg]);
uci1 84:80b15993944e 1079 ++gNumThmTrigs;
uci1 50:163ec8d88aa9 1080 AddToRate(ttms, true);
uci1 84:80b15993944e 1081 }
uci1 1:e392595b4b76 1082
uci1 84:80b15993944e 1083 if ( gForcedTrig || gFirstEvt ||
uci1 56:0bba0ef15697 1084 (etms>=gConf.GetEvtThrtlPeriodMs()) ) {
uci1 1:e392595b4b76 1085
uci1 12:d472f9811262 1086 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1087 gProfiler.stop(); befSaveEvt=gProfiler.read_us(); gProfiler.start();
uci1 56:0bba0ef15697 1088 #endif // EVT_TIME_PROFILE
uci1 84:80b15993944e 1089
uci1 84:80b15993944e 1090 // want to keep this event. save it (and check if it passes L1)
uci1 1:e392595b4b76 1091 SaveEvent(etms);
uci1 22:f957c4f840ad 1092 AddToRate(etms, false);
uci1 12:d472f9811262 1093 etms=0;
uci1 84:80b15993944e 1094
uci1 12:d472f9811262 1095 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1096 gProfiler.stop(); aftSaveEvt=gProfiler.read_us(); gProfiler.start();
uci1 56:0bba0ef15697 1097 #endif // EVT_TIME_PROFILE
uci1 84:80b15993944e 1098
uci1 56:0bba0ef15697 1099 } else {
uci1 56:0bba0ef15697 1100 #if CHIPBOARD==SST4CH
uci1 56:0bba0ef15697 1101 // reset in case a trigger arrived before we were ready
uci1 56:0bba0ef15697 1102 PIN_ResetChips = 1;
uci1 56:0bba0ef15697 1103 PIN_ResetChips = 0;
uci1 12:d472f9811262 1104 #endif
uci1 1:e392595b4b76 1105 }
uci1 67:ec999336fcd1 1106
uci1 84:80b15993944e 1107 // done with this event.
uci1 84:80b15993944e 1108 // reset flags from the "old" event
uci1 84:80b15993944e 1109 gForcedTrig = false;
uci1 84:80b15993944e 1110 gAdcToMBflag = false;
uci1 84:80b15993944e 1111
uci1 67:ec999336fcd1 1112 led1 = 1; led4 = 0; // end signal reading out
uci1 67:ec999336fcd1 1113
uci1 1:e392595b4b76 1114 }
uci1 12:d472f9811262 1115 #ifdef DEBUG
uci1 1:e392595b4b76 1116 printf("past reading out\r\n");
uci1 12:d472f9811262 1117 #endif
uci1 1:e392595b4b76 1118
uci1 23:ccf39298f205 1119 if (gHrtbtFired) {
uci1 67:ec999336fcd1 1120 led1 = 1; led4 = 1; // signal saving transient
uci1 84:80b15993944e 1121 gHrtbt.SetTime( gLastHrtbt );
uci1 84:80b15993944e 1122 // -1 so we start counting at 0
uci1 84:80b15993944e 1123 // counting inside proc so we have a record of the number of proc's
uci1 84:80b15993944e 1124 // even if we are saving/triggering slower than they're firing
uci1 84:80b15993944e 1125 gHrtbt.SetNum( (gHrtbtNum>0) ? (gHrtbtNum - 1) : 0 );
uci1 23:ccf39298f205 1126 SaveHeartbeat();
uci1 23:ccf39298f205 1127 gHrtbtFired=false;
uci1 84:80b15993944e 1128 gStNewHeartbeat = true;
uci1 67:ec999336fcd1 1129 led1 = 1; led4 = 0; // end signal saving transient
uci1 23:ccf39298f205 1130 }
uci1 12:d472f9811262 1131
uci1 12:d472f9811262 1132 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1133 gProfiler.stop(); befChkPow=gProfiler.read_us(); gProfiler.start();
uci1 56:0bba0ef15697 1134 #endif // EVT_TIME_PROFILE
uci1 8:95a325df1f6b 1135 // check the power?
uci1 8:95a325df1f6b 1136 if (gCheckPower) {
uci1 12:d472f9811262 1137 #ifdef DEBUG
uci1 8:95a325df1f6b 1138 printf("call check power\r\n");
uci1 12:d472f9811262 1139 #endif
uci1 67:ec999336fcd1 1140 led1 = 1; led4 = 1; // signal saving transient
uci1 8:95a325df1f6b 1141 CheckPower(false);
uci1 84:80b15993944e 1142 gStPower = gPower;
uci1 84:80b15993944e 1143 gStNewPower = true;
uci1 67:ec999336fcd1 1144 led1 = 1; led4 = 0; // end signal saving transient
uci1 8:95a325df1f6b 1145 }
uci1 12:d472f9811262 1146 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1147 gProfiler.stop(); aftChkPow=gProfiler.read_us(); gProfiler.start();
uci1 56:0bba0ef15697 1148 #endif // EVT_TIME_PROFILE
uci1 56:0bba0ef15697 1149
uci1 56:0bba0ef15697 1150 if (gCheckTemp) {
uci1 56:0bba0ef15697 1151 #ifdef DEBUG
uci1 56:0bba0ef15697 1152 printf("call check temp\r\n");
uci1 12:d472f9811262 1153 #endif
uci1 67:ec999336fcd1 1154 led1 = 1; led4 = 1; // signal saving transient
uci1 56:0bba0ef15697 1155 CheckTemp();
uci1 84:80b15993944e 1156 gStTemperature = gTemperature;
uci1 84:80b15993944e 1157 gStNewTemperature = true;
uci1 67:ec999336fcd1 1158 led1 = 1; led4 = 0; // end signal saving transient
uci1 56:0bba0ef15697 1159 }
uci1 8:95a325df1f6b 1160
uci1 21:ce51bb0ba4a5 1161 // open comm win?
uci1 21:ce51bb0ba4a5 1162 if (gOpenCommWin) {
uci1 21:ce51bb0ba4a5 1163 #ifdef DEBUG
uci1 21:ce51bb0ba4a5 1164 printf("gOpenComWin=%s, opening\r\n",gOpenCommWin?"true":"false");
uci1 41:d6f5e2f09e07 1165 printf("WriteTrigWaitWinTime (stop)\r\n");
uci1 21:ce51bb0ba4a5 1166 #endif
uci1 97:9f3fe603e8b5 1167 gClkSet.UpdateClock( gSinceClkSet );
uci1 40:1324da35afd4 1168 SnSDUtils::WriteTrigWaitWinTime(SnSDUtils::GetCurFile(),
uci1 40:1324da35afd4 1169 gClkSet,
uci1 40:1324da35afd4 1170 false);
uci1 84:80b15993944e 1171 gStTrgStopClk = gClkSet;
uci1 67:ec999336fcd1 1172 led1 = 0; // signal not waiting
uci1 21:ce51bb0ba4a5 1173 OpenCommWin();
uci1 67:ec999336fcd1 1174 led1 = 1; // end signal not waiting
uci1 21:ce51bb0ba4a5 1175 gOpenCommWin=false;
uci1 22:f957c4f840ad 1176 gFirstEvt = true;
uci1 40:1324da35afd4 1177 gAllTrgTimer.reset();
uci1 40:1324da35afd4 1178 gThmTrgTimer.reset();
uci1 22:f957c4f840ad 1179 etms=0;
uci1 21:ce51bb0ba4a5 1180 } else {
uci1 21:ce51bb0ba4a5 1181 #ifdef DEBUG
uci1 27:efc4d654b139 1182 printf("gOpenCommWin=false, gCommWinChecks=%u, gNcommWinChecks=%u\r\n",
uci1 27:efc4d654b139 1183 gCommWinChecks, gNcommWinChecks);
uci1 21:ce51bb0ba4a5 1184 #endif
uci1 21:ce51bb0ba4a5 1185 }
uci1 21:ce51bb0ba4a5 1186
uci1 12:d472f9811262 1187 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1188 gProfiler.stop(); befNewSeq=gProfiler.read_us(); gProfiler.start();
uci1 56:0bba0ef15697 1189 #endif // EVT_TIME_PROFILE
uci1 8:95a325df1f6b 1190 // make new seq?
uci1 8:95a325df1f6b 1191 if (IsSeqComplete()) {
uci1 12:d472f9811262 1192 #ifdef DEBUG
uci1 10:3c93db1cfb12 1193 printf("seq complete. sngseq=%d\r\n",gConf.IsSingleSeqRunMode());
uci1 41:d6f5e2f09e07 1194 printf("WriteTrigWaitWinTime (stop)\r\n");
uci1 12:d472f9811262 1195 #endif
uci1 67:ec999336fcd1 1196 led1 = 1; led2 = 1; led4 = 1; // signal saving file
uci1 97:9f3fe603e8b5 1197 gClkSet.UpdateClock( gSinceClkSet );
uci1 40:1324da35afd4 1198 SnSDUtils::WriteTrigWaitWinTime(SnSDUtils::GetCurFile(),
uci1 40:1324da35afd4 1199 gClkSet,
uci1 40:1324da35afd4 1200 false);
uci1 84:80b15993944e 1201 gStTrgStopClk = gClkSet;
uci1 8:95a325df1f6b 1202 MakeOutputFile(gConf.IsSingleSeqRunMode());
uci1 22:f957c4f840ad 1203 gFirstEvt = true;
uci1 40:1324da35afd4 1204 gThmTrgTimer.reset();
uci1 40:1324da35afd4 1205 gAllTrgTimer.reset();
uci1 22:f957c4f840ad 1206 etms=0;
uci1 67:ec999336fcd1 1207 led1 = 1; led2 = 0; led4 = 0; // end signal saving file
uci1 8:95a325df1f6b 1208 }
uci1 12:d472f9811262 1209 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1210 gProfiler.stop(); aftNewSeq=gProfiler.read_us(); gProfiler.start();
uci1 56:0bba0ef15697 1211 #endif // EVT_TIME_PROFILE
uci1 12:d472f9811262 1212
uci1 12:d472f9811262 1213 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1214 gProfiler.stop(); endOfLoop=gProfiler.read_us(); gProfiler.start();
uci1 84:80b15993944e 1215 printf("befSaveEvt=%d, aftSaveEvt=%d, "
uci1 12:d472f9811262 1216 "befChkPow=%d, aftChkPow=%d, befNewSeq=%d, aftNewSeq=%d, endOfLoop=%d\r\n",
uci1 84:80b15993944e 1217 befSaveEvt, aftSaveEvt,
uci1 12:d472f9811262 1218 befChkPow, aftChkPow, befNewSeq, aftNewSeq, endOfLoop);
uci1 56:0bba0ef15697 1219 #endif // EVT_TIME_PROFILE
uci1 41:d6f5e2f09e07 1220
uci1 41:d6f5e2f09e07 1221 /*
uci1 15:f2569d8e4176 1222 // get ready to trigger
uci1 15:f2569d8e4176 1223 PIN_spi.format( 16, 1 ); // change to data readout format
uci1 15:f2569d8e4176 1224 PIN_spi.frequency( 10000000 ); // Max is 12.5 MHz
uci1 41:d6f5e2f09e07 1225 */
uci1 22:f957c4f840ad 1226
uci1 21:ce51bb0ba4a5 1227 // reset event
uci1 22:f957c4f840ad 1228 // clear after comm win, so full event can be sent with status
uci1 22:f957c4f840ad 1229 // but don't clear counters or trigger bits, as
uci1 84:80b15993944e 1230 // gEvent.ClearEvent(true);
uci1 21:ce51bb0ba4a5 1231
uci1 41:d6f5e2f09e07 1232 } // end while (true)
uci1 0:664899e0b988 1233
uci1 0:664899e0b988 1234 }
uci1 0:664899e0b988 1235
uci1 0:664899e0b988 1236 //
uci1 22:f957c4f840ad 1237 // save a heartbeat tag
uci1 22:f957c4f840ad 1238 //
uci1 22:f957c4f840ad 1239 void SaveHeartbeat() {
uci1 22:f957c4f840ad 1240 #ifdef DEBUG
uci1 84:80b15993944e 1241 printf("save heartbeat #%u, time %u\r\n",
uci1 84:80b15993944e 1242 gHrtbt.GetNum(), gHrtbt.GetTime());
uci1 22:f957c4f840ad 1243 #endif
uci1 84:80b15993944e 1244 // save to SD
uci1 56:0bba0ef15697 1245 #if CHIPBOARD==ATWD4CH
uci1 84:80b15993944e 1246 PIN_lockRegisters = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 1247 #else
uci1 84:80b15993944e 1248 PIN_readingData = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 1249 #endif
uci1 84:80b15993944e 1250 SnSDUtils::WriteHeartbeatTo(SnSDUtils::GetCurFile(), gHrtbt);
uci1 22:f957c4f840ad 1251 }
uci1 22:f957c4f840ad 1252
uci1 22:f957c4f840ad 1253 //
uci1 0:664899e0b988 1254 // save the event
uci1 0:664899e0b988 1255 //
uci1 0:664899e0b988 1256 void SaveEvent(const int32_t etms) {
uci1 0:664899e0b988 1257 // write the event
uci1 12:d472f9811262 1258
uci1 12:d472f9811262 1259 #ifdef DEBUG
uci1 84:80b15993944e 1260 // check that the event is still the same as gLastEvent
uci1 84:80b15993944e 1261 /*
uci1 84:80b15993944e 1262 bool esame = gEvent.GetMbedTime() == gLastEvent.GetMbedTime();
uci1 84:80b15993944e 1263 esame &= gEvent.GetEvtNum() == gLastEvent.GetEvtNum();
uci1 84:80b15993944e 1264 esame &= gEvent.GetDTms() == gLastEvent.GetDTms();
uci1 84:80b15993944e 1265 esame &= gEvent.GetTrgNum() == gLastEvent.GetTrgNum();
uci1 84:80b15993944e 1266 esame &= gEvent.GetTrgBits() == gLastEvent.GetTrgBits();
uci1 84:80b15993944e 1267 esame &= gEvent.GetCRC() == gLastEvent.GetCRC();
uci1 84:80b15993944e 1268 for (uint16_t i=0; i<kTotSamps; ++i) {
uci1 84:80b15993944e 1269 esame &= (gEvent.GetData())[i] == (gLastEvent.GetData())[i];
uci1 84:80b15993944e 1270 }
uci1 84:80b15993944e 1271 #if CHIPBOARD!=ATWD4CH
uci1 84:80b15993944e 1272 for (uint16_t i=0; i<kNstopBytes; ++i) {
uci1 84:80b15993944e 1273 esame &= (gEvent.GetStop())[i] == (gLastEvent.GetStop())[i];
uci1 84:80b15993944e 1274 }
uci1 84:80b15993944e 1275 printf("EEEEEEEE event==lastEvt = %s\r\n", (esame?"true":"false"));
uci1 84:80b15993944e 1276 #endif
uci1 84:80b15993944e 1277 */
uci1 84:80b15993944e 1278 #endif
uci1 84:80b15993944e 1279
uci1 84:80b15993944e 1280 // ok, now we can overwrite the old gEvent data
uci1 84:80b15993944e 1281 // reset event
uci1 84:80b15993944e 1282 gEvent.ClearEvent(true, true);
uci1 84:80b15993944e 1283
uci1 84:80b15993944e 1284 // read data & calc CRC
uci1 84:80b15993944e 1285 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1286 int befReadWv=0, aftReadWv=0, befWriteEvt=0, aftWriteEvt=0;
uci1 84:80b15993944e 1287 gProfiler.stop(); befReadWv=gProfiler.read_us(); gProfiler.start();
uci1 84:80b15993944e 1288 #endif // EVT_TIME_PROFILE
uci1 84:80b15993944e 1289
uci1 84:80b15993944e 1290 #if CHIPBOARD==ATWD4CH
uci1 84:80b15993944e 1291 // get the data to the MBED
uci1 84:80b15993944e 1292 gEvent.ReadWaveformsATWD(PIN_spi, PIN_selCardHiBit, PIN_selCardLoBit);
uci1 84:80b15993944e 1293 #else
uci1 84:80b15993944e 1294 gEvent.ReadWaveformsSST(PIN_spi, PIN_readingData);
uci1 84:80b15993944e 1295 // reset in case a trigger arrived before we were ready
uci1 84:80b15993944e 1296 PIN_ResetChips = 1;
uci1 84:80b15993944e 1297 // wait_us(1);
uci1 84:80b15993944e 1298 PIN_ResetChips = 0;
uci1 84:80b15993944e 1299 #endif //ATWD4CH
uci1 84:80b15993944e 1300
uci1 84:80b15993944e 1301 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1302 gProfiler.stop(); aftReadWv=gProfiler.read_us(); gProfiler.start();
uci1 84:80b15993944e 1303 #endif // EVT_TIME_PROFILE
uci1 84:80b15993944e 1304
uci1 84:80b15993944e 1305 gEvent.SetCurMbedTime();
uci1 84:80b15993944e 1306
uci1 84:80b15993944e 1307 Watchdog::kick(); // don't reset!
uci1 84:80b15993944e 1308
uci1 84:80b15993944e 1309 #ifdef DEBUG
uci1 84:80b15993944e 1310 printf("gFirstEvt=%s\r\n",gFirstEvt?"true":"false");
uci1 84:80b15993944e 1311 #endif
uci1 84:80b15993944e 1312
uci1 84:80b15993944e 1313 #if CHIPBOARD==ATWD4CH
uci1 84:80b15993944e 1314 PIN_lockRegisters = 0; // done reading, unlock so we can talk to the SD card
uci1 84:80b15993944e 1315 #else
uci1 84:80b15993944e 1316 // (this is redundant; it's already set low by SnEventFrame)
uci1 84:80b15993944e 1317 PIN_readingData = 0; // done reading, unlock so we can talk to the SD card
uci1 84:80b15993944e 1318 #endif // ATWD4CH
uci1 84:80b15993944e 1319
uci1 84:80b15993944e 1320 #ifdef DEBUG
uci1 84:80b15993944e 1321 printf("waveform read out. save event (%u)\r\n", gEvtNum);
uci1 12:d472f9811262 1322 #endif
uci1 3:24c5f0f50bf1 1323
uci1 0:664899e0b988 1324 // set the event number & dt
uci1 3:24c5f0f50bf1 1325 gEvent.SetEvtNum(gEvtNum);
uci1 0:664899e0b988 1326 gEvent.SetDTms(etms);
uci1 84:80b15993944e 1327 // set trigger bits
uci1 84:80b15993944e 1328 if (gForcedTrig) {
uci1 84:80b15993944e 1329 gEvent.SetTrgBit(kForced);
uci1 84:80b15993944e 1330 // gEvent.SetTrgNum(gTrgNum[kFrcTrg]);
uci1 84:80b15993944e 1331 gEvent.SetTrgNum(gNumFrcTrigs);
uci1 84:80b15993944e 1332 } else {
uci1 84:80b15993944e 1333 gEvent.SetTrgBit(kThermal);
uci1 84:80b15993944e 1334 // gEvent.SetTrgNum(gTrgNum[kThmTrg]);
uci1 84:80b15993944e 1335 gEvent.SetTrgNum(gNumThmTrigs);
uci1 84:80b15993944e 1336 }
uci1 84:80b15993944e 1337 if (gAdcToMBflag) {
uci1 84:80b15993944e 1338 gEvent.SetTrgBit(kAdcToMBflag);
uci1 84:80b15993944e 1339 }
uci1 0:664899e0b988 1340
uci1 84:80b15993944e 1341 // this is in the config too, but doesn't hurt to flip the bit
uci1 84:80b15993944e 1342 // in the event
uci1 84:80b15993944e 1343 if (gConf.IsL1TrigApplied()) {
uci1 84:80b15993944e 1344 gEvent.SetTrgBit(kL1TrgApplied);
uci1 84:80b15993944e 1345 }
uci1 84:80b15993944e 1346
uci1 84:80b15993944e 1347 // ----
uci1 84:80b15993944e 1348 // L1 check(s) go here!
uci1 84:80b15993944e 1349 bool L1okToSave = true;
uci1 84:80b15993944e 1350
uci1 84:80b15993944e 1351 #ifdef DEBUG
uci1 84:80b15993944e 1352 Timer l1timer;
uci1 84:80b15993944e 1353 l1timer.start();
uci1 84:80b15993944e 1354 printf("L1 single freq supp ratio = %hhu (%g)\r\n",
uci1 84:80b15993944e 1355 gConf.GetSingleFreqSuppRatioRaw(),
uci1 84:80b15993944e 1356 gConf.GetSingleFreqSuppRatio());
uci1 84:80b15993944e 1357 #endif
uci1 84:80b15993944e 1358
uci1 84:80b15993944e 1359 // TODO: move the FFT calculation out here so that
uci1 84:80b15993944e 1360 // other L1's could use it too. haven't done this already
uci1 84:80b15993944e 1361 // in order to save RAM and not cache the whole thing when
uci1 84:80b15993944e 1362 // we only have one L1 cut.
uci1 84:80b15993944e 1363
uci1 84:80b15993944e 1364 // check L1 single frequency suppression cut
uci1 84:80b15993944e 1365 if ( gConf.IsSingleFreqSuppEnabled() ) {
uci1 84:80b15993944e 1366 const EL1TrigStatus passL1SingleFreqSupp =
uci1 84:80b15993944e 1367 SnL1SingleFreqSupp::ProcessEvent(gEvent, gChanFFT,
uci1 84:80b15993944e 1368 gConf.GetSingleFreqSuppRatio());
uci1 84:80b15993944e 1369 #ifdef DEBUG
uci1 84:80b15993944e 1370 l1timer.stop();
uci1 84:80b15993944e 1371 printf("L1 single freq supp took [%d] us\r\n",
uci1 84:80b15993944e 1372 l1timer.read_us());
uci1 84:80b15993944e 1373 printf("passL1SingleFreqSupp=%s\r\n",
uci1 84:80b15993944e 1374 passL1SingleFreqSupp==kL1Pass ? "pass"
uci1 84:80b15993944e 1375 : passL1SingleFreqSupp==kL1Fail ? "fail"
uci1 84:80b15993944e 1376 : "other");
uci1 84:80b15993944e 1377 #endif
uci1 84:80b15993944e 1378 if (passL1SingleFreqSupp==kL1Pass) {
uci1 84:80b15993944e 1379 gEvent.SetTrgBit(kSingleFreqSupp);
uci1 84:80b15993944e 1380 } else if ( (passL1SingleFreqSupp==kL1Fail) &&
uci1 84:80b15993944e 1381 gConf.IsL1TrigApplied() ) {
uci1 84:80b15993944e 1382 L1okToSave = false;
uci1 84:80b15993944e 1383 }
uci1 84:80b15993944e 1384 // else if kL1UnableToProcess, the bit won't get set
uci1 84:80b15993944e 1385 // but the event can/will be saved
uci1 84:80b15993944e 1386 }
uci1 84:80b15993944e 1387
uci1 84:80b15993944e 1388
uci1 84:80b15993944e 1389 // NO MORE L1 checks below here! (or the scaledown won't work)
uci1 84:80b15993944e 1390 // -----
uci1 84:80b15993944e 1391
uci1 84:80b15993944e 1392 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1393 gProfiler.stop(); befWriteEvt=gProfiler.read_us(); gProfiler.start();
uci1 84:80b15993944e 1394 #endif // EVT_TIME_PROFILE
uci1 84:80b15993944e 1395
uci1 0:664899e0b988 1396 // save to SD
uci1 56:0bba0ef15697 1397 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 1398 PIN_lockRegisters = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 1399 #else
uci1 56:0bba0ef15697 1400 PIN_readingData = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 1401 #endif
uci1 84:80b15993944e 1402
uci1 84:80b15993944e 1403 // scale down to override L1 trigger failures
uci1 84:80b15993944e 1404 if ( (L1okToSave==false) && (gConf.GetL1Scaledown()!=0) ) {
uci1 84:80b15993944e 1405 ++gL1ScaledownCount;
uci1 84:80b15993944e 1406
uci1 84:80b15993944e 1407 if ( gL1ScaledownCount == gConf.GetL1Scaledown() ) {
uci1 84:80b15993944e 1408 gL1ScaledownCount = 0;
uci1 84:80b15993944e 1409 L1okToSave = true;
uci1 84:80b15993944e 1410 #ifdef DEBUG
uci1 84:80b15993944e 1411 printf("))) L1 scaledown!\r\n");
uci1 84:80b15993944e 1412 #endif
uci1 84:80b15993944e 1413 }
uci1 84:80b15993944e 1414 }
uci1 84:80b15993944e 1415
uci1 84:80b15993944e 1416 #ifdef DEBUG
uci1 84:80b15993944e 1417 printf("L1 scaledown count = %hhu, scaledown=%hhu, L1okToSave=%s\r\n",
uci1 84:80b15993944e 1418 gL1ScaledownCount,
uci1 84:80b15993944e 1419 gConf.GetL1Scaledown(),
uci1 84:80b15993944e 1420 L1okToSave ? "true" : "false");
uci1 84:80b15993944e 1421 printf("event trigger bits = ");
uci1 84:80b15993944e 1422 SnBitUtils::printBits(gEvent.GetTrgBits(), true);
uci1 84:80b15993944e 1423 #endif
uci1 0:664899e0b988 1424
uci1 84:80b15993944e 1425 // always save forced triggers
uci1 84:80b15993944e 1426 if (L1okToSave || gForcedTrig) {
uci1 84:80b15993944e 1427 SnSDUtils::WriteEventTo(SnSDUtils::GetCurFile(), gGenBuf, gEvent, gConf);
uci1 84:80b15993944e 1428
uci1 84:80b15993944e 1429 // a good event
uci1 84:80b15993944e 1430 gStNewEvent = true;
uci1 84:80b15993944e 1431
uci1 84:80b15993944e 1432 // send it?
uci1 84:80b15993944e 1433 if ( gConf.IsCommWindowEachEvent() ) {
uci1 84:80b15993944e 1434 #ifdef DEBUG
uci1 84:80b15993944e 1435 printf("COMM EACH EVENT => gOpenCommWin = true\r\n");
uci1 84:80b15993944e 1436 #endif
uci1 84:80b15993944e 1437 gOpenCommWin = true;
uci1 84:80b15993944e 1438 }
uci1 84:80b15993944e 1439 }
uci1 84:80b15993944e 1440
uci1 84:80b15993944e 1441 #ifdef EVT_TIME_PROFILE
uci1 84:80b15993944e 1442 gProfiler.stop(); aftWriteEvt=gProfiler.read_us(); gProfiler.start();
uci1 84:80b15993944e 1443 printf("befReadWv=%d, aftReadWv=%d, befWriteEvt=%d, aftWriteEvt=%d\r\n",
uci1 84:80b15993944e 1444 befReadWv, aftReadWv, befWriteEvt, aftWriteEvt);
uci1 84:80b15993944e 1445 #endif // EVT_TIME_PROFILE
uci1 84:80b15993944e 1446
uci1 40:1324da35afd4 1447 // make a copy in case we need to send it with the status
uci1 40:1324da35afd4 1448 // (copy it because we are going to clear this event while
uci1 40:1324da35afd4 1449 // waiting for the next trigger)
uci1 84:80b15993944e 1450 // gEvent.CopyTo(gLastEvent);
uci1 40:1324da35afd4 1451
uci1 3:24c5f0f50bf1 1452 // increment event number
uci1 3:24c5f0f50bf1 1453 ++gEvtNum;
uci1 3:24c5f0f50bf1 1454
uci1 12:d472f9811262 1455 #ifdef DEBUG
uci1 84:80b15993944e 1456 printf("next gEvtNum=%u\r\n",gEvtNum);
uci1 12:d472f9811262 1457 #endif
uci1 3:24c5f0f50bf1 1458 }
uci1 3:24c5f0f50bf1 1459
uci1 3:24c5f0f50bf1 1460 void MakeOutputFile(const bool stopRunning) {
uci1 56:0bba0ef15697 1461 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 1462 PIN_lockRegisters = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 1463 #else
uci1 56:0bba0ef15697 1464 PIN_readingData = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 1465 #endif
uci1 12:d472f9811262 1466 #ifdef DEBUG
uci1 10:3c93db1cfb12 1467 printf("closing output file. gEvtNum=%u, gPowNum=%u, stop=%d\r\n",
uci1 10:3c93db1cfb12 1468 gEvtNum,gPowNum,(int)stopRunning);
uci1 12:d472f9811262 1469 #endif
uci1 13:7a1fb885a8e4 1470
uci1 3:24c5f0f50bf1 1471 SnSDUtils::CloseOutputFile(SnSDUtils::GetCurFile());
uci1 13:7a1fb885a8e4 1472
uci1 12:d472f9811262 1473 #ifdef DEBUG
uci1 10:3c93db1cfb12 1474 printf("file closed\r\n");
uci1 12:d472f9811262 1475 #endif
uci1 3:24c5f0f50bf1 1476 if (stopRunning) {
uci1 8:95a325df1f6b 1477 StopRunning();
uci1 0:664899e0b988 1478 }
uci1 56:0bba0ef15697 1479 FILE* cf = SnSDUtils::OpenNewOutputFile(SnConfigFrame::GetMacAddress(),
uci1 40:1324da35afd4 1480 gConf.GetRun(),
uci1 76:f8383f0292c2 1481 gConf.GetFirstSeq(),
uci1 76:f8383f0292c2 1482 gConf.IsSendingFilesRunSeqList());
uci1 13:7a1fb885a8e4 1483 // reset event, timers, trigger counters
uci1 84:80b15993944e 1484 ResetCounters();
uci1 8:95a325df1f6b 1485 if (cf!=0) {
uci1 40:1324da35afd4 1486 #ifdef USE_RTOS
uci1 40:1324da35afd4 1487 Thread::wait(200);
uci1 40:1324da35afd4 1488 #else
uci1 8:95a325df1f6b 1489 wait_ms(200);
uci1 40:1324da35afd4 1490 #endif
uci1 8:95a325df1f6b 1491 GetAvePowerReading();
uci1 12:d472f9811262 1492 #ifdef DEBUG
uci1 8:95a325df1f6b 1493 printf("writing power. v1=%g, v2=%g, r1=%g, r2=%g, t=%u, pownum=%u\r\n",
uci1 8:95a325df1f6b 1494 gPower.GetAveV1(), gPower.GetAveV2(),
uci1 8:95a325df1f6b 1495 gPower.GetRmsV1(), gPower.GetRmsV2(), gPower.GetTime(),
uci1 8:95a325df1f6b 1496 gPowNum);
uci1 12:d472f9811262 1497 #endif
uci1 8:95a325df1f6b 1498 SnSDUtils::WritePowerTo(cf, gPower, gPowNum);
uci1 8:95a325df1f6b 1499 }
uci1 12:d472f9811262 1500 #ifdef DEBUG
uci1 3:24c5f0f50bf1 1501 printf("made output file with run %u\r\n",gConf.GetRun());
uci1 3:24c5f0f50bf1 1502 printf("filename=%s\r\n",SnSDUtils::GetCurFileName());
uci1 12:d472f9811262 1503 #endif
uci1 3:24c5f0f50bf1 1504 SnSDUtils::WriteConfig(SnSDUtils::GetCurFile(), gConf);
uci1 19:74155d652c37 1505 #ifdef DEBUG
uci1 19:74155d652c37 1506 printf("write config to file\r\n");
uci1 19:74155d652c37 1507 #endif
uci1 0:664899e0b988 1508 }
uci1 0:664899e0b988 1509
uci1 40:1324da35afd4 1510 bool PowerDownCommPeriph(const SnConfigFrame::EDatPackBit type) {
uci1 67:ec999336fcd1 1511 #ifdef DEBUG
uci1 67:ec999336fcd1 1512 printf("PowerDownCommPeriph: type=%d\r\n",(int)type);
uci1 67:ec999336fcd1 1513 #endif
uci1 40:1324da35afd4 1514 SnCommWin** cw = gComms;
uci1 56:0bba0ef15697 1515 for (uint8_t i=0; i<kNcomms; ++i, ++cw) {
uci1 40:1324da35afd4 1516 if ((*cw)==0) {
uci1 40:1324da35afd4 1517 continue;
uci1 40:1324da35afd4 1518 } else if ((*cw)->GetCommType()==type) {
uci1 67:ec999336fcd1 1519 #ifdef DEBUG
uci1 67:ec999336fcd1 1520 printf("calling PowerDown\r\n");
uci1 67:ec999336fcd1 1521 #endif
uci1 40:1324da35afd4 1522 return (*cw)->PowerDown(gConf.GetTimeoutTime(time(0),
uci1 84:80b15993944e 1523 gConf.GetCommWinConnectTO(type)));
uci1 40:1324da35afd4 1524 }
uci1 40:1324da35afd4 1525 }
uci1 40:1324da35afd4 1526 return false;
uci1 40:1324da35afd4 1527 }
uci1 40:1324da35afd4 1528
uci1 0:664899e0b988 1529 //
uci1 4:a91682e19d6b 1530 // power stuff
uci1 4:a91682e19d6b 1531 //
uci1 67:ec999336fcd1 1532 bool IsCurrentlyPowered(const SnConfigFrame::EPowerModeBit p,
uci1 67:ec999336fcd1 1533 DigitalOut& pin) {
uci1 67:ec999336fcd1 1534 // check if the current pin value is equal to
uci1 67:ec999336fcd1 1535 // what it should be if the peripheral is on
uci1 67:ec999336fcd1 1536 return gConf.GetPowPinSetting(p, true) == pin.read();
uci1 67:ec999336fcd1 1537 }
uci1 67:ec999336fcd1 1538
uci1 84:80b15993944e 1539 void ChangeCardPower(const bool isCommWin,
uci1 84:80b15993944e 1540 const bool isOn) {
uci1 67:ec999336fcd1 1541 // change cards power
uci1 67:ec999336fcd1 1542 const SnConfigFrame::EPowerModeBit pbit = (isCommWin)
uci1 67:ec999336fcd1 1543 ? SnConfigFrame::kCardComWin
uci1 67:ec999336fcd1 1544 : SnConfigFrame::kCardDatTak;
uci1 84:80b15993944e 1545 const int value = gConf.GetPowPinSetting(pbit, isOn);
uci1 21:ce51bb0ba4a5 1546 #ifdef DEBUG
uci1 67:ec999336fcd1 1547 printf("setting cards pin power to %d (comm=%d)\r\n",
uci1 67:ec999336fcd1 1548 value, static_cast<int>(isCommWin));
uci1 21:ce51bb0ba4a5 1549 #endif
uci1 67:ec999336fcd1 1550 PIN_turn_on_system = value;
uci1 40:1324da35afd4 1551 #ifdef USE_RTOS
uci1 40:1324da35afd4 1552 Thread::wait(10);
uci1 40:1324da35afd4 1553 #else
uci1 30:f869ed4bcc08 1554 wait_ms(10);
uci1 40:1324da35afd4 1555 #endif
uci1 67:ec999336fcd1 1556 }
uci1 67:ec999336fcd1 1557
uci1 84:80b15993944e 1558 void ChangeAmpsPower(const bool isCommWin,
uci1 84:80b15993944e 1559 const bool isOn) {
uci1 40:1324da35afd4 1560 // change amps power
uci1 67:ec999336fcd1 1561 const SnConfigFrame::EPowerModeBit pbit = (isCommWin)
uci1 67:ec999336fcd1 1562 ? SnConfigFrame::kAmpsComWin
uci1 67:ec999336fcd1 1563 : SnConfigFrame::kAmpsDatTak;
uci1 84:80b15993944e 1564 const int value = gConf.GetPowPinSetting(pbit, isOn);
uci1 40:1324da35afd4 1565 #ifdef DEBUG
uci1 67:ec999336fcd1 1566 printf("setting amps pin power to %d (comm=%d)\r\n",
uci1 67:ec999336fcd1 1567 value, static_cast<int>(isCommWin));
uci1 40:1324da35afd4 1568 #endif
uci1 67:ec999336fcd1 1569 PIN_turn_on_amps = value;
uci1 40:1324da35afd4 1570 #ifdef USE_RTOS
uci1 40:1324da35afd4 1571 Thread::wait(10);
uci1 40:1324da35afd4 1572 #else
uci1 30:f869ed4bcc08 1573 wait_ms(10);
uci1 40:1324da35afd4 1574 #endif
uci1 67:ec999336fcd1 1575 }
uci1 67:ec999336fcd1 1576
uci1 84:80b15993944e 1577 void ChangeIridPower(const bool isCommWin,
uci1 84:80b15993944e 1578 const bool isOn) {
uci1 67:ec999336fcd1 1579 // change iridium power setting
uci1 67:ec999336fcd1 1580 // if going from ON to OFF, call the special
uci1 67:ec999336fcd1 1581 // power down procedure, so as not to lose
uci1 67:ec999336fcd1 1582 // the non-volatile memory settings
uci1 67:ec999336fcd1 1583
uci1 67:ec999336fcd1 1584 const SnConfigFrame::EPowerModeBit ibit = (isCommWin)
uci1 67:ec999336fcd1 1585 ? SnConfigFrame::kIridComWin
uci1 67:ec999336fcd1 1586 : SnConfigFrame::kIridDatTak;
uci1 67:ec999336fcd1 1587 const SnConfigFrame::EPowerModeBit abit = (isCommWin)
uci1 67:ec999336fcd1 1588 ? SnConfigFrame::kAfarComWin
uci1 67:ec999336fcd1 1589 : SnConfigFrame::kAfarDatTak;
uci1 67:ec999336fcd1 1590
uci1 67:ec999336fcd1 1591 // these checks are complicated because the iridium might
uci1 67:ec999336fcd1 1592 // be powered off the Afar (12V) relay,
uci1 67:ec999336fcd1 1593 // rather than the iridium (5V) relay
uci1 67:ec999336fcd1 1594 const bool iridFromOn = (kIridPwrFromAfar) ?
uci1 67:ec999336fcd1 1595 IsCurrentlyPowered(abit, PIN_afar_power) :
uci1 67:ec999336fcd1 1596 IsCurrentlyPowered(ibit, PIN_iridSbd_power);
uci1 84:80b15993944e 1597 if ( iridFromOn && (isOn==false) ) {
uci1 40:1324da35afd4 1598 #ifdef DEBUG
uci1 40:1324da35afd4 1599 printf("calling PowerDown for Iridium\r\n");
uci1 40:1324da35afd4 1600 #endif
uci1 40:1324da35afd4 1601 PowerDownCommPeriph(SnConfigFrame::kIrid);
uci1 40:1324da35afd4 1602 }
uci1 67:ec999336fcd1 1603 const int value = (kIridPwrFromAfar)
uci1 67:ec999336fcd1 1604 ? gConf.GetPowPinSetting(ibit, false) // leave the iridium relay off. use afar relay.
uci1 84:80b15993944e 1605 : gConf.GetPowPinSetting(ibit, isOn);
uci1 40:1324da35afd4 1606 #ifdef DEBUG
uci1 67:ec999336fcd1 1607 printf("setting iridium pin power to %d (comm=%d)\r\n",
uci1 67:ec999336fcd1 1608 value, static_cast<int>(isCommWin));
uci1 40:1324da35afd4 1609 #endif
uci1 67:ec999336fcd1 1610 PIN_iridSbd_power = value;
uci1 40:1324da35afd4 1611 #ifdef USE_RTOS
uci1 40:1324da35afd4 1612 Thread::wait(10);
uci1 40:1324da35afd4 1613 #else
uci1 30:f869ed4bcc08 1614 wait_ms(10);
uci1 40:1324da35afd4 1615 #endif
uci1 67:ec999336fcd1 1616
uci1 67:ec999336fcd1 1617 }
uci1 67:ec999336fcd1 1618
uci1 84:80b15993944e 1619 void ChangeAfarPower(const bool isCommWin,
uci1 84:80b15993944e 1620 const bool isOn) {
uci1 67:ec999336fcd1 1621 // change the AFAR relay power setting
uci1 67:ec999336fcd1 1622 // also power up or down the ethernet PHY port
uci1 67:ec999336fcd1 1623 // as appropriate
uci1 67:ec999336fcd1 1624 // the procedure is complicated by the fact that
uci1 67:ec999336fcd1 1625 // the iridium may be powered off the Afar (12V) relay,
uci1 67:ec999336fcd1 1626 // in which case we need to turn this relay on if
uci1 67:ec999336fcd1 1627 // *either* Afar or iridium want power
uci1 67:ec999336fcd1 1628 #ifdef DEBUG
uci1 67:ec999336fcd1 1629 printf("bef: pconp=%u (%08x), pcenet=%u (%08x)\r\n",
uci1 67:ec999336fcd1 1630 LPC_SC->PCONP, LPC_SC->PCONP, LPC1768_PCONP_PCENET, LPC1768_PCONP_PCENET);
uci1 67:ec999336fcd1 1631 printf("pcenet bef power: status=%d\r\n",Peripheral_GetStatus(LPC1768_PCONP_PCENET));
uci1 67:ec999336fcd1 1632 #endif
uci1 67:ec999336fcd1 1633
uci1 67:ec999336fcd1 1634 const SnConfigFrame::EPowerModeBit abit = (isCommWin)
uci1 67:ec999336fcd1 1635 ? SnConfigFrame::kAfarComWin
uci1 67:ec999336fcd1 1636 : SnConfigFrame::kAfarDatTak;
uci1 67:ec999336fcd1 1637
uci1 67:ec999336fcd1 1638 const bool afarFromOn = IsCurrentlyPowered(abit, PIN_afar_power);
uci1 67:ec999336fcd1 1639
uci1 40:1324da35afd4 1640 // change ethernet PHY port power
uci1 21:ce51bb0ba4a5 1641 #ifdef DEBUG
uci1 67:ec999336fcd1 1642 printf("afar pin=%d, afarFromOn=%d, afarToOn=%d\r\n",
uci1 67:ec999336fcd1 1643 PIN_afar_power.read(), static_cast<int>(afarFromOn),
uci1 84:80b15993944e 1644 static_cast<int>(isOn));
uci1 21:ce51bb0ba4a5 1645 #endif
uci1 84:80b15993944e 1646 if (isOn) {
uci1 21:ce51bb0ba4a5 1647 #ifdef DEBUG
uci1 30:f869ed4bcc08 1648 printf("PHY cowin powering up\r\n");
uci1 21:ce51bb0ba4a5 1649 #endif
uci1 40:1324da35afd4 1650 PHY_PowerUp();
uci1 40:1324da35afd4 1651 #ifdef USE_RTOS
uci1 40:1324da35afd4 1652 Thread::wait(1000);
uci1 40:1324da35afd4 1653 #else
uci1 40:1324da35afd4 1654 wait(1);
uci1 40:1324da35afd4 1655 #endif
uci1 21:ce51bb0ba4a5 1656 #ifdef DEBUG
uci1 30:f869ed4bcc08 1657 printf("PHY cowin powered up\r\n");
uci1 21:ce51bb0ba4a5 1658 #endif
uci1 4:a91682e19d6b 1659 } else {
uci1 40:1324da35afd4 1660 // change afar power
uci1 40:1324da35afd4 1661 // power down periph if going from on to off
uci1 40:1324da35afd4 1662 // change afar power
uci1 40:1324da35afd4 1663 if (afarFromOn) {
uci1 40:1324da35afd4 1664 PowerDownCommPeriph(SnConfigFrame::kAfar);
uci1 40:1324da35afd4 1665 }
uci1 21:ce51bb0ba4a5 1666 #ifdef DEBUG
uci1 30:f869ed4bcc08 1667 printf("PHY cowin powering down\r\n");
uci1 21:ce51bb0ba4a5 1668 #endif
uci1 40:1324da35afd4 1669 PHY_PowerDown();
uci1 40:1324da35afd4 1670 #ifdef USE_RTOS
uci1 40:1324da35afd4 1671 Thread::wait(1000);
uci1 40:1324da35afd4 1672 #else
uci1 40:1324da35afd4 1673 wait(1);
uci1 40:1324da35afd4 1674 #endif
uci1 21:ce51bb0ba4a5 1675 #ifdef DEBUG
uci1 30:f869ed4bcc08 1676 printf("PHY cowin powered down\r\n");
uci1 21:ce51bb0ba4a5 1677 #endif
uci1 30:f869ed4bcc08 1678 }
uci1 21:ce51bb0ba4a5 1679 #ifdef DEBUG
uci1 30:f869ed4bcc08 1680 printf("PHY done\r\n");
uci1 21:ce51bb0ba4a5 1681 #endif
uci1 40:1324da35afd4 1682 #ifdef USE_RTOS
uci1 40:1324da35afd4 1683 Thread::wait(100);
uci1 40:1324da35afd4 1684 #else
uci1 30:f869ed4bcc08 1685 wait_ms(100);
uci1 40:1324da35afd4 1686 #endif
uci1 67:ec999336fcd1 1687
uci1 40:1324da35afd4 1688 // change afar power
uci1 84:80b15993944e 1689 const int value = gConf.GetPowPinSetting(abit, isOn);
uci1 67:ec999336fcd1 1690 PIN_afar_power = value;
uci1 40:1324da35afd4 1691 #ifdef USE_RTOS
uci1 40:1324da35afd4 1692 Thread::wait(1500);
uci1 40:1324da35afd4 1693 #else
uci1 40:1324da35afd4 1694 wait(1.5);
uci1 40:1324da35afd4 1695 #endif
uci1 12:d472f9811262 1696 #ifdef DEBUG
uci1 21:ce51bb0ba4a5 1697 printf("aft: pconp=%u (%08x), pcenet=%u (%08x)\r\n",
uci1 21:ce51bb0ba4a5 1698 LPC_SC->PCONP, LPC_SC->PCONP, LPC1768_PCONP_PCENET, LPC1768_PCONP_PCENET);
uci1 67:ec999336fcd1 1699 printf("pcenet aft power: status=%d\r\n",Peripheral_GetStatus(LPC1768_PCONP_PCENET));
uci1 21:ce51bb0ba4a5 1700 #endif
uci1 67:ec999336fcd1 1701
uci1 67:ec999336fcd1 1702 }
uci1 67:ec999336fcd1 1703
uci1 84:80b15993944e 1704 bool IsPowerAllowedFor(const bool isCommWin,
uci1 84:80b15993944e 1705 const uint8_t devicesInUse,
uci1 84:80b15993944e 1706 const SnConfigFrame::EDatPackBit b) {
uci1 84:80b15993944e 1707 if (isCommWin && (gConf.IsCommPowerSimple()==false)) {
uci1 84:80b15993944e 1708 return ( (devicesInUse & b)!=0 );
uci1 84:80b15993944e 1709 }
uci1 84:80b15993944e 1710 return true;
uci1 84:80b15993944e 1711 }
uci1 84:80b15993944e 1712
uci1 84:80b15993944e 1713 void SetPower(const bool isCommWin,
uci1 84:80b15993944e 1714 const uint8_t devicesInUse) {
uci1 84:80b15993944e 1715 // devicesInUse could really just be a second set of "power mode" bits
uci1 84:80b15993944e 1716 // where the bit being on means "I want to change power for this device"
uci1 84:80b15993944e 1717 // but then.. how to handle the possibility that the bit word contains,
uci1 84:80b15993944e 1718 // for example, both bits AfarDatTak and AfarComWin being on?
uci1 84:80b15993944e 1719 // so instead, we keep the "isCommWin" boolean which forces the separation
uci1 84:80b15993944e 1720 // and deviceInUse is only applied when isCommWin==true
uci1 84:80b15993944e 1721 //
uci1 84:80b15993944e 1722 // multiple devices can be specified by, e.g., kIrid | kAfar
uci1 67:ec999336fcd1 1723 #ifdef DEBUG
uci1 67:ec999336fcd1 1724 printf("set power. isCommWin=%s\r\n",(isCommWin)?"true":"false");
uci1 67:ec999336fcd1 1725 printf("WD reset = %d\r\n",(int)Watchdog::didWatchdogReset());
uci1 67:ec999336fcd1 1726 printf("power word (%hhu): ",gConf.GetPowerMode()); SnBitUtils::printBits(gConf.GetPowerMode(),true);
uci1 67:ec999336fcd1 1727 printf("IsPoweredFor CardDatTak = %d\r\n",(int)gConf.IsPoweredFor(SnConfigFrame::kCardDatTak));
uci1 67:ec999336fcd1 1728 printf("IsPoweredFor AmpsDatTak = %d\r\n",(int)gConf.IsPoweredFor(SnConfigFrame::kAmpsDatTak));
uci1 67:ec999336fcd1 1729 printf("IsPoweredFor IridDatTak = %d\r\n",(int)gConf.IsPoweredFor(SnConfigFrame::kIridDatTak));
uci1 67:ec999336fcd1 1730 printf("IsPoweredFor AfarDatTak = %d\r\n",(int)gConf.IsPoweredFor(SnConfigFrame::kAfarDatTak));
uci1 67:ec999336fcd1 1731 printf("IsPoweredFor CardComWin = %d\r\n",(int)gConf.IsPoweredFor(SnConfigFrame::kCardComWin));
uci1 67:ec999336fcd1 1732 printf("IsPoweredFor AmpsComWin = %d\r\n",(int)gConf.IsPoweredFor(SnConfigFrame::kAmpsComWin));
uci1 67:ec999336fcd1 1733 printf("IsPoweredFor IridComWin = %d\r\n",(int)gConf.IsPoweredFor(SnConfigFrame::kIridComWin));
uci1 67:ec999336fcd1 1734 printf("IsPoweredFor AfarComWin = %d\r\n",(int)gConf.IsPoweredFor(SnConfigFrame::kAfarComWin));
uci1 84:80b15993944e 1735 printf("devicesInUse = %hhu\r\n", (uint8_t)devicesInUse);
uci1 84:80b15993944e 1736 printf("IsCommPowerSimple = %s\r\n", (gConf.IsCommPowerSimple() ? "true" : "false"));
uci1 67:ec999336fcd1 1737 #endif
uci1 67:ec999336fcd1 1738
uci1 67:ec999336fcd1 1739 const SnConfigFrame::EPowerModeBit cardpb = (isCommWin)
uci1 67:ec999336fcd1 1740 ? SnConfigFrame::kCardComWin
uci1 67:ec999336fcd1 1741 : SnConfigFrame::kCardDatTak;
uci1 67:ec999336fcd1 1742 const SnConfigFrame::EPowerModeBit ampspb = (isCommWin)
uci1 67:ec999336fcd1 1743 ? SnConfigFrame::kAmpsComWin
uci1 67:ec999336fcd1 1744 : SnConfigFrame::kAmpsDatTak;
uci1 67:ec999336fcd1 1745 const SnConfigFrame::EPowerModeBit iridpb = (isCommWin)
uci1 67:ec999336fcd1 1746 ? SnConfigFrame::kIridComWin
uci1 67:ec999336fcd1 1747 : SnConfigFrame::kIridDatTak;
uci1 67:ec999336fcd1 1748 const SnConfigFrame::EPowerModeBit afarpb = (isCommWin)
uci1 67:ec999336fcd1 1749 ? SnConfigFrame::kAfarComWin
uci1 67:ec999336fcd1 1750 : SnConfigFrame::kAfarDatTak;
uci1 67:ec999336fcd1 1751
uci1 67:ec999336fcd1 1752 //
uci1 67:ec999336fcd1 1753 // FIRST turn the things off that should be off.
uci1 67:ec999336fcd1 1754 // this prevents short periods of high power usage
uci1 67:ec999336fcd1 1755 //
uci1 67:ec999336fcd1 1756
uci1 84:80b15993944e 1757 const bool cardToOn = gConf.IsPoweredFor(cardpb);
uci1 84:80b15993944e 1758 const bool ampsToOn = gConf.IsPoweredFor(ampspb);
uci1 84:80b15993944e 1759
uci1 84:80b15993944e 1760 // these are complicated because iridium might
uci1 67:ec999336fcd1 1761 // be powered off of the afar line
uci1 84:80b15993944e 1762 // also ignore the devices in use if we're not in a comm window
uci1 67:ec999336fcd1 1763 const bool iridToOn = (kIridPwrFromAfar) ?
uci1 84:80b15993944e 1764 (gConf.IsPoweredFor(afarpb) && IsPowerAllowedFor(isCommWin, devicesInUse, SnConfigFrame::kIrid)) :
uci1 84:80b15993944e 1765 (gConf.IsPoweredFor(iridpb) && IsPowerAllowedFor(isCommWin, devicesInUse, SnConfigFrame::kIrid));
uci1 84:80b15993944e 1766 const bool afarToOn = (kIridPwrFromAfar) ?
uci1 84:80b15993944e 1767 ( (gConf.IsPoweredFor(afarpb) && IsPowerAllowedFor(isCommWin, devicesInUse, SnConfigFrame::kAfar))
uci1 84:80b15993944e 1768 ||(gConf.IsPoweredFor(iridpb) && IsPowerAllowedFor(isCommWin, devicesInUse, SnConfigFrame::kIrid)) ) :
uci1 84:80b15993944e 1769 (gConf.IsPoweredFor(afarpb) && IsPowerAllowedFor(isCommWin, devicesInUse, SnConfigFrame::kAfar));
uci1 67:ec999336fcd1 1770
uci1 84:80b15993944e 1771 if (cardToOn==false) {
uci1 67:ec999336fcd1 1772 #ifdef DEBUG
uci1 67:ec999336fcd1 1773 printf("power down cards\r\n");
uci1 67:ec999336fcd1 1774 #endif
uci1 84:80b15993944e 1775 ChangeCardPower(isCommWin, cardToOn);
uci1 67:ec999336fcd1 1776 }
uci1 84:80b15993944e 1777 if (ampsToOn==false) {
uci1 67:ec999336fcd1 1778 #ifdef DEBUG
uci1 67:ec999336fcd1 1779 printf("power down amps\r\n");
uci1 67:ec999336fcd1 1780 printf("ampspb=%d, is powered for =%d\r\n",
uci1 67:ec999336fcd1 1781 (int)ampspb,
uci1 67:ec999336fcd1 1782 (int)(gConf.IsPoweredFor(ampspb)));
uci1 67:ec999336fcd1 1783 printf("is powered amps dat tak = %d, amps com win = %d\r\n",
uci1 67:ec999336fcd1 1784 (int)(gConf.IsPoweredFor(SnConfigFrame::kAmpsDatTak)),
uci1 67:ec999336fcd1 1785 (int)(gConf.IsPoweredFor(SnConfigFrame::kAmpsComWin)));
uci1 67:ec999336fcd1 1786 #endif
uci1 84:80b15993944e 1787 ChangeAmpsPower(isCommWin, ampsToOn);
uci1 67:ec999336fcd1 1788 }
uci1 67:ec999336fcd1 1789 if (iridToOn==false) {
uci1 67:ec999336fcd1 1790 #ifdef DEBUG
uci1 67:ec999336fcd1 1791 printf("power down irid\r\n");
uci1 67:ec999336fcd1 1792 #endif
uci1 84:80b15993944e 1793 ChangeIridPower(isCommWin, iridToOn);
uci1 67:ec999336fcd1 1794 }
uci1 67:ec999336fcd1 1795 if (afarToOn==false) {
uci1 67:ec999336fcd1 1796 #ifdef DEBUG
uci1 67:ec999336fcd1 1797 printf("power down afar\r\n");
uci1 67:ec999336fcd1 1798 #endif
uci1 84:80b15993944e 1799 ChangeAfarPower(isCommWin, afarToOn);
uci1 67:ec999336fcd1 1800 }
uci1 67:ec999336fcd1 1801
uci1 67:ec999336fcd1 1802 //
uci1 67:ec999336fcd1 1803 // THEN turn on things that want to go on
uci1 67:ec999336fcd1 1804 //
uci1 84:80b15993944e 1805 if (cardToOn) {
uci1 67:ec999336fcd1 1806 #ifdef DEBUG
uci1 67:ec999336fcd1 1807 printf("power ON cards\r\n");
uci1 67:ec999336fcd1 1808 #endif
uci1 84:80b15993944e 1809 ChangeCardPower(isCommWin, cardToOn);
uci1 67:ec999336fcd1 1810 }
uci1 84:80b15993944e 1811 if (ampsToOn) {
uci1 67:ec999336fcd1 1812 #ifdef DEBUG
uci1 67:ec999336fcd1 1813 printf("power ON amps\r\n");
uci1 67:ec999336fcd1 1814 #endif
uci1 84:80b15993944e 1815 ChangeAmpsPower(isCommWin, ampsToOn);
uci1 67:ec999336fcd1 1816 }
uci1 67:ec999336fcd1 1817 if (iridToOn) {
uci1 67:ec999336fcd1 1818 #ifdef DEBUG
uci1 67:ec999336fcd1 1819 printf("power ON iridium\r\n");
uci1 67:ec999336fcd1 1820 #endif
uci1 84:80b15993944e 1821 ChangeIridPower(isCommWin, iridToOn);
uci1 67:ec999336fcd1 1822 }
uci1 67:ec999336fcd1 1823 if (afarToOn) {
uci1 67:ec999336fcd1 1824 #ifdef DEBUG
uci1 67:ec999336fcd1 1825 printf("power ON afar\r\n");
uci1 67:ec999336fcd1 1826 #endif
uci1 84:80b15993944e 1827 ChangeAfarPower(isCommWin, afarToOn);
uci1 67:ec999336fcd1 1828 }
uci1 67:ec999336fcd1 1829
uci1 21:ce51bb0ba4a5 1830 #ifdef DEBUG
uci1 16:744ce85aede2 1831 printf("power word (%hhu): ",gConf.GetPowerMode()); SnBitUtils::printBits(gConf.GetPowerMode(),true);
uci1 6:6f002d202f59 1832 printf("set power (iscom %d, pw %hhu): cards %d, amps %d, irid %d, afar %d\r\n",
uci1 6:6f002d202f59 1833 isCommWin, gConf.GetPowerMode(), PIN_turn_on_system.read(), PIN_turn_on_amps.read(),
uci1 6:6f002d202f59 1834 PIN_iridSbd_power.read(), PIN_afar_power.read());
uci1 12:d472f9811262 1835 #endif
uci1 4:a91682e19d6b 1836 }
uci1 4:a91682e19d6b 1837
uci1 4:a91682e19d6b 1838 //
uci1 0:664899e0b988 1839 // set configuration
uci1 0:664899e0b988 1840 //
uci1 1:e392595b4b76 1841 void SetConfigAndMakeOutputFile() {
uci1 12:d472f9811262 1842 #ifdef DEBUG
uci1 1:e392595b4b76 1843 printf("SetConfigAndMakeOutputFile\r\n");
uci1 12:d472f9811262 1844 #endif
uci1 1:e392595b4b76 1845
uci1 0:664899e0b988 1846 // restart watchdog
uci1 62:4b59c1eb429f 1847 #ifdef DEBUG
uci1 62:4b59c1eb429f 1848 printf("Restart watchdog with time [%u]\r\n",
uci1 62:4b59c1eb429f 1849 gConf.GetWatchdogPeriod());
uci1 62:4b59c1eb429f 1850 #endif
uci1 0:664899e0b988 1851 Watchdog::kick(gConf.GetWatchdogPeriod());
uci1 0:664899e0b988 1852
uci1 1:e392595b4b76 1853 // block (thermal) triggers during configuration
uci1 1:e392595b4b76 1854 PIN_enableThermTrig = 0;
uci1 56:0bba0ef15697 1855 #if CHIPBOARD==ATWD4CH
uci1 1:e392595b4b76 1856 PIN_ADC_CS = 1;
uci1 1:e392595b4b76 1857 PIN_DoNotRestartAllClocks = 1;
uci1 56:0bba0ef15697 1858 #endif
uci1 1:e392595b4b76 1859 PIN_forceTrigger = 0;
uci1 3:24c5f0f50bf1 1860 PIN_heartbeat = 0;
uci1 40:1324da35afd4 1861 #ifdef USE_RTOS
uci1 40:1324da35afd4 1862 Thread::wait(20);
uci1 40:1324da35afd4 1863 #else
uci1 1:e392595b4b76 1864 wait_ms(20);
uci1 40:1324da35afd4 1865 #endif
uci1 1:e392595b4b76 1866
uci1 22:f957c4f840ad 1867 gCommWinChecks = 0;
uci1 22:f957c4f840ad 1868 gNcommWinChecks = gConf.GetCommWinPeriod() / kCommWinLongPrdTk;
uci1 22:f957c4f840ad 1869
uci1 21:ce51bb0ba4a5 1870 if (AreCardsPowered(true)) {
uci1 8:95a325df1f6b 1871 // Set PLA value(s)
uci1 56:0bba0ef15697 1872 PIN_spi.format( 16, 0 ); // change mode for DAC & PLA value setting (with ATWD4CH)
uci1 8:95a325df1f6b 1873 PIN_spi.frequency(1000000);
uci1 8:95a325df1f6b 1874 PIN_MajLogHiBit=1;
uci1 8:95a325df1f6b 1875 PIN_MajLogLoBit=1;
uci1 8:95a325df1f6b 1876 PIN_enableThermTrig=0;
uci1 0:664899e0b988 1877
uci1 56:0bba0ef15697 1878 #if CHIPBOARD==ATWD4CH
uci1 8:95a325df1f6b 1879 uint16_t hi, lo;
uci1 8:95a325df1f6b 1880 PIN_PLA_cs=1;
uci1 40:1324da35afd4 1881 #ifdef USE_RTOS
uci1 40:1324da35afd4 1882 Thread::wait(4000);
uci1 40:1324da35afd4 1883 #else
uci1 8:95a325df1f6b 1884 wait(4);
uci1 40:1324da35afd4 1885 #endif
uci1 56:0bba0ef15697 1886 for (uint8_t pi=0; pi<kNplas; ++pi) {
uci1 8:95a325df1f6b 1887 if (pi < gConf.GetNumPlas()) {
uci1 8:95a325df1f6b 1888 SnConfigFrame::GetHiLoPlas(gConf.GetPla(pi), hi, lo);
uci1 8:95a325df1f6b 1889 PIN_spi.write(hi);
uci1 8:95a325df1f6b 1890 PIN_spi.write(lo);
uci1 12:d472f9811262 1891 #ifdef DEBUG
uci1 8:95a325df1f6b 1892 printf("pla hi %hu, lo %hu\r\n",hi,lo);
uci1 12:d472f9811262 1893 #endif
uci1 8:95a325df1f6b 1894 } else {
uci1 8:95a325df1f6b 1895 PIN_spi.write(kNoTrigPla); // hi
uci1 8:95a325df1f6b 1896 PIN_spi.write(kNoTrigPla); // lo
uci1 12:d472f9811262 1897 #ifdef DEBUG
uci1 8:95a325df1f6b 1898 printf("pla hi %hu, lo %hu\r\n",kNoTrigPla,kNoTrigPla);
uci1 12:d472f9811262 1899 #endif
uci1 8:95a325df1f6b 1900 }
uci1 8:95a325df1f6b 1901 Watchdog::kick();
uci1 0:664899e0b988 1902 }
uci1 40:1324da35afd4 1903 #ifdef USE_RTOS
uci1 40:1324da35afd4 1904 Thread::wait(3000);
uci1 40:1324da35afd4 1905 #else
uci1 8:95a325df1f6b 1906 wait(3);
uci1 40:1324da35afd4 1907 #endif
uci1 8:95a325df1f6b 1908 PIN_PLA_cs=0;
uci1 40:1324da35afd4 1909 #ifdef USE_RTOS
uci1 40:1324da35afd4 1910 Thread::wait(3000);
uci1 40:1324da35afd4 1911 #else
uci1 8:95a325df1f6b 1912 wait(3);
uci1 40:1324da35afd4 1913 #endif
uci1 0:664899e0b988 1914
uci1 56:0bba0ef15697 1915
uci1 8:95a325df1f6b 1916 // DAC values
uci1 8:95a325df1f6b 1917 //
uci1 8:95a325df1f6b 1918 // first 12 bits = DAC value
uci1 8:95a325df1f6b 1919 // next 2 bits = DAC ID
uci1 8:95a325df1f6b 1920 // last 2 bits = dFPGA ID
uci1 8:95a325df1f6b 1921 //
uci1 8:95a325df1f6b 1922 // But FPGA uses "gray encoding" which means only 1 bit
uci1 8:95a325df1f6b 1923 // can change at a time (of the last 4 bits). So even tho
uci1 8:95a325df1f6b 1924 // the card/dac# is encoded, the order is also important
uci1 8:95a325df1f6b 1925 // 0000 (dac0,card0), 0001 (dac0,card1), 0011 (dac0,card3), 0010 (dac0,card2),
uci1 8:95a325df1f6b 1926 // 0110 (dac1,card2), 0111 (dac1,card3), 0101 (dac1,card1), etc.
uci1 12:d472f9811262 1927 #ifdef DEBUG
uci1 8:95a325df1f6b 1928 printf("setting dacs\r\n");
uci1 12:d472f9811262 1929 #endif
uci1 8:95a325df1f6b 1930 uint16_t dv=0;
uci1 56:0bba0ef15697 1931 for (uint8_t i=0, gri=0; i<kTotDacs; ++i) {
uci1 8:95a325df1f6b 1932 // get the gray-codes for this iteration
uci1 8:95a325df1f6b 1933 gri = SnBitUtils::binToGray(i);
uci1 8:95a325df1f6b 1934
uci1 8:95a325df1f6b 1935 // build bit word
uci1 8:95a325df1f6b 1936 dv = static_cast<int>(gConf.GetDac(gri & 0x0003u, gri >> 2u));
uci1 8:95a325df1f6b 1937 dv <<= 4u;
uci1 8:95a325df1f6b 1938 dv |= gri;
uci1 8:95a325df1f6b 1939
uci1 12:d472f9811262 1940 #ifdef DEBUG
uci1 8:95a325df1f6b 1941 printf("dac %04x\r\n",dv);
uci1 12:d472f9811262 1942 #endif
uci1 8:95a325df1f6b 1943
uci1 8:95a325df1f6b 1944 // send to FPGA
uci1 8:95a325df1f6b 1945 PIN_start_fpga=1;
uci1 8:95a325df1f6b 1946 PIN_spi.write(dv);
uci1 8:95a325df1f6b 1947 PIN_start_fpga=0;
uci1 8:95a325df1f6b 1948
uci1 8:95a325df1f6b 1949 Watchdog::kick();
uci1 8:95a325df1f6b 1950
uci1 8:95a325df1f6b 1951 }
uci1 56:0bba0ef15697 1952 #else // SST
uci1 56:0bba0ef15697 1953
uci1 56:0bba0ef15697 1954 // set and/or & differential pins
uci1 56:0bba0ef15697 1955
uci1 56:0bba0ef15697 1956 // set DACs via I2C
uci1 56:0bba0ef15697 1957
uci1 56:0bba0ef15697 1958 uint16_t dv=0;
uci1 56:0bba0ef15697 1959 uint8_t dn=0;
uci1 56:0bba0ef15697 1960 uint8_t cmdAndDac[3];
uci1 56:0bba0ef15697 1961 for (uint8_t ch=0; ch<kNchans; ++ch) {
uci1 56:0bba0ef15697 1962 for (uint8_t dc=0; dc<kNchanDacs; ++dc) {
uci1 56:0bba0ef15697 1963 // for (uint16_t dc=kNchanDacs-1; dc>=0; --dc) { // first all the highs, then the lows
uci1 56:0bba0ef15697 1964 // for (int16_t ch=kNchans-1; ch>=0; --ch) { // chans in reverse order
uci1 56:0bba0ef15697 1965 bool dok = false;
uci1 56:0bba0ef15697 1966 for (uint8_t tries = 0; (tries<kMaxDacSetTries) && (dok==false); ++tries) {
uci1 56:0bba0ef15697 1967 #ifdef DEBUG
uci1 56:0bba0ef15697 1968 printf("start i2c for dc=%hhu, ch=%hhu, try=%hhu, dok=%s\r\n",
uci1 56:0bba0ef15697 1969 dc, ch, tries, (dok ? "true" : "false"));
uci1 56:0bba0ef15697 1970 printf("address 0x%hhx (%hhd) ", kAllLTC2657, kAllLTC2657);
uci1 56:0bba0ef15697 1971 SnBitUtils::printBits(kAllLTC2657, true);
uci1 56:0bba0ef15697 1972 #endif
uci1 56:0bba0ef15697 1973 // build data to send
uci1 56:0bba0ef15697 1974 // blame the engineers for this bizzare mapping from
uci1 56:0bba0ef15697 1975 // chan, threshold -> DAC number
uci1 56:0bba0ef15697 1976 dn = (kTotDacs-1)-(dc*kNchans)-ch;
uci1 56:0bba0ef15697 1977 if (dn>7) { // invalid code for LTC2657 dac chip
uci1 56:0bba0ef15697 1978 error("chan/dac combination too big for 3 bits!");
uci1 56:0bba0ef15697 1979 }
uci1 56:0bba0ef15697 1980 dn |= (kUpdateDacCmd<<4); // prefix with update DAC value command
uci1 56:0bba0ef15697 1981 #ifdef DEBUG
uci1 56:0bba0ef15697 1982 printf("dn=%hhu ", dn);
uci1 56:0bba0ef15697 1983 SnBitUtils::printBits(dn, true);
uci1 56:0bba0ef15697 1984 #endif
uci1 56:0bba0ef15697 1985 dv = (gConf.GetDac(ch, dc)) << 4; // put 0's at the end (12 bits of num then 4 zero bits)
uci1 56:0bba0ef15697 1986 #ifdef DEBUG
uci1 56:0bba0ef15697 1987 printf("dv=%hu\r\n",dv);
uci1 56:0bba0ef15697 1988 printf("ch=%hhu, dc=%hhu, dac=%hu\r\n",ch,dc,gConf.GetDac(ch,dc));
uci1 56:0bba0ef15697 1989 #endif
uci1 56:0bba0ef15697 1990 // mbed i2c.write seems to send it "backwards" from a (low endian) bit
uci1 56:0bba0ef15697 1991 // point of view.. i guess it's forwards from an intuitive pov?
uci1 56:0bba0ef15697 1992 cmdAndDac[0] = dn;
uci1 56:0bba0ef15697 1993 cmdAndDac[1] = (dv & 0xFF00u) >> 8; // 8 MSBs of 12 bit num first
uci1 56:0bba0ef15697 1994 cmdAndDac[2] = (dv & 0x00FFu); // 4 LSBs of 12 bit num followed by 4 zeros
uci1 56:0bba0ef15697 1995
uci1 56:0bba0ef15697 1996 #ifdef DEBUG
uci1 56:0bba0ef15697 1997 printf("cmdAndDac[0]="); SnBitUtils::printBits(cmdAndDac[2],true);
uci1 56:0bba0ef15697 1998 printf("cmdAndDac[1]="); SnBitUtils::printBits(cmdAndDac[1],true);
uci1 56:0bba0ef15697 1999 printf("cmdAndDac[2]="); SnBitUtils::printBits(cmdAndDac[0],true);
uci1 56:0bba0ef15697 2000 #endif
uci1 56:0bba0ef15697 2001 // try to send it
uci1 56:0bba0ef15697 2002 // TODO: if no ACK, is just re-trying the whole thing good enough?
uci1 56:0bba0ef15697 2003 // TODO: assign correct slave address for the DAC chip (this is a global address)
uci1 56:0bba0ef15697 2004 dok = PIN_i2c.write(kAllLTC2657,
uci1 56:0bba0ef15697 2005 reinterpret_cast<char*>(cmdAndDac),
uci1 56:0bba0ef15697 2006 3*sizeof(uint8_t))==0;
uci1 56:0bba0ef15697 2007 } // end try loop
uci1 56:0bba0ef15697 2008 }
uci1 56:0bba0ef15697 2009 }
uci1 56:0bba0ef15697 2010
uci1 56:0bba0ef15697 2011 #endif // CHIPBOARD
uci1 56:0bba0ef15697 2012
uci1 12:d472f9811262 2013 #ifdef DEBUG
uci1 8:95a325df1f6b 2014 printf("dacs set\r\n");
uci1 12:d472f9811262 2015 #endif
uci1 40:1324da35afd4 2016 #ifdef USE_RTOS
uci1 40:1324da35afd4 2017 Thread::wait(20);
uci1 40:1324da35afd4 2018 #else
uci1 8:95a325df1f6b 2019 wait_ms(20);
uci1 40:1324da35afd4 2020 #endif
uci1 8:95a325df1f6b 2021 } else {
uci1 12:d472f9811262 2022 #ifdef DEBUG
uci1 8:95a325df1f6b 2023 printf("cards off. skipping PLA and DAC setting\r\n");
uci1 12:d472f9811262 2024 #endif
uci1 0:664899e0b988 2025 }
uci1 56:0bba0ef15697 2026
uci1 56:0bba0ef15697 2027 #if CHIPBOARD==SST4CH
uci1 56:0bba0ef15697 2028 // set the SST triggering run mode
uci1 56:0bba0ef15697 2029 PIN_dualOrSingleThresholds = gConf.IsDualThresholdMode();
uci1 56:0bba0ef15697 2030 PIN_differentialTrigSignal = gConf.IsDifferentialTrigMode();
uci1 56:0bba0ef15697 2031 #endif
uci1 0:664899e0b988 2032
uci1 0:664899e0b988 2033 // Majority Logic Trigger selection (# of cards)
uci1 0:664899e0b988 2034 SnBitUtils::SetChanNumBits(gConf.GetNumCardsMajLog() - 1u,
uci1 0:664899e0b988 2035 PIN_MajLogHiBit, PIN_MajLogLoBit);
uci1 0:664899e0b988 2036
uci1 0:664899e0b988 2037 // Enable thermal trigger?
uci1 0:664899e0b988 2038 PIN_enableThermTrig = gConf.IsThermTrigEnabled();
uci1 0:664899e0b988 2039
uci1 56:0bba0ef15697 2040 #if CHIPBOARD==SST4CH
uci1 56:0bba0ef15697 2041 InitTempProbe();
uci1 56:0bba0ef15697 2042 #endif
uci1 56:0bba0ef15697 2043
uci1 0:664899e0b988 2044 PIN_spi.format( 16, 1 ); // back to trigger mode
uci1 1:e392595b4b76 2045 PIN_spi.frequency( 10000000 ); // Max is 12.5 MHz
uci1 1:e392595b4b76 2046
uci1 8:95a325df1f6b 2047 // make new output file
uci1 8:95a325df1f6b 2048 // put after PLA/DAC, in case they affect the power readings
uci1 40:1324da35afd4 2049 #ifdef USE_RTOS
uci1 40:1324da35afd4 2050 Thread::wait(200);
uci1 40:1324da35afd4 2051 #else
uci1 8:95a325df1f6b 2052 wait_ms(200);
uci1 40:1324da35afd4 2053 #endif
uci1 8:95a325df1f6b 2054 MakeOutputFile();
uci1 8:95a325df1f6b 2055
uci1 21:ce51bb0ba4a5 2056 // reset tickers
uci1 21:ce51bb0ba4a5 2057 ResetAllTickers();
uci1 0:664899e0b988 2058
uci1 0:664899e0b988 2059 Watchdog::kick(); // don't reset!
uci1 8:95a325df1f6b 2060
uci1 12:d472f9811262 2061 #ifdef DEBUG
uci1 8:95a325df1f6b 2062 printf("set config done\r\n");
uci1 12:d472f9811262 2063 #endif
uci1 0:664899e0b988 2064 }
uci1 0:664899e0b988 2065
uci1 0:664899e0b988 2066 //
uci1 0:664899e0b988 2067 // readout functions
uci1 0:664899e0b988 2068 //
uci1 0:664899e0b988 2069 void WaitTrigAndSendClock() {
uci1 1:e392595b4b76 2070
uci1 12:d472f9811262 2071 #ifdef DEBUG
uci1 1:e392595b4b76 2072 printf("WaitTrigAndSendClock\r\n");
uci1 6:6f002d202f59 2073 printf("wait trig: (pw %hhu): cards %d, amps %d, irid %d, afar %d\r\n",
uci1 6:6f002d202f59 2074 gConf.GetPowerMode(), PIN_turn_on_system.read(), PIN_turn_on_amps.read(),
uci1 6:6f002d202f59 2075 PIN_iridSbd_power.read(), PIN_afar_power.read());
uci1 21:ce51bb0ba4a5 2076 printf("cards powered=%d\r\n",(int)AreCardsPowered(true));
uci1 12:d472f9811262 2077 #endif
uci1 15:f2569d8e4176 2078
uci1 21:ce51bb0ba4a5 2079 #ifdef DEBUG
uci1 41:d6f5e2f09e07 2080 printf("gFirstEvt=%s\r\n",gFirstEvt?"true":"false");
uci1 21:ce51bb0ba4a5 2081 #endif
uci1 41:d6f5e2f09e07 2082 if (AreCardsPowered(false)) {
uci1 41:d6f5e2f09e07 2083
uci1 41:d6f5e2f09e07 2084 PIN_spi.format( 16, 1 ); // back to trigger mode
uci1 41:d6f5e2f09e07 2085 PIN_spi.frequency( 10000000 ); // Max is 12.5 MHz
uci1 8:95a325df1f6b 2086
uci1 47:fbe956b10a91 2087 if (gFirstEvt==false) {
uci1 56:0bba0ef15697 2088 #if CHIPBOARD==ATWD4CH
uci1 47:fbe956b10a91 2089 PIN_DoNotRestartAllClocks = 0;
uci1 47:fbe956b10a91 2090 wait_us(1);
uci1 47:fbe956b10a91 2091 PIN_DoNotRestartAllClocks = 1;
uci1 56:0bba0ef15697 2092 #endif
uci1 47:fbe956b10a91 2093 } else {
uci1 47:fbe956b10a91 2094 gFirstEvt = false;
uci1 47:fbe956b10a91 2095 }
uci1 47:fbe956b10a91 2096
uci1 8:95a325df1f6b 2097 //
uci1 8:95a325df1f6b 2098 // wait for a trigger here.
uci1 8:95a325df1f6b 2099 //
uci1 12:d472f9811262 2100 #ifdef DEBUG
uci1 8:95a325df1f6b 2101 printf("starting wait for trig\r\n");
uci1 12:d472f9811262 2102 #endif
uci1 16:744ce85aede2 2103
uci1 8:95a325df1f6b 2104 gReadingOut = false; // this will allow forced triggers (see procForceTrigger())
uci1 56:0bba0ef15697 2105 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 2106 while ( PIN_a_sf_clk == 1 ) { // wait for trigger
uci1 56:0bba0ef15697 2107 #else
uci1 56:0bba0ef15697 2108 while ( PIN_dataReady==0 ) { // wait for data in mb fpga
uci1 56:0bba0ef15697 2109 #endif
uci1 56:0bba0ef15697 2110 if (gOpenCommWin || gCheckPower || gCheckTemp) {
uci1 12:d472f9811262 2111 #ifdef DEBUG
uci1 56:0bba0ef15697 2112 printf("break com=%d, pow=%d, tmp=%d\r\n",
uci1 56:0bba0ef15697 2113 gOpenCommWin,gCheckPower,gCheckTemp);
uci1 12:d472f9811262 2114 #endif
uci1 8:95a325df1f6b 2115 return; // break out to open comms or check power
uci1 8:95a325df1f6b 2116 }
uci1 0:664899e0b988 2117 }
uci1 8:95a325df1f6b 2118 gReadingOut = true; // disallow new forced triggers
uci1 56:0bba0ef15697 2119
uci1 15:f2569d8e4176 2120 // we can't be interrupted before data arrives at the MB FPGA
uci1 15:f2569d8e4176 2121 //StopAllTickers();
uci1 16:744ce85aede2 2122
uci1 23:ccf39298f205 2123 //wait_us(5);
uci1 56:0bba0ef15697 2124
uci1 56:0bba0ef15697 2125 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 2126 // ATWD
uci1 8:95a325df1f6b 2127 //
uci1 8:95a325df1f6b 2128 // collect data from daughter cards
uci1 8:95a325df1f6b 2129 //
uci1 8:95a325df1f6b 2130 // TODO: what if some card (set of channels) doesn't respond?
uci1 8:95a325df1f6b 2131 // currently, will wait forever?
uci1 8:95a325df1f6b 2132 // also, if ch1 is dead, will wait forever (due to FPGA code)
uci1 16:744ce85aede2 2133 gAdcToMBtimer.start();
uci1 56:0bba0ef15697 2134 for( uint16_t i = 0; i < kNsamps; ++i ) {
uci1 16:744ce85aede2 2135 while (PIN_a_sf_clk==1) {}
uci1 16:744ce85aede2 2136 while (PIN_a_sf_clk==0) {}
uci1 56:0bba0ef15697 2137
uci1 16:744ce85aede2 2138 PIN_ADC_CS = 0;
uci1 16:744ce85aede2 2139 PIN_spi.write( 0x00 );
uci1 16:744ce85aede2 2140 PIN_ADC_CS = 1;
uci1 0:664899e0b988 2141 }
uci1 16:744ce85aede2 2142 gAdcToMBtimer.stop();
uci1 16:744ce85aede2 2143 #ifdef DEBUG
uci1 16:744ce85aede2 2144 printf("total time = %d us\r\n", gAdcToMBtimer.read_us());
uci1 16:744ce85aede2 2145 #endif
uci1 16:744ce85aede2 2146 if ( kAdcToMBtimeCut < gAdcToMBtimer.read_us() ) {
uci1 84:80b15993944e 2147 // gEvent.SetTrgBit(kAdcToMBflag);
uci1 84:80b15993944e 2148 gAdcToMBflag = true;
uci1 16:744ce85aede2 2149 }
uci1 16:744ce85aede2 2150 gAdcToMBtimer.reset();
uci1 15:f2569d8e4176 2151
uci1 56:0bba0ef15697 2152 #else
uci1 56:0bba0ef15697 2153 // For SST, data is already in the mb FPGA, so no need to do anything here
uci1 56:0bba0ef15697 2154 #endif
uci1 56:0bba0ef15697 2155
uci1 8:95a325df1f6b 2156 } else {
uci1 8:95a325df1f6b 2157 // cards have no power. don't try reading out
uci1 8:95a325df1f6b 2158 gReadingOut=false;
uci1 47:fbe956b10a91 2159 // set gFirstEvt to false even if cards are powered off.
uci1 47:fbe956b10a91 2160 // otherwise, if cards ARE powered off, it will always be
uci1 47:fbe956b10a91 2161 // true and the "start trigger" clock will be written continuously
uci1 47:fbe956b10a91 2162 gFirstEvt = false;
uci1 0:664899e0b988 2163 }
uci1 56:0bba0ef15697 2164
uci1 0:664899e0b988 2165 }
uci1 0:664899e0b988 2166
uci1 40:1324da35afd4 2167 bool IsPinPowered(const SnCommWin* cw) {
uci1 40:1324da35afd4 2168 bool havePower = false;
uci1 40:1324da35afd4 2169 switch (cw->GetCommType()) {
uci1 40:1324da35afd4 2170 case SnConfigFrame::kIrid:
uci1 40:1324da35afd4 2171 havePower = gConf.IsPoweredFor(SnConfigFrame::kIridComWin)
uci1 40:1324da35afd4 2172 && ( (kIridPwrFromAfar)
uci1 40:1324da35afd4 2173 ? PIN_afar_power.read()
uci1 40:1324da35afd4 2174 : PIN_iridSbd_power.read() ==
uci1 40:1324da35afd4 2175 gConf.GetPowPinSetting(SnConfigFrame::kIridComWin));
uci1 40:1324da35afd4 2176 break;
uci1 40:1324da35afd4 2177 case SnConfigFrame::kAfar:
uci1 40:1324da35afd4 2178 havePower = gConf.IsPoweredFor(SnConfigFrame::kAfarComWin)
uci1 40:1324da35afd4 2179 && (PIN_afar_power.read() ==
uci1 40:1324da35afd4 2180 gConf.GetPowPinSetting(SnConfigFrame::kAfarComWin));
uci1 40:1324da35afd4 2181 break;
uci1 40:1324da35afd4 2182 case SnConfigFrame::kUSB:
uci1 40:1324da35afd4 2183 havePower = true; // USB always on (for now)
uci1 40:1324da35afd4 2184 break;
uci1 40:1324da35afd4 2185 case SnConfigFrame::kSDcard: // shouldn't happen. skip it
uci1 40:1324da35afd4 2186 default: // unknown.. skip it
uci1 40:1324da35afd4 2187 break;
uci1 40:1324da35afd4 2188 };
uci1 40:1324da35afd4 2189 return havePower;
uci1 40:1324da35afd4 2190 }
uci1 40:1324da35afd4 2191
uci1 40:1324da35afd4 2192
uci1 40:1324da35afd4 2193 SnCommWin::ECommWinResult OpenCommWin(const bool forceReconfig,
uci1 40:1324da35afd4 2194 const bool isStartupWin) {
uci1 0:664899e0b988 2195 // loop through each comm mode:
uci1 0:664899e0b988 2196 // a) try to connect
uci1 0:664899e0b988 2197 // b) if connected, listen for config
uci1 0:664899e0b988 2198 // c) if config requests data, send it
uci1 67:ec999336fcd1 2199
uci1 67:ec999336fcd1 2200 led2 = 1;
uci1 67:ec999336fcd1 2201
uci1 3:24c5f0f50bf1 2202 gLastCommWin = time(0);
uci1 13:7a1fb885a8e4 2203
uci1 0:664899e0b988 2204 SnCommWin::ECommWinResult res = SnCommWin::kUndefFail;
uci1 0:664899e0b988 2205
uci1 21:ce51bb0ba4a5 2206 // get the trigger rates
uci1 21:ce51bb0ba4a5 2207 float thmrate=0, evtrate=0;
uci1 21:ce51bb0ba4a5 2208 GetRates(thmrate, evtrate);
uci1 22:f957c4f840ad 2209 #ifdef DEBUG
uci1 56:0bba0ef15697 2210 printf("config=%s\r\n", gConf.GetLabel());
uci1 22:f957c4f840ad 2211 printf("thmrate=%g, evtrate=%g\r\n",thmrate,evtrate);
uci1 84:80b15993944e 2212 printf("Free memory = %d\r\n", FreeMem());
uci1 22:f957c4f840ad 2213 #endif
uci1 21:ce51bb0ba4a5 2214
uci1 21:ce51bb0ba4a5 2215 StopAllTickers();
uci1 40:1324da35afd4 2216
uci1 13:7a1fb885a8e4 2217 if (gConf.GetCommWinDuration()==0) {
uci1 13:7a1fb885a8e4 2218 // TODO: set min so this is not possible
uci1 13:7a1fb885a8e4 2219 res = SnCommWin::kOkNoMsg;
uci1 13:7a1fb885a8e4 2220 } else {
uci1 13:7a1fb885a8e4 2221
uci1 13:7a1fb885a8e4 2222 gCommWinOpen = true;
uci1 1:e392595b4b76 2223 Watchdog::kick(); // don't reset!
uci1 13:7a1fb885a8e4 2224
uci1 13:7a1fb885a8e4 2225 #ifdef DEBUG
uci1 13:7a1fb885a8e4 2226 printf("opening comm window at %d\r\n", (int32_t)gLastCommWin);
uci1 16:744ce85aede2 2227 printf("duration=%u\r\n",gConf.GetCommWinDuration());
uci1 13:7a1fb885a8e4 2228 #endif
uci1 13:7a1fb885a8e4 2229
uci1 13:7a1fb885a8e4 2230 // close the file so that the data is all written out.
uci1 13:7a1fb885a8e4 2231 // and open it back up at the beginning (for reading)
uci1 12:d472f9811262 2232 #ifdef DEBUG
uci1 13:7a1fb885a8e4 2233 printf("close & open file. gEvtNum=%u, gPowNum=%u\r\n",gEvtNum,gPowNum);
uci1 25:57b2627fe756 2234 printf("curfile=%p, filename=%s\r\n",SnSDUtils::GetCurFile(),
uci1 25:57b2627fe756 2235 SnSDUtils::GetCurFileName());
uci1 12:d472f9811262 2236 #endif
uci1 40:1324da35afd4 2237
uci1 40:1324da35afd4 2238 if (isStartupWin==false) {
uci1 56:0bba0ef15697 2239 #if CHIPBOARD==ATWD4CH
uci1 56:0bba0ef15697 2240 PIN_lockRegisters = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 2241 #else
uci1 56:0bba0ef15697 2242 PIN_readingData = 0; // unlock so we can talk to the SD card
uci1 56:0bba0ef15697 2243 #endif
uci1 25:57b2627fe756 2244 #ifdef DEBUG
uci1 40:1324da35afd4 2245 printf("closing output file\r\n");
uci1 25:57b2627fe756 2246 #endif
uci1 40:1324da35afd4 2247 SnSDUtils::CloseOutputFile(SnSDUtils::GetCurFile());
uci1 25:57b2627fe756 2248 #ifdef DEBUG
uci1 40:1324da35afd4 2249 printf("open existing file (%d)\r\n",strlen(SnSDUtils::GetCurFileName()));
uci1 25:57b2627fe756 2250 #endif
uci1 40:1324da35afd4 2251 SnSDUtils::OpenExistingFile(SnSDUtils::GetCurFileName(), true, false);
uci1 40:1324da35afd4 2252 }
uci1 40:1324da35afd4 2253
uci1 21:ce51bb0ba4a5 2254 #ifdef DEBUG
uci1 21:ce51bb0ba4a5 2255 printf("setting power\r\n");
uci1 21:ce51bb0ba4a5 2256 #endif
uci1 84:80b15993944e 2257 // (probably) power down cards,amps
uci1 84:80b15993944e 2258 // don't power up comms yet (only as needed for use)
uci1 84:80b15993944e 2259 SetPower(true, 0);
uci1 13:7a1fb885a8e4 2260
uci1 25:57b2627fe756 2261 // time to recount files for the status update
uci1 40:1324da35afd4 2262 // for the startup win, don't access SD card in case we
uci1 40:1324da35afd4 2263 // rebooted due to a problem with the SD card
uci1 40:1324da35afd4 2264 SnStatusFrame::fgRecalcFiles = !isStartupWin;
uci1 25:57b2627fe756 2265
uci1 28:484943132bb0 2266 #if defined(ENABLE_AFAR_TWITTER) && defined(ENABLE_AFAR_COMM)
uci1 28:484943132bb0 2267 bool doTwitter = false;
uci1 28:484943132bb0 2268 #endif
uci1 28:484943132bb0 2269
uci1 21:ce51bb0ba4a5 2270 #ifdef DEBUG
uci1 21:ce51bb0ba4a5 2271 printf("start loop over comms\r\n");
uci1 21:ce51bb0ba4a5 2272 #endif
uci1 84:80b15993944e 2273 bool needToConnect=true; // still need to talk to the outside
uci1 84:80b15993944e 2274 bool sendStat[kNcomms]; // if need to send status over this peripheral
uci1 84:80b15993944e 2275 bool needClos[kNcomms]; // if need to call CloseConn on this peripheral
uci1 56:0bba0ef15697 2276 for (uint8_t i=0; i<kNcomms; ++i) {
uci1 13:7a1fb885a8e4 2277 sendStat[i]=true;
uci1 84:80b15993944e 2278 needClos[i]=true;
uci1 13:7a1fb885a8e4 2279 }
uci1 13:7a1fb885a8e4 2280 bool* ss = sendStat;
uci1 84:80b15993944e 2281 bool* nc = needClos;
uci1 13:7a1fb885a8e4 2282 SnCommWin** cw = gComms;
uci1 84:80b15993944e 2283 for (uint8_t i=0; needToConnect && ((time(0)-gLastCommWin)<gConf.GetCommWinDuration());
uci1 84:80b15993944e 2284 ++i, ++cw, ++ss, ++nc) {
uci1 1:e392595b4b76 2285 Watchdog::kick(); // don't reset!
uci1 13:7a1fb885a8e4 2286 if (i==kNcomms) {
uci1 13:7a1fb885a8e4 2287 i=0;
uci1 13:7a1fb885a8e4 2288 cw = gComms;
uci1 13:7a1fb885a8e4 2289 ss = sendStat;
uci1 84:80b15993944e 2290 nc = needClos;
uci1 13:7a1fb885a8e4 2291 }
uci1 27:efc4d654b139 2292 // skip if no comm object
uci1 13:7a1fb885a8e4 2293 if ((*cw)==0) {
uci1 13:7a1fb885a8e4 2294 continue;
uci1 13:7a1fb885a8e4 2295 }
uci1 84:80b15993944e 2296
uci1 84:80b15993944e 2297 const SnConfigFrame::EDatPackBit ctype = (*cw)->GetCommType();
uci1 84:80b15993944e 2298
uci1 84:80b15993944e 2299 // power up for this device
uci1 84:80b15993944e 2300 if (gConf.IsCommPowerSimple()==false) {
uci1 84:80b15993944e 2301 SetPower(true, ctype);
uci1 84:80b15993944e 2302 }
uci1 84:80b15993944e 2303
uci1 27:efc4d654b139 2304 // skip if no power for this comm
uci1 27:efc4d654b139 2305 // THIS IS VITAL! For example, if the ethernet
uci1 27:efc4d654b139 2306 // port is powered down, making an Ethernet obejct
uci1 27:efc4d654b139 2307 // (done in netif) will stall forever waiting for the clock.
uci1 27:efc4d654b139 2308 // Do it here to keep all PIN usage in main.cpp
uci1 40:1324da35afd4 2309 const bool havePower=IsPinPowered(*cw);
uci1 27:efc4d654b139 2310 if (havePower==false) {
uci1 27:efc4d654b139 2311 continue;
uci1 27:efc4d654b139 2312 }
uci1 40:1324da35afd4 2313
uci1 40:1324da35afd4 2314 // always apply safety nets to connection and listen so
uci1 40:1324da35afd4 2315 // that we don't accidently shut down comms (i.e. with
uci1 40:1324da35afd4 2316 // connectTO or listnTO being 0)
uci1 40:1324da35afd4 2317 gConf.ApplyConnectListenSafetyNets();
uci1 84:80b15993944e 2318
uci1 16:744ce85aede2 2319 const uint32_t conto =
uci1 84:80b15993944e 2320 (gConf.GetCommWinDuration() < gConf.GetCommWinConnectTO(ctype)) ?
uci1 84:80b15993944e 2321 gConf.GetCommWinDuration() : gConf.GetCommWinConnectTO(ctype);
uci1 16:744ce85aede2 2322 const uint32_t listo =
uci1 84:80b15993944e 2323 (gConf.GetCommWinDuration() < gConf.GetCommWinListenTO(ctype)) ?
uci1 84:80b15993944e 2324 gConf.GetCommWinDuration() : gConf.GetCommWinListenTO(ctype);
uci1 40:1324da35afd4 2325
uci1 84:80b15993944e 2326 //
uci1 84:80b15993944e 2327 // try to connect to the outside if we haven't yet
uci1 84:80b15993944e 2328 //
uci1 16:744ce85aede2 2329 // update power reading in case we want to send it in status
uci1 16:744ce85aede2 2330 GetAvePowerReading();
uci1 56:0bba0ef15697 2331
uci1 56:0bba0ef15697 2332 // update temperature in case we want to send it in status
uci1 56:0bba0ef15697 2333 if (isStartupWin) {
uci1 56:0bba0ef15697 2334 #if CHIPBOARD==SST4CH
uci1 56:0bba0ef15697 2335 InitTempProbe();
uci1 56:0bba0ef15697 2336 #endif
uci1 56:0bba0ef15697 2337 }
uci1 56:0bba0ef15697 2338 UpdateTemperature();
uci1 21:ce51bb0ba4a5 2339
uci1 13:7a1fb885a8e4 2340 // open window and (mabye) send status update
uci1 12:d472f9811262 2341 #ifdef DEBUG
uci1 84:80b15993944e 2342 printf("Free memory = %d\r\n", FreeMem());
uci1 84:80b15993944e 2343 printf("calling OpenWindow. ss=%d. ctype=%hhu (%s)\r\n",
uci1 84:80b15993944e 2344 (int)(*ss),(uint8_t)ctype,SnConfigFrame::GetDataStreamName(ctype));
uci1 40:1324da35afd4 2345 printf("conto=%u, listo=%u, dur=%u, connTO=%u, lisTO=%u\r\n",
uci1 40:1324da35afd4 2346 conto,listo,gConf.GetCommWinDuration(),
uci1 84:80b15993944e 2347 gConf.GetCommWinConnectTO(ctype), gConf.GetCommWinListenTO(ctype));
uci1 84:80b15993944e 2348 printf("stopAt=%u, current=%d, lastComWin=%d, dt~%u\r\n",
uci1 84:80b15993944e 2349 gConf.GetTimeoutTime(gLastCommWin,conto),
uci1 84:80b15993944e 2350 time(0), gLastCommWin,
uci1 84:80b15993944e 2351 gConf.GetTimeoutTime(gLastCommWin,conto)-time(0));
uci1 12:d472f9811262 2352 #endif
uci1 84:80b15993944e 2353
uci1 84:80b15993944e 2354 //
uci1 84:80b15993944e 2355 // open the connection and send the status update (if the
uci1 84:80b15993944e 2356 // status has not yet been sent over this peripheral)
uci1 84:80b15993944e 2357 //
uci1 84:80b15993944e 2358 const SnCommWin::ECommWinResult conres = (*cw)->OpenWindow( *ss,
uci1 84:80b15993944e 2359 gConf, gPower, gEvent, SnSDUtils::GetCurSeqNum(), thmrate, evtrate,
uci1 84:80b15993944e 2360 gPowerOnTime, gTemperature,
uci1 84:80b15993944e 2361 gGenBuf, gConf.GetTimeoutTime(gLastCommWin, conto));
uci1 84:80b15993944e 2362
uci1 56:0bba0ef15697 2363 #ifdef DEBUG
uci1 56:0bba0ef15697 2364 printf("conres = %d\r\n",static_cast<int>(conres));
uci1 56:0bba0ef15697 2365 #endif
uci1 13:7a1fb885a8e4 2366 if (conres>=SnCommWin::kConnected) {
uci1 1:e392595b4b76 2367 Watchdog::kick(); // don't reset!
uci1 13:7a1fb885a8e4 2368 // connected. listen for config
uci1 13:7a1fb885a8e4 2369 *ss = false; // don't send status next time
uci1 84:80b15993944e 2370 *nc = true; // will need to close this connection
uci1 40:1324da35afd4 2371
uci1 40:1324da35afd4 2372 // clear watchdog reset bit now that we've told someone
uci1 40:1324da35afd4 2373 Watchdog::clearResetFlag();
uci1 40:1324da35afd4 2374
uci1 28:484943132bb0 2375 #if defined(ENABLE_AFAR_TWITTER) && defined(ENABLE_AFAR_COMM)
uci1 84:80b15993944e 2376 if (ctype==SnConfigFrame::kAfar) {
uci1 28:484943132bb0 2377 // if we connected by Afar
uci1 28:484943132bb0 2378 doTwitter = true;
uci1 28:484943132bb0 2379 }
uci1 28:484943132bb0 2380 #endif
uci1 28:484943132bb0 2381
uci1 12:d472f9811262 2382 #ifdef DEBUG
uci1 21:ce51bb0ba4a5 2383 printf("get conf gtt=%u\r\n",gConf.GetTimeoutTime(gLastCommWin, listo));
uci1 12:d472f9811262 2384 #endif
uci1 84:80b15993944e 2385 //
uci1 84:80b15993944e 2386 // ask for a new config
uci1 84:80b15993944e 2387 //
uci1 13:7a1fb885a8e4 2388 const SnCommWin::ECommWinResult cfgres = (*cw)->GetConfig(
uci1 21:ce51bb0ba4a5 2389 gConf, gConf.GetTimeoutTime(gLastCommWin, listo), gGenBuf, gBufSize);
uci1 56:0bba0ef15697 2390 #ifdef DEBUG
uci1 56:0bba0ef15697 2391 printf("cfgres = %d\r\n",static_cast<int>(cfgres));
uci1 56:0bba0ef15697 2392 #endif
uci1 13:7a1fb885a8e4 2393 if (cfgres>=SnCommWin::kOkWithMsg) {
uci1 13:7a1fb885a8e4 2394 Watchdog::kick(); // don't reset!
uci1 16:744ce85aede2 2395
uci1 12:d472f9811262 2396 #ifdef DEBUG
uci1 13:7a1fb885a8e4 2397 printf("received config!\r\n");
uci1 13:7a1fb885a8e4 2398 printf("send data = %d\r\n", gConf.GetCommSendData());
uci1 12:d472f9811262 2399 #endif
uci1 84:80b15993944e 2400
uci1 21:ce51bb0ba4a5 2401 const uint32_t winto = gConf.GetTimeoutTime(gLastCommWin,
uci1 21:ce51bb0ba4a5 2402 gConf.GetCommWinDuration());
uci1 40:1324da35afd4 2403 //const uint32_t gtt = gConf.IsObeyingTimeout() ? winto : 0;
uci1 40:1324da35afd4 2404
uci1 84:80b15993944e 2405 //
uci1 84:80b15993944e 2406 // send status data -- do this after getting the config!
uci1 84:80b15993944e 2407 // (avoid a situation where sending all this data causes a timeout,
uci1 84:80b15993944e 2408 // thereby preventing a new config from being accepted)
uci1 84:80b15993944e 2409 //
uci1 84:80b15993944e 2410 res = (*cw)->SendStatusData(gConf,
uci1 84:80b15993944e 2411 gStTrgStartClk, gStTrgStopClk,
uci1 84:80b15993944e 2412 gStPower, gEvent, gStTemperature,
uci1 84:80b15993944e 2413 gHrtbt, gStNewPower, gStNewEvent,
uci1 84:80b15993944e 2414 gStNewHeartbeat, gStNewTemperature,
uci1 84:80b15993944e 2415 gGenBuf, winto);
uci1 84:80b15993944e 2416 #ifdef DEBUG
uci1 84:80b15993944e 2417 printf("SendStatusData res=%d\r\n",
uci1 84:80b15993944e 2418 static_cast<int32_t>(res));
uci1 84:80b15993944e 2419 #endif
uci1 84:80b15993944e 2420
uci1 84:80b15993944e 2421 //
uci1 40:1324da35afd4 2422 // check if there are any requests before sending data
uci1 84:80b15993944e 2423 //
uci1 40:1324da35afd4 2424 if (gConf.IsWaitingHndShkBeforeSendData()) {
uci1 40:1324da35afd4 2425 // send handshake request
uci1 40:1324da35afd4 2426 (*cw)->SendHndshkReq(gGenBuf, winto);
uci1 40:1324da35afd4 2427 // wait for response
uci1 40:1324da35afd4 2428 uint8_t hndshk(0); uint32_t hndshkLen(0);
uci1 40:1324da35afd4 2429 res = (*cw)->WaitHandshake(gConf, winto, gGenBuf, gBufSize, hndshk,
uci1 40:1324da35afd4 2430 &hndshkLen);
uci1 56:0bba0ef15697 2431 #ifdef DEBUG
uci1 56:0bba0ef15697 2432 printf("WaitHandshake res = %d\r\n",static_cast<int>(res));
uci1 56:0bba0ef15697 2433 #endif
uci1 40:1324da35afd4 2434 // handle response
uci1 40:1324da35afd4 2435 if (SnCommWin::kOkWithMsg==res) {
uci1 40:1324da35afd4 2436 res = (*cw)->HandleHandshake(SnSDUtils::GetCurFile(),
uci1 40:1324da35afd4 2437 SnSDUtils::GetCurFileName(),
uci1 84:80b15993944e 2438 gConf, gEvent, gPower, gGenBuf, gBufSize,
uci1 84:80b15993944e 2439 // gConf, gLastEvent, gPower, gGenBuf, gBufSize,
uci1 40:1324da35afd4 2440 winto, hndshk, hndshkLen);
uci1 56:0bba0ef15697 2441 #ifdef DEBUG
uci1 56:0bba0ef15697 2442 printf("HandleHandshake res = %d\r\n",static_cast<int>(res));
uci1 56:0bba0ef15697 2443 #endif
uci1 40:1324da35afd4 2444 }
uci1 84:80b15993944e 2445 } // if handshake before data
uci1 84:80b15993944e 2446
uci1 84:80b15993944e 2447 //
uci1 84:80b15993944e 2448 // send data if need be (files, some events, etc)
uci1 84:80b15993944e 2449 //
uci1 13:7a1fb885a8e4 2450 if (gConf.GetCommSendData()!=0) {
uci1 12:d472f9811262 2451 #ifdef DEBUG
uci1 40:1324da35afd4 2452 printf("sending data, winto=%u. lcw=%u, dur=%u, obey=%s\r\n",
uci1 40:1324da35afd4 2453 winto,
uci1 13:7a1fb885a8e4 2454 gLastCommWin, gConf.GetCommWinDuration(),
uci1 13:7a1fb885a8e4 2455 gConf.IsObeyingTimeout() ? "true" : "false");
uci1 12:d472f9811262 2456 #endif
uci1 16:744ce85aede2 2457
uci1 84:80b15993944e 2458 res = (*cw)->SendData(gConf,
uci1 84:80b15993944e 2459 // gLastEvent, gPower, gGenBuf, gBufSize,
uci1 84:80b15993944e 2460 gEvent, gPower, gGenBuf, gBufSize,
uci1 40:1324da35afd4 2461 winto);
uci1 56:0bba0ef15697 2462 #ifdef DEBUG
uci1 56:0bba0ef15697 2463 printf("SendData res = %d\r\n",static_cast<int>(res));
uci1 56:0bba0ef15697 2464 #endif
uci1 56:0bba0ef15697 2465
uci1 13:7a1fb885a8e4 2466 } else {
uci1 13:7a1fb885a8e4 2467 // don't send anything
uci1 13:7a1fb885a8e4 2468 res = cfgres;
uci1 84:80b15993944e 2469 } // if send data
uci1 13:7a1fb885a8e4 2470 #ifdef DEBUG
uci1 13:7a1fb885a8e4 2471 printf("Got config!\r\n");
uci1 13:7a1fb885a8e4 2472 #endif
uci1 13:7a1fb885a8e4 2473 Watchdog::kick(); // don't reset!
uci1 84:80b15993944e 2474
uci1 84:80b15993944e 2475 // need to close this connection
uci1 84:80b15993944e 2476 *nc = true;
uci1 84:80b15993944e 2477 // stop trying to connect to outside
uci1 84:80b15993944e 2478 // don't break immediately, so that we can close conn and
uci1 84:80b15993944e 2479 // maybe tweet (pff..)
uci1 84:80b15993944e 2480 needToConnect = false;
uci1 84:80b15993944e 2481
uci1 84:80b15993944e 2482 } // if config recvd ok with message
uci1 84:80b15993944e 2483
uci1 84:80b15993944e 2484 //
uci1 84:80b15993944e 2485 // stupid legacy twitter crap.
uci1 84:80b15993944e 2486 //
uci1 84:80b15993944e 2487 // after normal Afar connection closed, try to tweet
uci1 84:80b15993944e 2488 #if defined(ENABLE_AFAR_TWITTER) && defined(ENABLE_AFAR_COMM)
uci1 84:80b15993944e 2489 if (ctype==SnConfigFrame::kAfar) {
uci1 84:80b15993944e 2490 // tweet
uci1 84:80b15993944e 2491 #ifdef DEBUG
uci1 84:80b15993944e 2492 printf("for twitter: gTwit=%p, doTwitter=%d\r\n",gTwit,(int)doTwitter);
uci1 84:80b15993944e 2493 #endif
uci1 84:80b15993944e 2494 // send a twitter update
uci1 84:80b15993944e 2495 if ( (gTwit!=0) && doTwitter ) {
uci1 84:80b15993944e 2496 const uint32_t conto =
uci1 84:80b15993944e 2497 (gConf.GetCommWinDuration() < gTwit->GetConnectTimeout()) ?
uci1 84:80b15993944e 2498 gConf.GetCommWinDuration() : gTwit->GetConnectTimeout();
uci1 84:80b15993944e 2499 const uint32_t listo =
uci1 84:80b15993944e 2500 (gConf.GetCommWinDuration() < gTwit->GetListenTimeout()) ?
uci1 84:80b15993944e 2501 gConf.GetCommWinDuration() : gTwit->GetListenTimeout();
uci1 84:80b15993944e 2502 #ifdef DEBUG
uci1 84:80b15993944e 2503 printf("open twit window. conto=%u, listo=%u\r\n",
uci1 84:80b15993944e 2504 conto, listo);
uci1 84:80b15993944e 2505 #endif
uci1 84:80b15993944e 2506 const SnCommWin::ECommWinResult conres = gTwit->OpenWindow(
uci1 84:80b15993944e 2507 gConf.GetTimeoutTime(gLastCommWin, conto), false, gConf,
uci1 84:80b15993944e 2508 // gLastEvent, gPower,
uci1 84:80b15993944e 2509 gEvent, gPower,
uci1 84:80b15993944e 2510 SnSDUtils::GetCurSeqNum(), thmrate, evtrate,
uci1 84:80b15993944e 2511 gGenBuf);
uci1 84:80b15993944e 2512 if (conres>=SnCommWin::kConnected) {
uci1 84:80b15993944e 2513 Watchdog::kick(); // don't reset!
uci1 84:80b15993944e 2514 gTwit->Tweet(gConf, thmrate, evtrate, gGenBuf,
uci1 84:80b15993944e 2515 gConf.GetTimeoutTime(time(0), listo));
uci1 84:80b15993944e 2516 }
uci1 84:80b15993944e 2517 }
uci1 84:80b15993944e 2518 } // end tweet block
uci1 84:80b15993944e 2519 #endif
uci1 84:80b15993944e 2520
uci1 21:ce51bb0ba4a5 2521 } else {
uci1 40:1324da35afd4 2522 // OpenWindow did not connect
uci1 21:ce51bb0ba4a5 2523 (*cw)->CloseConn(gConf.GetTimeoutTime(gLastCommWin, listo));
uci1 84:80b15993944e 2524 *nc = false;
uci1 84:80b15993944e 2525 #ifdef DEBUG
uci1 84:80b15993944e 2526 printf("no connect close conn. i=%d, nc=%s\r\n",
uci1 84:80b15993944e 2527 (int32_t)i, (*nc) ? "true" : "false");
uci1 84:80b15993944e 2528 #endif
uci1 21:ce51bb0ba4a5 2529 } // if connected
uci1 13:7a1fb885a8e4 2530
uci1 13:7a1fb885a8e4 2531 Watchdog::kick(); // don't reset!
uci1 84:80b15993944e 2532
uci1 84:80b15993944e 2533 if (*nc) {
uci1 84:80b15993944e 2534 // need to close this connection
uci1 84:80b15993944e 2535 #ifdef DEBUG
uci1 84:80b15993944e 2536 printf("close conn extra time. i=%d, nc=%s\r\n",
uci1 84:80b15993944e 2537 (int32_t)i, (*nc) ? "true" : "false");
uci1 84:80b15993944e 2538 #endif
uci1 84:80b15993944e 2539 const uint32_t extraDiscTime = gLastCommWin
uci1 84:80b15993944e 2540 + gConf.GetCommWinConnectTO((*cw)->GetCommType());
uci1 84:80b15993944e 2541 (*cw)->CloseConn(
uci1 84:80b15993944e 2542 gConf.GetTimeoutTime(extraDiscTime, gConf.GetCommWinDuration()));
uci1 84:80b15993944e 2543 *nc = false;
uci1 84:80b15993944e 2544 }
uci1 84:80b15993944e 2545
uci1 84:80b15993944e 2546 Watchdog::kick(); // don't reset!
uci1 21:ce51bb0ba4a5 2547 } // end loop over comms
uci1 28:484943132bb0 2548
uci1 84:80b15993944e 2549
uci1 41:d6f5e2f09e07 2550 // check Iridium time, send Iridium signal strength, and close the connection(s)
uci1 15:f2569d8e4176 2551 cw = gComms;
uci1 84:80b15993944e 2552 nc = needClos;
uci1 84:80b15993944e 2553 for (uint8_t i=0; i<kNcomms; ++i, ++cw, ++nc) {
uci1 15:f2569d8e4176 2554 if ((*cw)==0) {
uci1 15:f2569d8e4176 2555 continue;
uci1 15:f2569d8e4176 2556 }
uci1 84:80b15993944e 2557
uci1 84:80b15993944e 2558 const SnConfigFrame::EDatPackBit ctype = (*cw)->GetCommType();
uci1 84:80b15993944e 2559
uci1 84:80b15993944e 2560 // check Iridium time
uci1 84:80b15993944e 2561 if (ctype==SnConfigFrame::kIrid) {
uci1 40:1324da35afd4 2562
uci1 84:80b15993944e 2563 // power up for this device
uci1 84:80b15993944e 2564 if (gConf.IsCommPowerSimple()==false) {
uci1 84:80b15993944e 2565 SetPower(true, ctype);
uci1 84:80b15993944e 2566 }
uci1 84:80b15993944e 2567 const bool havePower=IsPinPowered(*cw);
uci1 84:80b15993944e 2568 if (havePower==false) {
uci1 84:80b15993944e 2569 continue;
uci1 84:80b15993944e 2570 }
uci1 84:80b15993944e 2571
uci1 16:744ce85aede2 2572 #ifdef DEBUG
uci1 16:744ce85aede2 2573 printf("try to set iridium time\r\n");
uci1 16:744ce85aede2 2574 #endif
uci1 16:744ce85aede2 2575 // set the clock before closing connection
uci1 41:d6f5e2f09e07 2576 const uint32_t totime =
uci1 41:d6f5e2f09e07 2577 gConf.GetTimeoutTime(gLastCommWin,
uci1 41:d6f5e2f09e07 2578 gConf.GetCommWinDuration());
uci1 41:d6f5e2f09e07 2579 #ifdef DEBUG
uci1 41:d6f5e2f09e07 2580 printf("totime=%u, ctime=%u\r\n",totime,time(0));
uci1 41:d6f5e2f09e07 2581 #endif
uci1 41:d6f5e2f09e07 2582 const bool con = (*cw)->Connect(totime);
uci1 84:80b15993944e 2583 *nc = true;
uci1 84:80b15993944e 2584
uci1 16:744ce85aede2 2585 if (con) {
uci1 40:1324da35afd4 2586 uint32_t prvTime(0), setTime(0);
uci1 41:d6f5e2f09e07 2587 const bool gottime = (*cw)->TrySetSysTimeUnix(
uci1 41:d6f5e2f09e07 2588 totime, prvTime, setTime);
uci1 41:d6f5e2f09e07 2589 if (gottime) {
uci1 84:80b15993944e 2590 gClkSet.SetClocks( prvTime, setTime, time(0),
uci1 84:80b15993944e 2591 gSinceClkSet.read_us() );
uci1 84:80b15993944e 2592 gSinceClkSet.reset();
uci1 84:80b15993944e 2593 gSinceClkSet.start();
uci1 41:d6f5e2f09e07 2594 #ifdef DEBUG
uci1 84:80b15993944e 2595 // printf("sig str: totime=%u, ctime=%u\r\n",totime,time(0));
uci1 84:80b15993944e 2596 printf("sig str: totime=%u, ctime=%u\r\n",totime,gClkSet.GetCurTime());
uci1 41:d6f5e2f09e07 2597 #endif
uci1 41:d6f5e2f09e07 2598 // got time; now send signal strength
uci1 41:d6f5e2f09e07 2599 (*cw)->SendSignalStrength( gGenBuf, gSigStr, totime );
uci1 84:80b15993944e 2600 } // if got the iridium system time
uci1 84:80b15993944e 2601 } // if connected (again, possibly)
uci1 84:80b15993944e 2602 } // if iridium
uci1 84:80b15993944e 2603
uci1 84:80b15993944e 2604 if (*nc) {
uci1 84:80b15993944e 2605
uci1 84:80b15993944e 2606 // power up for this device
uci1 84:80b15993944e 2607 if (gConf.IsCommPowerSimple()==false) {
uci1 84:80b15993944e 2608 SetPower(true, ctype);
uci1 16:744ce85aede2 2609 }
uci1 84:80b15993944e 2610 const bool havePower=IsPinPowered(*cw);
uci1 84:80b15993944e 2611 if (havePower==false) {
uci1 84:80b15993944e 2612 continue;
uci1 84:80b15993944e 2613 }
uci1 84:80b15993944e 2614
uci1 28:484943132bb0 2615 #ifdef DEBUG
uci1 84:80b15993944e 2616 printf("last loop close conn. i=%d, nc=%s\r\n",
uci1 84:80b15993944e 2617 (int32_t)i, (*nc) ? "true" : "false");
uci1 28:484943132bb0 2618 #endif
uci1 84:80b15993944e 2619
uci1 84:80b15993944e 2620 const uint32_t extraDiscTime = gLastCommWin
uci1 84:80b15993944e 2621 + gConf.GetCommWinConnectTO((*cw)->GetCommType());
uci1 84:80b15993944e 2622 (*cw)->CloseConn(gConf.GetTimeoutTime(extraDiscTime, gConf.GetCommWinDuration()));
uci1 84:80b15993944e 2623 *nc = false;
uci1 84:80b15993944e 2624 }
uci1 84:80b15993944e 2625 } // end loop: check time, close conns
uci1 40:1324da35afd4 2626
uci1 84:80b15993944e 2627 /*
uci1 40:1324da35afd4 2628 // close connections
uci1 40:1324da35afd4 2629 cw = gComms;
uci1 56:0bba0ef15697 2630 for (uint8_t i=0; i<kNcomms; ++i, ++cw) {
uci1 40:1324da35afd4 2631 if ((*cw)==0) {
uci1 40:1324da35afd4 2632 continue;
uci1 40:1324da35afd4 2633 } else {
uci1 40:1324da35afd4 2634 }
uci1 28:484943132bb0 2635 }
uci1 84:80b15993944e 2636 */
uci1 84:80b15993944e 2637
uci1 28:484943132bb0 2638 } // if duration >0
uci1 28:484943132bb0 2639
uci1 28:484943132bb0 2640 /* not working. must use DEFCONF.DAT to change IP's.
uci1 28:484943132bb0 2641 // change comm parameters (IP addresses)
uci1 28:484943132bb0 2642 #ifdef DEBUG
uci1 28:484943132bb0 2643 printf("set comm params\r\n");
uci1 28:484943132bb0 2644 #endif
uci1 28:484943132bb0 2645 for (uint8_t cc=0; cc<kNcomms; cc++) {
uci1 28:484943132bb0 2646 if (gComms[cc]!=0) {
uci1 28:484943132bb0 2647 gComms[cc]->Set(gConf);
uci1 15:f2569d8e4176 2648 }
uci1 0:664899e0b988 2649 }
uci1 28:484943132bb0 2650 */
uci1 40:1324da35afd4 2651
uci1 40:1324da35afd4 2652
uci1 40:1324da35afd4 2653 // check if we missed too many consecutive connections
uci1 40:1324da35afd4 2654 if (res<=SnCommWin::kAllFails) {
uci1 40:1324da35afd4 2655 ++gConsecCommFails;
uci1 40:1324da35afd4 2656 #ifdef DEBUG
uci1 56:0bba0ef15697 2657 printf("res=%d, gConsecCommFails=%hu, kMaxConsecCommFails=%hu\r\n",
uci1 56:0bba0ef15697 2658 static_cast<int>(res), gConsecCommFails,kMaxConsecCommFails);
uci1 40:1324da35afd4 2659 #endif
uci1 40:1324da35afd4 2660 if (gConsecCommFails>kMaxConsecCommFails) {
uci1 40:1324da35afd4 2661 #ifdef DEBUG
uci1 40:1324da35afd4 2662 printf("rebooting\r\n");
uci1 40:1324da35afd4 2663 #endif
uci1 40:1324da35afd4 2664 // goodbye cruel world, it's over. walk on by...
uci1 40:1324da35afd4 2665 mbed_reset();
uci1 40:1324da35afd4 2666 }
uci1 40:1324da35afd4 2667 } else {
uci1 40:1324da35afd4 2668 gConsecCommFails=0;
uci1 40:1324da35afd4 2669 }
uci1 28:484943132bb0 2670
uci1 4:a91682e19d6b 2671 // (probably) power down comms and power up cards,amps
uci1 84:80b15993944e 2672 SetPower(false, SnConfigFrame::kIrid | SnConfigFrame::kAfar);
uci1 4:a91682e19d6b 2673
uci1 1:e392595b4b76 2674 // reset config with system powered (for DAC/PLA setting)
uci1 12:d472f9811262 2675 #ifdef DEBUG
uci1 21:ce51bb0ba4a5 2676 printf("calling SetConfigAndMakeOutputFile\r\n");
uci1 12:d472f9811262 2677 #endif
uci1 76:f8383f0292c2 2678
uci1 76:f8383f0292c2 2679 if (gConf.IsRunSeqListOneCommWinOnly()) {
uci1 76:f8383f0292c2 2680 SnSDUtils::ClearRunSeqList(gConf.IsSendingFilesRunSeqList());
uci1 76:f8383f0292c2 2681 }
uci1 22:f957c4f840ad 2682
uci1 21:ce51bb0ba4a5 2683 SetConfigAndMakeOutputFile();
uci1 21:ce51bb0ba4a5 2684
uci1 56:0bba0ef15697 2685 // check power in case we should be in low power mode
uci1 56:0bba0ef15697 2686 // but don't save this reading to the file
uci1 56:0bba0ef15697 2687 // (there's already one near the beginning)
uci1 56:0bba0ef15697 2688 CheckPower(false, false);
uci1 56:0bba0ef15697 2689
uci1 12:d472f9811262 2690 #ifdef DEBUG
uci1 1:e392595b4b76 2691 printf("closing comm win at %d\r\n",(int32_t)time(0));
uci1 84:80b15993944e 2692 printf("Free memory = %d\r\n", FreeMem());
uci1 12:d472f9811262 2693 #endif
uci1 67:ec999336fcd1 2694
uci1 67:ec999336fcd1 2695 led2 = 0;
uci1 1:e392595b4b76 2696
uci1 0:664899e0b988 2697 gCommWinOpen = false;
uci1 0:664899e0b988 2698 return res;
uci1 0:664899e0b988 2699 }