/*
 * David Muller; Germán Alfaro
 * davehmuller@gmail.com; alfaro.germanevera@gmail.com
 *
 * Thom Maughan; tm@mbari.org  2018...
 */


#ifndef PHFETSOS_SYSTEM_H_
#define PHFETSOS_SYSTEM_H_

#include <stdint.h>
#include <stdbool.h>
#include <math.h>
#include <time.h>
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include <stdlib.h>
#include <ctype.h>

#if BOARD_MFET >= 1 || BOARD_MPHOX == 1  || BOARD_MSC == 2
#include "inc/tm4c123gh6pge.h"
#endif
#if BOARD_NANOFET == 1 || BOARD_MSC == 3
#include "inc/tm4c123gh6pm.h"
#endif

#include "inc/hw_memmap.h"
#include "inc/hw_types.h"
#include "inc/hw_hibernate.h"

#include "driverlib/debug.h"
#include "driverlib/fpu.h"
#include "driverlib/gpio.h"
#include "driverlib/pin_map.h"
#include "driverlib/rom.h"
#include "driverlib/rom_map.h"
#include "driverlib/sysctl.h"
#include "driverlib/uart.h"
#include "driverlib/eeprom.h"
#include "driverlib/gpio.h"
#include "driverlib/hibernate.h"
#include "driverlib/ssi.h"
#include "driverlib/interrupt.h"


//V=I*R => V=I*15K => I=V/15K amps => I=V*10^9/15K nano-Amps => I=V*66.6k nA => 15uV/nA.
#define COUNTERELECTRODE_IK_SCALE       66666.667   // 10^9/15K MCAP has 15K resistor, Ik
//
#define SUBSTRATECURRENT_IB_SCALING     1000        // 10^9/1M = 1000   MCAP has 1M resistor for Ib, substrate current

#define SIZEOF_PRNBUF  1020

#if BOARD_MFET == 1
#define 	VERSION		"v3.7.1 was the last support for MFET v1"     // MFET software version   Glider is 9600 baud
// battery backed HIB, no FRAM
// only one can be set to 1.  HIB uses battery backed ram in hibernate module, EEPROM uses onchip EEPROM with 500K cycles, FRAM requires 24CL04B chip on MFET v2
#define NONVOLATILEMEM  "Nonvol mem: Hibernate module battery backed RAM"
#define EEPROM_REG_STORE 0      // old, wear out EEPROM
#define HIB_REG_STORE   1       // used to turn on HIB register store to prevent EEPROM wearout
#define FRAM_REG_STORE  0
#endif
#if BOARD_MFET == 2
#define     VERSION     "v5.0.0 MFET revC"     // MFET software version   Glider is 9600 baud
// FRAM (and battery backed HIB)
#define NONVOLATILEMEM  "Nonvol mem: i2c Ferroelectric RAM"
#define EEPROM_REG_STORE 0      // old, wear out EEPROM
#define HIB_REG_STORE   0       // used to turn on HIB register store to prevent EEPROM wearout
#define FRAM_REG_STORE  2       // was 1, 2 means use of sys_samp
#endif
#if BOARD_MPHOX == 1  || BOARD_MSC == 2
#define     VERSION     "v5.0.0 MpHOx revA/B"     // MFET software version   Glider is 9600 baud
// FRAM (and battery backed HIB)
#define NONVOLATILEMEM  "Nonvol mem: i2c Ferroelectric RAM"
#define EEPROM_REG_STORE 0      // old, wear out EEPROM
#define HIB_REG_STORE   0       // used to turn on HIB register store to prevent EEPROM wearout
#define FRAM_REG_STORE  2       // was 1 (sys_samp)
#endif
#if BOARD_NANOFET == 1
#define     VERSION     "v5.0.0 NanoFET revB"     // NanoFET software version, hardware version (revA and revB and compatible)
// FRAM (and battery backed HIB)
#define NONVOLATILEMEM  "Nonvol mem: i2c Ferroelectric RAM"
#define EEPROM_REG_STORE 0      // old, wear out EEPROM
#define HIB_REG_STORE   0       // used to turn on HIB register store to prevent EEPROM wearout
#define FRAM_REG_STORE  2
#endif
#if BOARD_MSC == 3
#define     VERSION     "v5.0.0 MSC3 revA"     // MSC3 Tiva software version, hardware version
// FRAM (and battery backed HIB)
#define NONVOLATILEMEM  "Nonvol mem: i2c Ferroelectric RAM"
#define EEPROM_REG_STORE 0      // old, wear out EEPROM
#define HIB_REG_STORE   0       // used to turn on HIB register store to prevent EEPROM wearout
#define FRAM_REG_STORE  2
#endif
#ifndef VERSION
#define     VERSION     "COMPILER FLAGS BOARD_MFET or BOARD_MPHOX or BOARD NANOFET NOT DEFINED"
#endif

#define NOMINAL_SAMPLE_TIMES    1
#define FAST_SAMPLE_TIMES       0


/* Boolean type */
typedef enum { FALSE = 0, TRUE } BOOL;
//typedef enum {IDLE, START, DEPLOYED, COMMAND} deploy_state;
typedef enum {IDLE, DEPLOYED} deploy_state;     //DEPLOYED is WAKERTC, IDLE is WAKEGPIO
typedef enum {NORMAL=1, VERBOSE} output_mode;
#define GPIOWAKEUP      0
#define RTCWAKEUP       1


/*
 * Delay lengths for SysCtlDelay().
 */
#define CLOCKSPEED 50000000.0  						//clock is set to run at 50MHZ
#define ONESEC (int)ceil((CLOCKSPEED/3.0))  		//SysCtlDelay takes 3 cycles per loop...so delay = DesiredDelayTimeInSeconds/((1/CLOCKSPEED)*3)
#define MILLISECOND (int)ceil((.001 / ((1.0/CLOCKSPEED)*3.0)))
#define MICROSECOND (int)ceil((.000001 / ((1.0/CLOCKSPEED)*3.0)))

/*
 * Buffer lengths.   Thom TODO: consolidate the buffers to one for each uart rather than for each driver.
 */
#define TIMESTAMPLENGTH 		50
#define INSTRUMENTBUFFSIZE 		400
#define MICROCAT_BUFFER_SIZE 	128
#define DBG_UART_BUFFER_SIZE    128     // buffer defined in microcat.h microcat sbe37 is on uart4
//#define OPTODE_BUFFER_SIZE 		128     // buffer defined in optode.h optode is on uart3
//#define CTD_BUFFER_SIZE         128
#define AUX1_BUFFER_SIZE		128
#define AUX2_BUFFER_SIZE		128
//#define OCR_BUFFER_SIZE         128     // UART3
//#define NANOFET_BUFFER_SIZE     256 //128     // UART3

#define GDATA_BYTES				512	// Number of bytes to read out with gdata command

#define IS_PRESENT		  1
#define NOT_PRESENT 	  0



/*
 * Constants
 */
#define R_			8.31451			// Univ gas constant
#define F_ 			96487			// Faraday constant
#define dEoINT_dt	-0.0011012		// Temperature coefficient for internal reference [Volts/C]
#define dEoEXT_dt	-0.0010482		// Temeprature coefficient for external reference [Volts/C]
#define LN10		2.302585		// Natural log of 10

// Standard deviation array values
#define SD_AVG		5
#define SD_MEAN		SD_AVG
#define SD_DIFF_SQ	SD_AVG+1
#define SD_VALUES	5

// AD1248 24-bit A/D defines
// signed 24bit numeric range is: -8,388608 to +8,388607
#define TWOTOTHE23 8388608  // 2 to the 23rd = 8388608
#define COUNTSTOVOLTS (float) (2.048 / (TWOTOTHE23 - 1))  //each count returned from the ADC has a weight of (Vref/PGA)/(2^23 -1 ).  We use PGA = 1.
#define PGA_1		0x00
#define PGA_2		0x10
#define PGA_4		0x20
#define PGA_8		0x30
#define PGA_16		0x40
#define PGA_32		0x50
#define PGA_64		0x60
#define PGA_128		0x70

#define SPS_5		0x00
#define SPS_10		0x01
#define SPS_20		0x02
#define SPS_40		0x03
#define SPS_80		0x04
#define SPS_160		0x05
#define SPS_320		0x06
#define SPS_640		0x07
#define SPS_1000	0x08
#define SPS_2000	0x09

#define VTHERM_TRIALS   5
#define VTHERM_SPS      20

#define VRSI_TRIALS     10
#define VRSI_SPS        20

#define VRSE_TRIALS     10
#define VRSE_SPS        20

#define IK_TRIALS       1
#define IK_SPS          20

#define VK_TRIALS       5
#define VK_SPS          20

#define IB_TRIALS       1
#define IB_SPS          20

#define VB_TRIALS       5
#define VB_SPS          20

#define VBIAS_TRIALS   1
#define VBIAS_SPS      40


#define MAX_SAMPLING_PERIOD     3600            // New 15 Aug 2022, implementing a fix in sleep.c for a corrupt wakeup time.
#define MIN_SAMPLING_PERIOD     2

/*
 * Definition of a structure containing the controller's parameters
 * These parameters are all modifiable by external user except where noted.
 * Structure is stored in EEPROM during hibernation.
 */
#define MAX_NUMOF_CONFIG_FIELDS         32  //was 30  These are for sampling / data logging configuration A-Z, 0-9
#define MAX_NUMOF_APP_CONFIG_FIELDS     16  // was 8 in 4.0.7

#define MAX_NUMOF_K2_CAL_FIELDS         4   // Storage allocated in sys_data
#define NUMOF_K2_CAL_FIELDS             4   // present size of polynomial
#define MAX_NUMOF_FP_CAL_FIELDS         7  // Worse case storage allocation based on Josh Plant discussion
#define NUMOF_FP_CAL_FIELDS             7   // present size of polynomial

#define MAX_FILENAME        16      // 8.3 filename plus padding 24      //80 is too much, should be 32 or 40 at most.
#define MAX_USER_INITIALS   8
#define MAX_TESTER_NAME     48
#define MAX_VERSION_SIZE    32

#define MAX_BOARD_SN        24      //30
#define MAX_PT_CAL_DATE     12
#define MAX_K0_CAL_DATE     12
#define MAX_SERVICE_DATE    12
#define MAX_CAL_FILENAME    32      //16

#define MAX_MCAP_SN         24      //30
#define MAX_PACKAGE_NAME    32      //30
#define MAX_SENSOR_SN       8       //24      //30  new 7 Sep 2023 changed from 24 to 8 and added 2 more 8 char fields, was MAX_DURAFET_SN
#define MAX_ISFET_SN        8       // MAX_CAPADAP_SN      24      //30
#define MAX_ISE_SN          8       //24      //30
#define MAX_OPTODE_SN       24      //30
#define MAX_CTD_SN          24      //30
#define MAX_PUMP_SN         24      //30
#define MAX_BOARD_FABNOTE   80      // was 80, now part of qa
#define MAX_PACKAGE_FABNOTE 80      //
#define MAX_DEPLOY_NOTE     80

// pump_sequencing types for selecting sequencing statemachine
#define TYPE_PUMP_NOTDEFD       0
#define TYPE_PUMP_SINGLE        1
#define TYPE_2PUMP_BEAMSV1      2
#define TYPE_2PUMP_BEAMSV2      3
#define TYPE_PUMP_SELFCAL       4




struct qaData
{
    uint32_t    microSD;            // microSD
    uint32_t    time;               // time of QA
    uint32_t    test_time;          // time it took to run QA
    uint32_t    eeprom;             // size of sys_data in eeprom, 0 if there is a problem
    uint32_t    sys_data_init;      // was the data initialized
    uint32_t    fram;
    uint32_t    adc12onchip;
    uint32_t    adc24;              // how many of the ADC fields are out of expected Jensenian range


    float    Vrsi;
    float    Vrsi_std;
    float    Vrsi_err;
    float    Vrse;
    float    Vrse_std;
    float    Vrse_err;
    float    Vtherm;
    float    Vtherm_std;
    float    Vtherm_err;

    float    Ik;
    float    Ik_std;
    float    Ik_err;

    float    Vk;
    float    Vk_std;
    float    Vk_err;

    float    Ib;
    float    Ib_std;
    float    Ib_err;

    float    Vb;
    float    Vb_std;
    float    Vb_err;

    float    Vbias_pos;
    float    Vbias_neg;

    uint32_t    aux_pwr1;
    uint32_t    aux_pwr2;
    uint32_t    aux_pwr3;

    uint32_t    ctd;
    uint32_t    optode;
    uint32_t    comm_pwr;

    char        tester[MAX_TESTER_NAME];
    char        firmware_version[MAX_VERSION_SIZE];
    char        board_fab_note[MAX_BOARD_FABNOTE];        //  New  board fabrication notes, dates, etc.
};


struct sampData
{
    unsigned int    sampNum;        // 1
    unsigned int    timestamp;      // 2
    float           fBiasNeg;       // 3
    float           fBiasPos;       // 4
    float           fIb;            // 5 (Ib) SubstrateCurrent
    float           fIk;            // 6 (Ik) CounterElectrodeCurrent
    float           fIk_std;        // 7
    float           fVk;            // 8 (Vk) CounterElectrodeVoltage
    float           fVk_std;        // 9
    float           fVtherm;        // 10
    float           fVtherm_std;    // 11  Likely not needed
    float           fTempC;         // 12
    float           fVrsi;          // 13
    float           fVrsi_std;      // 14
    float           pHint;          // 15
    float           fVrse;          // 16
    float           fVrse_std;      // 17
    float           pHext;          // 18
    float           fVbat_main;     // 19
    float           fBrdTempC;      // 20
    unsigned int    uiHumidity;     // 21
    float           spare1;         // 22
    float           spare2;         // 23
    float           spare3;         // 24
};

// systemData struct organized for 4 byte packing, also fixed buffer overruns by setting size of fields in define
struct systemData
{
    //---------------- samplingData ---------------------------
	uint32_t sampling_period;	    //8 pH sampling period
	uint32_t chksum;	    	// was sample_average DEPRECATED (was int32_t) 12 Number of pH sensor samples to average
	uint32_t averaging_interval;    //16 Number of seconds between each average

	float low_batt_volt;            //4  Low battery voltage threshold
	float TCOffset;					//24 DuraFET temperature calibration variable (not needed)
    float TCSlope;
	float k0ext;					//28 was float Eo_ext_25C;, renamed k0ext 2 Apr 2021
	float k0int;					//32 was float Eo_int_25C;, renamed k0int  2 Apr 2021
    float k2ext;                    //28 added  25 Apr 2021
    float k2int;                    //32 added  25 Apr 2021
    double quadTherm_c0;             // 4 coefficient c0 for thermistor
    double quadTherm_c1;             // 4 coefficient c1 for thermistor
    double quadTherm_c2;             // 4 coefficient c2 for thermistor
    double quadTherm_c3;             // 4 coefficient c3 for thermistor
    double shTherm_A;                // steinhart-hart coefficient A
    double shTherm_B;                // steinhart-hart coefficient C
    double shTherm_C;                // steinhart-hart coefficient B
	float default_sal;               //36 default salinity (FRAM) TODO
	//float spareVar;                 // was sensor_sal
	//float sensor_sal;               // salinity read from conductivity (SBE, Aanderaa)   FRAM

	uint32_t Vrsi_sps;				//Vrsi_sps	//418 pH Vint data rate setting (sps)
	uint32_t Vrsi_trials;           //Vrsi_trials
	uint32_t Vrse_sps;
	uint32_t Vrse_trials;
	uint32_t Vtherm_sps;
	uint32_t Vtherm_trials;
	uint32_t Ik_sps;
	uint32_t Ik_trials;
	uint32_t Vk_sps;
	uint32_t Vk_trials;
	uint32_t Ib_sps;
	uint32_t Ib_trials;
    uint32_t Vb_sps;
    uint32_t Vb_trials;
    uint32_t Vbias_sps;
    uint32_t Vbias_trials;

    uint32_t offset_Ik;             // 800uV or so, tbd measure a QA step.
    uint32_t offset_Ib;
	output_mode output;				//422 Verbose mode during deployment if true (enum is 4 bytes?)
	uint32_t test_mode;		        //426 Indicates test deployment
	uint32_t fast_mode;             // Future: changed to sampling mode (fast, precise, etc.)
	uint32_t solenoid_on2hold_msec;
	uint32_t solenoid_hold_pwm;
	uint32_t solenoid_holdtime;     // new 20 Jul 2021

    uint32_t baud_rate;        //470 baud rate  (added by tm Jul 2018)
	unsigned char data_cfg[MAX_NUMOF_CONFIG_FIELDS];     //data field / logging configuration (added by tm Jul 2018)
	unsigned char app_cfg[MAX_NUMOF_APP_CONFIG_FIELDS];

    bool GMT;                       //456 GMT or Local time
    bool sample_aligned;            //460 Sample aligned to hour

    uint32_t diag;                  // diagnostic flag, for developer
    uint32_t debug_flag;            // turn on diagnostic debug printf's


    // Sampling and Sequencing StateMachine variables
    uint32_t deploy_time;               // timestamp of when 'deploy' menu action.   deployment time  (Todo, put in FRAM?) (variable location changed from above diag).
    uint32_t start_pump_time;         // (seconds) Wakeup on sampling interval, but check the 'start deployment time' before actual pumping/sampling 16 Feb 2022


    uint32_t pump_seq_type;             // 0) legacy single pump, 1) BEAMS v1 dual pump seq, 2) BEAMS v2
    uint32_t sampleCnt_duty_on;         // duty cycle for extending experiment.   3 days on, 5 days off.   Number of 'sample periods' on
    uint32_t sampleCnt_duty_off;        // in sample periods.    Accept input in hours, translate to sample periods (keep implementation simple for now).
    uint32_t pump1_cycles;                   // = 10 cycles
    uint32_t pump2_cycles;                   // = 5 cycles
    uint32_t pump1_ontime;          //20 Active pump time;                 // = 30 cycles
    uint32_t pump2_ontime;                 // = 10 cycles

    uint32_t pump_spare[16];            // make room for other variables (future pump sequencer) pump3, etc.

    // was float spare[9];
    float pHOffset;                 // new 3 Aug 2021 (speculative placeholders, can be used as spare)  k0, etc are used for offsets on ph
    float pHSlope;
    //float TCSlope;
    float sensor_ctd_TC;
    float sensor_optode_TC;
    float K2_Cal[MAX_NUMOF_K2_CAL_FIELDS];                // worse case 4th order polynomial
    float fP_Cal[MAX_NUMOF_FP_CAL_FIELDS];               // worse case 7th order polynomial
    float k0_HCL;
    float k0_SW;
    float k0std_SW;
    float spare[25];   // was spare[56] until 6 K2 and 12 F(p) cal coeeff (56-6-12=38), was float spare[64]; reduced by 32bytes (8 float) 10 Oct 2022  // LAYOUT CHANGE 16 Feb 2022, now 64 for v4.x future expansion. was 4 (was 9) 4 byte spares (36 bytes) for future expansion without causing EEPROM struct issues
    char service_date[MAX_SERVICE_DATE];    //12
    char PT_Cal_date[MAX_PT_CAL_DATE];      //12
    char k0_Cal_date[MAX_K0_CAL_DATE];      //12
    char cal_filename[MAX_CAL_FILENAME];       //32, was 16
	char firmware_version[MAX_VERSION_SIZE]; //32
	//------------------ System MetaData ------------------
	// re-arranged struct to put char fields after numeric
    char fileName[MAX_FILENAME];              //116 The name the user would like to give their data output file, fatfs max is 8.3
    char user[MAX_USER_INITIALS];                  //452 User initials

    char board_SN[MAX_BOARD_SN];              //146 (added 3Apr2021) board (MFET, MpHOx, nanoFET) serial number
    char mcap_SN[MAX_MCAP_SN];               //176 (added 3Apr2021) mcap serial number
    char sensor_SN[MAX_SENSOR_SN];            //226 was 24, now 8, was durafet_SN, now sensor_SN, 7 Sep 2023 DuraFET sensor serial number
    char isfet_SN[MAX_ISFET_SN];              // new 7 Sep 2023
    char ise_SN[MAX_ISE_SN];                // new 7 Sep 2023
    char package_name[MAX_PACKAGE_NAME];       //196 Name of integrated package (underway system, etc.)  (was 20, now 30, bug in buff entry size)

    char optode_SN[MAX_OPTODE_SN];             //346 (added 3Apr2021) Aanderaa optode serial number
    char ctd_SN[MAX_CTD_SN];                 //376 (added 3Apr2021) Aanderaa conductivity or MicroCat aka ctd serial number
    char pump_SN[MAX_PUMP_SN];                  //406 Pump serial number
    char pump2_SN[MAX_PUMP_SN];                  //406 Pump serial number
    char pump3_SN[MAX_PUMP_SN];                  //406 Pump serial number
    char package_fab_note[MAX_BOARD_FABNOTE];    //  (added 4Apr2021)  was board fabrication notes, now 7 Nov 2023 package fab notes
    char deploy_note[MAX_DEPLOY_NOTE];          // (Todo FRAM)

    struct qaData qa;
};


//Note: i2c_fram.c has fram layout (64bytes allocated for the 15*4=60 byte struct)
struct systemSamplingData           //TODO: rename to systemVolatileData
{
    int32_t state;                  //430 IDLE, DEPLOYED, COMMAND,  NOT USER MODIFIABLE                        <<<<<------
    uint32_t nextWakeUp;            //434 Next intended RTC match (wake-up time) NOT USER MODIFIABLE           <<<<<------
    uint32_t next_gdata_fptr;       //438 The file position of the next gdata sample. NOT USER MODIFIABLE      <<<<<------
    uint32_t current_sample;        //442 The current data record to be stored. NOT USER MODIFIABLE            <<<<<------
    float AD24_std;                 //464 standard deviation for AD24                                          <<<<--------
    float sensor_sal;               // salinity read from conductivity (SBE, Aanderaa)
    float spare1;
    float spare2;
    float spare3;
    float spare4;
    uint32_t initNum;
    uint32_t pump_seq_state;      // for controlling/sequencing pump/solenoid
    uint32_t pump1_cnt;
    uint32_t pump2_cnt;
    uint32_t start_pump_cntdown;      // count down in 'sample periods'
};

// DEPRECATED variables that change each sample (will wear out onchip 500k write cycle flash / eeprom), stored in FRAM
struct systemDataVolatile
{
    uint32_t state;                     // IDLE, DEPLOYED, COMMAND,  NOT USER MODIFIABLE
    uint32_t nextWakeUp;                // Next intended RTC match (wake-up time) NOT USER MODIFIABLE
    uint32_t next_gdata_fptr;           // The file position of the next gdata sample. NOT USER MODIFIABLE Note: was unsigned long
    uint32_t current_sample;            // The current data record to be stored. NOT USER MODIFIABLE
    float AD24_std;
    uint32_t samp_state;
    uint32_t chksum;
};

#define SYSDATACHG_NUMWORDS     7       // number of 4byte words in above struct
//#endif








//DEFAULT Configuration for get_sample() is for all fields
// index into sys_data.data_cfg[]
#define CFG_SAMPLE_NUM          0
#define CFG_TIMESTAMP           1   // + MM/DD/YYYY HH:MM:SS

#define CFG_V_THERMISTOR        2       //+ Vthermistor\t
#define CFG_V_THERMISTOR_STD    3   //+ Vthermistor_std\t
#define CFG_CALC_TEMP           4   //+ calculated_temperature_Vthermistor\t

#define CFG_VRSI                5   //+ Vint\t
#define CFG_VRSI_STD            6   //+ Vint_std\t
#define CFG_CALC_PH_VRSI        7   //+ estimated_pH_int\r\n

#define CFG_VRSE                8   //+ Vext
#define CFG_VRSE_STD            9   // + Vext_std
#define CFG_CALC_PH_VRSE        10   //+ estimated_pH_ext\r\n (new 6May2019 TM)

#define CFG_VRSI_BIASED         11   //+ Vint_offset\t
#define CFG_VRSI_BIASED_STD     12   //+ Vint_offset_std\t
#define CFG_VRSE_BIASED         13   //+ Vext_offset\t
#define CFG_VRSE_BIASED_STD     14   //+ Vext_offset_std\t


#define CFG_V_COUNTER_ELECT     15   //+ Vcounter_electrode
#define CFG_V_COUNTER_ELECT_STD 16   //+ Vcounter_electrode_std
#define CFG_I_COUNTER           17   // + Counter_current
#define CFG_I_SUBSTRATE         18   //+ Substrate_current

#define CFG_VIN_BAT_VOLT        19   //+ Battery_Volt
#define CFG_BIAS_BAT_POS        20   //+ Bias Bat Volt
#define CFG_BIAS_BAT_NEG        21

#define CFG_BRD_TEMP            22   //+ Board_Temperature\t
#define CFG_BRD_HUMIDITY        23   // + Humidity_sensor


#define CFG_UART3_INST          24      // UART3 Instrument, was #define CFG_OPTODE              24   // Aanderaa optode
#define CFG_UART4_INST          25   // Aanderaa or MicroCat conductivity, AKA CFG_CONDUCTIVITY new 25 Mar 2021, was CFG_CTD

#define CFG_SPARE1              26  // was spare1 CFG_OCR
#define CFG_SPARE2              27

#define CFG_SPARE3              28
#define CFG_SPARE4              29
#define CFG_SPARE5              30
#define CFG_SPARE6              31

// Instrument drivers for UART3/Optode port and UART4/CTD port (sequential numbering, renumber is OK to do)
#define INST_OPTODE_NOTDEFD     0       // Instrument driver types for Uart3 / Optode port
#define INST_OPTODE             1
#define INST_OCR504             2
#define INST_NANOFET            3
#define INST_PICOPH             4

#define INST_CTD_NOTDEFD        5       // Instrument driver types for Uart4 / CTD port
#define INST_SBE37_MICROCAT     6
#define INST_AANDERAA_5860      7
#define INST_ADV                8

// MAX_NUMOF_CONFIG_FIELDS is set to 32 above.

//sys_data.app_cfg
// App config, used for bringing out new features, etc
#define APPCFG_SAMPLING_DIAG    0   // switch on timing printfs in fast_sample
#define APPCFG_TEMPC_SH_ALG     1   // used in Durafet_temp to switch algorithm
#define APPCFG_MICROSD_ENABLE   2   // APPCFG_SAMP_FLEX        2   // In fast_sample, used to allow for user edit variables for Trials and sps per ADS1284 sample
#define APPCFG_MENU_LEVEL       3
#define APPCFG_DEPLOY_UARTECHO  4   //Turn off uartEcho in deployment to help m2m with labview   //#define APPCFG_SPARE4           4
#define APPCFG_EXEC_SWITCHERONI 5   // Was APPCFG_SPARE5
#define APPCFG_SPARE6           6
#define APPCFG_SPARE7           7
#define APPCFG_SPARE8           8
#define APPCFG_SPARE9           9
#define APPCFG_SPARE10          10
#define APPCFG_SPARE11          11
#define APPCFG_SPARE12          12
#define APPCFG_SPARE13          13
#define APPCFG_SPARE14          14
#define APPCFG_SPARE15          15


// Defines for exec / sampling function called in main
#define EXEC_DEPLOY               0
#define EXEC_EDDY_COVARIANCE      1
#define EXEC_FASTSAMP             2
// Defaults and limits
#define EXEC_MAXDEFD                EXEC_FASTSAMP
#define EXEC_DEFAULT                EXEC_DEPLOY




//----------- Key Defs --------
#define CTRL_X          24
//#define CTRL-X          CTRL_X


// Global variables
extern struct systemData sys_data;
extern struct systemDataVolatile sys_data_vol;
extern struct systemDataVolatile sys_data_chg;

void read_bias_bat(void);

void display_battery_boardSensors(void);
void display_ph_ref_therm_volts(void);
void display_calcd_pH_intRef_therm(void);
void display_calcd_pH_extRef_therm_sal(float Salinity);
void communicate_with_instruments(void);
int power_output_tests(void);
void test_24bit_adc_mux(void);
int board_qa_and_init(int initFlg);


void initSysDataVolatileVariables(void);

void SysTickHandler(void);
unsigned long Timer_10ms(bool reset);
unsigned long Timer_1ms(bool reset);
void ms_delay(unsigned int msec);
void delay_sec(unsigned int secs);
void delay_msec(unsigned int msec);
void delay_usec(unsigned int usec);
struct tm *get_RTC_time(void);

uint32_t storeSysDataVariables(void); //EEPROM
void retrieveSysDataVariables(void);
uint32_t  storeSysSampFRAMVariables(void);      //was void storeSysSampFRAMVariables(void);  //FRAM
void retrieveSysSampFRAMVariables(void);

int verifySysDataVariables(void);
uint32_t smartStoreSysData(void);

void initSysSampFRAMVariables(void);

int isNameInSavedDataString(char* name);
void saveSysDataVariableName();

float batt_volt();
float batt_volt_iso();


float controller_temp();
float pressure(void);
//int writeDeploymentInformationHeader(const time_t currentTime);  //deprecated 21 Apr 2021

void sendlast_takesample(void);
//void fast_sample(int txFlg);  // moved to sampling.c

void error_store(const char *error_buff);
float DuraFET_temp(float V_therm, float TCOffset);
float calc_pHext(float Eext, float TC, float salt);
float calc_pHint(float Eint, float TC);
void ph_calib(void);

float read_env_sensors(void);




#endif /* PHFETSOS_SYSTEM_H_ */
