int main(void) { uint32_t data_counter=0; //used as data timestamp uint8_t deadly_flashes=0,system_state=0,repetition_counter=0; int16_t sensor_data, sensor_raw_data[3]={}; //used for handling data passed back from sensors int16_t sfe_sensor_ref_buff[2][3],sfe_sensor_ref_buff_old[2][3];//used to detect and fix I2C bus lockup RTC_t RTC_time; wave_stuffer Gyro_wav_stuffer={0,0},Accel_wav_stuffer={0,0};//Used to controlling wav file bit packing SystemInit(); //Sets up the clk setup_gpio(); //Initialised pins, and detects boot source DBGMCU_Config(DBGMCU_IWDG_STOP, ENABLE); //Watchdog stopped during JTAG halt if(RCC->CSR&RCC_CSR_IWDGRSTF) { //Watchdog reset, turn off RCC->CSR|=RCC_CSR_RMVF; //Reset the reset flags shutdown(); } SysTick_Configuration(); //Start up system timer at 100Hz for uSD card functionality Watchdog_Config(WATCHDOG_TIMEOUT); //Set the watchdog Watchdog_Reset(); //Reset watchdog as soon as possible incase it is still running at power on rtc_init(); //Real time clock initialise - (keeps time unchanged if set) Usarts_Init(); ISR_Config(); rprintfInit(__usart_send_char); //Printf over the bluetooth if(USB_SOURCE==bootsource) { Set_System(); //This actually just inits the storage layer Set_USBClock(); USB_Interrupts_Config(); USB_Init(); uint32_t nojack=0x000FFFFF; //Countdown timer - a few hundered ms of 0v on jack detect forces a shutdown while (bDeviceState != CONFIGURED) { //Wait for USB config - timeout causes shutdown if(Millis>10000 || !nojack) //No USB cable - shutdown (Charger pin will be set to open drain, cant be disabled without usb) shutdown(); if(GET_CHRG_STATE) //Jack detect resets the countdown nojack=0x0FFFFF; nojack--; Watchdog_Reset(); //Reset watchdog here, if we are stalled here the Millis timeout should catch us } USB_Configured_LED(); EXTI_ONOFF_EN(); //Enable the off interrupt - allow some time for debouncing while(1) { //If running off USB (mounted as mass storage), stay in this loop - dont turn on anything if(Millis%1000>500) //1Hz on/off flashing switch_leds_on(); //Flash the LED(s) else switch_leds_off(); Watchdog_Reset(); __WFI(); //Sleep until something arrives } } else { if(!GET_PWR_STATE) //Check here to make sure the power button is still pressed, if not, sleep shutdown(); //This means a glitch on the supply line, or a power glitch results in sleep EXTI_ONOFF_EN(); //Enable the off interrupt - allow some time for debouncing ADC_Configuration(); //At present this is purely here to detect low battery do { battery_voltage=Battery_Voltage;//Have to flush adc for some reason Delay(25000); } while(fabs(Battery_Voltage-battery_voltage)>0.01 || !battery_voltage); I2C_Config(); //Setup the I2C bus Sensors=detect_sensors(0); //Search for connected sensors if(battery_voltage<BATTERY_STARTUP_LIMIT) deadly_flashes=1; if(!(Sensors&(1<<FOREHEAD_ACCEL))) //Check for any missing sensors deadly_flashes=2; if(!(Sensors&(1<<(FOREHEAD_GYRO-1)))) deadly_flashes=3; if(!(Sensors&(1<<(SFE_1_ACCEL-1)))) deadly_flashes=4; if(!(Sensors&(1<<(SFE_1_MAGNO-1)))) deadly_flashes=5; if(!(Sensors&(1<<(SFE_1_GYRO-1)))) deadly_flashes=6; if(!(Sensors&(1<<(SFE_2_ACCEL-3)))) deadly_flashes=7; if(!(Sensors&(1<<(SFE_2_MAGNO-3)))) deadly_flashes=8; if(!(Sensors&(1<<(SFE_2_GYRO-3)))) deadly_flashes=9; if((f_err_code = f_mount(0, &FATFS_Obj)))Usart_Send_Str((char*)"FatFs mount error\r\n");//This should only error if internal error else if(!deadly_flashes){ //FATFS and the I2C initialised ok, try init the card, this also sets up the SPI1 if(!f_open(&FATFS_logfile,"time.txt",FA_OPEN_EXISTING | FA_READ | FA_WRITE)) {//Try and open a time file to get the system time if(!f_stat((const TCHAR *)"time.txt",&FATFS_info)) {//Get file info if(!FATFS_info.fsize) {//Empty file RTC_time.year=(FATFS_info.fdate>>9)+1980;//populate the time struct (FAT start==1980, RTC.year==0) RTC_time.month=(FATFS_info.fdate>>5)&0x000F; RTC_time.mday=FATFS_info.fdate&0x001F; RTC_time.hour=(FATFS_info.ftime>>11)&0x001F; RTC_time.min=(FATFS_info.ftime>>5)&0x003F; RTC_time.sec=(FATFS_info.ftime<<1)&0x003E; rtc_settime(&RTC_time); rprintfInit(__fat_print_char);//printf to the open file printf("RTC set to %d/%d/%d %d:%d:%d\n",RTC_time.mday,RTC_time.month,RTC_time.year,\ RTC_time.hour,RTC_time.min,RTC_time.sec); } } f_close(&FATFS_logfile);//Close the time.txt file } rtc_gettime(&RTC_time); //Get the RTC time and put a timestamp on the start of the file rprintfInit(__str_print_char); //Print to the string //timestamp name printf("%d-%02d-%02dT%02d-%02d-%02d",RTC_time.year,RTC_time.month,RTC_time.mday,RTC_time.hour,RTC_time.min,RTC_time.sec); rprintfInit(__usart_send_char); //Printf over the bluetooth f_err_code = f_mkdir(print_string); //Try to make a directory where the logfiles will live if(f_err_code) { printf("FatFs drive error %d\r\n",f_err_code); if(f_err_code==FR_DISK_ERR || f_err_code==FR_NOT_READY) Usart_Send_Str((char*)"No uSD card inserted?\r\n"); repetition_counter=1; } else f_err_code=f_chdir(print_string);//enter our new directory if(f_err_code) { if(!repetition_counter) printf("FatFs drive error entering direcotry %d\r\n",f_err_code); repetition_counter=1; } else { strcat(print_string,".csv"); f_err_code=f_open(&FATFS_logfile,print_string,FA_CREATE_ALWAYS | FA_WRITE);//Try to open the main 100sps csv logfile } if(f_err_code) { if(!repetition_counter) printf("FatFs drive error creating logfile %d\r\n",f_err_code); repetition_counter=1; } else { print_string[strlen(print_string)-4]=0x00; //Wipe the .csv off the string strcat(print_string,"_accel.wav"); f_err_code=f_open(&FATFS_wavfile_accel,print_string,FA_CREATE_ALWAYS | FA_WRITE);//Try to open the accel wav logfile } if(f_err_code) { if(!repetition_counter) printf("FatFs drive error creating accel wav file %d\r\n",f_err_code); repetition_counter=1; } else { print_string[strlen(print_string)-9]=0x00; //Wipe the accel.wav off the string strcat(print_string,"gyro.wav"); f_err_code=f_open(&FATFS_wavfile_gyro,print_string,FA_CREATE_ALWAYS | FA_WRITE);//Try to open the gyro wav logfile } if(f_err_code) { if(!repetition_counter) printf("FatFs drive error creating gyro wav file %d\r\n",f_err_code); } else { //We have a mounted card print_string[0]=0x00; //Wipe the string f_err_code=f_lseek(&FATFS_logfile, PRE_SIZE);// Pre-allocate clusters if (f_err_code || f_tell(&FATFS_logfile) != PRE_SIZE)// Check if the file size has been increased correctly Usart_Send_Str((char*)"Pre-Allocation error\r\n"); else { if((f_err_code=f_lseek(&FATFS_logfile, 0)))//Seek back to start of file to start writing Usart_Send_Str((char*)"Seek error\r\n"); else rprintfInit(__str_print_char);//Printf to the logfile } if(f_err_code) f_close(&FATFS_logfile);//Close the already opened file on error else file_opened=0x01;//So we know to close the file properly on shutdown - bit mask for the files if(!f_err_code) { f_err_code=f_lseek(&FATFS_wavfile_accel, PRE_SIZE);// Pre-allocate clusters if (f_err_code || f_tell(&FATFS_wavfile_accel) != PRE_SIZE)// Check if the file size has been increased correctly Usart_Send_Str((char*)"Pre-Allocation error\r\n"); else { if((f_err_code=f_lseek(&FATFS_wavfile_accel, 0)))//Seek back to start of file to start writing Usart_Send_Str((char*)"Seek error\r\n"); } if(f_err_code) f_close(&FATFS_wavfile_accel);//Close the already opened file on error else file_opened|=0x02;//So we know to close the file properly on shutdown - bit mask for the files } if(!f_err_code) { f_err_code=f_lseek(&FATFS_wavfile_gyro, PRE_SIZE);// Pre-allocate clusters if (f_err_code || f_tell(&FATFS_wavfile_gyro) != PRE_SIZE)// Check if the file size has been increased correctly Usart_Send_Str((char*)"Pre-Allocation error\r\n"); else { if((f_err_code=f_lseek(&FATFS_wavfile_gyro, 0)))//Seek back to start of file to start writing Usart_Send_Str((char*)"Seek error\r\n"); } if(f_err_code) f_close(&FATFS_wavfile_gyro);//Close the already opened file on error else file_opened|=0x04;//So we know to close the file properly on shutdown - bit mask for the files } } } repetition_counter=0; //Reset this here //We die, but flash out a number of flashes first if(f_err_code || deadly_flashes) { //There was an init error for(;deadly_flashes;deadly_flashes--) { RED_LED_ON; Delay(200000); RED_LED_OFF; Delay(200000); Watchdog_Reset(); } RED_LED_ON; Delay(400000); shutdown(); //Abort after a (further )single red flash } }
int main(void) { uint8_t system_state=0, i2c_resets=0, si446x_resets=0;//used to track button press functionality and any errors uint8_t sensors=0; uint32_t repetition_counter=0; //Used to detect any I2C lockup uint8_t L3GD20_Data_Buffer_old[8]; //Used to test for noise in the gyro data (indicating that it is working) uint8_t UplinkFlags=0,CutFlags=0; uint16_t UplinkBytes=0; //Counters and flags for telemetry uint32_t last_telemetry=0,cutofftime=0,indtest=0,badgyro=0,permission_time=0,countdown_time=0,last_cuttest=0; uint16_t sentence_counter=0; uint8_t silab; //Cutdown config stuff here, atm uses hardcoded polygon defined in polygon.h static const int32_t Geofence[UK_GEOFENCE_POINTS*2]=UK_GEOFENCE; RTC_t RTC_time; _REENT_INIT_PTR(&my_reent); _impure_ptr = &my_reent; SystemInit(); //Sets up the clk setup_gpio(); //Initialised pins, and detects boot source DBGMCU_Config(DBGMCU_IWDG_STOP, ENABLE); //Watchdog stopped during JTAG halt RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR | RCC_APB1Periph_BKP, ENABLE);/* Enable PWR and BKP clocks */ PWR_BackupAccessCmd(ENABLE);/* Allow access to BKP Domain */ uint16_t shutdown_lock=BKP_ReadBackupRegister(BKP_DR3); //Holds the shutdown lock setting uint16_t reset_counter=BKP_ReadBackupRegister(BKP_DR2); //The number of consecutive failed reboot cycles PWR_BackupAccessCmd(DISABLE); if(RCC->CSR&RCC_CSR_IWDGRSTF && shutdown_lock!=SHUTDOWNLOCK_MAGIC) {//Watchdog reset, turn off RCC->CSR|=RCC_CSR_RMVF; //Reset the reset flags shutdown(); } if(USB_SOURCE==bootsource) { RCC->CFGR &= ~(uint32_t)RCC_CFGR_PPRE1_DIV16; RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE1_DIV4;//Swap the ABP1 bus to run at 12mhz rather than 4 if we booted from USB, makes USB fast enough } SysTick_Configuration(); //Start up system timer at 100Hz for uSD card functionality Watchdog_Config(WATCHDOG_TIMEOUT); //Set the watchdog Watchdog_Reset(); //Reset watchdog as soon as possible incase it is still running at power on rtc_init(); //Real time clock initialise - (keeps time unchanged if set) Usarts_Init(); ISR_Config(); rprintfInit(__usart_send_char); //Printf over the bluetooth if(USB_SOURCE==bootsource) { Set_System(); //This actually just inits the storage layer Set_USBClock(); USB_Interrupts_Config(); USB_Init(); uint32_t nojack=0x000FFFFF; //Countdown timer - a few hundered ms of 0v on jack detect forces a shutdown while (bDeviceState != CONFIGURED) { //Wait for USB config - timeout causes shutdown if((Millis>10000 && bDeviceState == UNCONNECTED)|| !nojack) //No USB cable - shutdown (Charger pin will be set to open drain, cant be disabled without usb) shutdown(); if(GET_VBUS_STATE) //Jack detect resets the countdown nojack=0x0FFFFF; nojack--; Watchdog_Reset(); //Reset watchdog here, if we are stalled here the Millis timeout should catch us } PWR_BackupAccessCmd(ENABLE); /* Allow access to BKP Domain */ BKP_WriteBackupRegister(BKP_DR3,0x0000);//Wipe the shutdown lock setting PWR_BackupAccessCmd(DISABLE); while(1) { if(!(Millis%1000) && bDeviceState == SUSPENDED) { Delay(100); if(!GET_VBUS_STATE) shutdown(); } Watchdog_Reset(); __WFI(); //Sleep mode } } if(!GET_PWR_STATE && !(CoreDebug->DHCSR&0x00000001) && shutdown_lock!=SHUTDOWNLOCK_MAGIC) {//Check here to make sure the power button is still pressed, if not, sleep if no debug and not in always on flight mode shutdown(); //This means a glitch on the supply line, or a power glitch results in sleep } // check to see if battery has enough charge to start ADC_Configuration(); //We leave this a bit later to allow stabilisation { uint32_t t=Millis; while(Millis<(t+100)){__WFI();} //Sensor+inst amplifier takes about 100ms to stabilise after power on } if(Battery_Voltage<BATTERY_STARTUP_LIMIT) { //We will have to turn off if(reset_counter<10) shutdown(); } Watchdog_Reset(); //Card Init can take a second or two // system has passed battery level check and so file can be opened {//Context uint8_t silabs_header[5]={}; uint8_t* silabs_header_=NULL; //Pointer to the array (if all goes ok) if((f_err_code = f_mount(0, &FATFS_Obj)))Usart_Send_Str((char*)"FatFs mount error\r\n");//This should only error if internal error else { //FATFS initialised ok, try init the card, this also sets up the SPI1 if(!(f_err_code=f_open(&FATFS_logfile,(const TCHAR*)"time.txt",FA_OPEN_EXISTING|FA_READ|FA_WRITE))){//Try to open time file get system time if(!f_stat((const TCHAR *)"time.txt",&FATFS_info)) {//Get file info if(FATFS_info.fsize<5) { //Empty file RTC_time.year=(FATFS_info.fdate>>9)+1980;//populate the time struct (FAT start==1980, RTC.year==0) RTC_time.month=(FATFS_info.fdate>>5)&0x000F; RTC_time.mday=FATFS_info.fdate&0x001F; RTC_time.hour=(FATFS_info.ftime>>11)&0x001F; RTC_time.min=(FATFS_info.ftime>>5)&0x003F; RTC_time.sec=(FATFS_info.ftime<<1)&0x003E; rtc_settime(&RTC_time); rprintfInit(__fat_print_char);//printf to the open file printf("RTC set to %d/%d/%d %d:%d:%d\n",RTC_time.mday,RTC_time.month,RTC_time.year,\ RTC_time.hour,RTC_time.min,RTC_time.sec); } } f_close(&FATFS_logfile); //Close the time.txt file } // load settings if file exists Watchdog_Reset(); //Card Init can take a second or two if(!f_open(&FATFS_logfile,(const TCHAR *)"settings.dat",FA_OPEN_EXISTING | FA_READ)) { UINT br; int8_t rtc_correction; f_read(&FATFS_logfile, (void*)(&rtc_correction),sizeof(rtc_correction),&br); //Use the setting to apply correction to the RTC if(br && (rtc_correction<30) && (rtc_correction>-92) && rtc_correction ) { PWR_BackupAccessCmd(ENABLE);/* Allow access to BKP Domain */ uint16_t tweaked_prescale = (0x0001<<15)-2;/* Try to run the RTC slightly too fast so it can be corrected either way */ RTC_WaitForSynchro(); /* Wait for RTC registers synchronization */ if( RTC->PRLL != tweaked_prescale ) {/*Note that there is a 0.5ppm offset here (correction 0==0.5ppm slow)*/ RTC_SetPrescaler(tweaked_prescale); /* RTC period = RTCCLK/RTC_PR = (32.768 KHz)/(32767-2+1) */ RTC_WaitForLastTask(); } BKP_SetRTCCalibrationValue((uint8_t) ((int16_t)31-(21*(int16_t)rtc_correction)/(int16_t)20) ); BKP_RTCOutputConfig(BKP_RTCOutputSource_None);/* Ensure any output is disabled here */ /* Lock access to BKP Domain */ PWR_BackupAccessCmd(DISABLE); } else if(br && ((uint8_t)rtc_correction==0x91) ) {/* 0x91 magic flag sets the RTC clock output on */ PWR_BackupAccessCmd(ENABLE);/* Allow access to BKP Domain */ BKP_RTCOutputConfig(BKP_RTCOutputSource_CalibClock);/* Output a 512Hz reference clock on the TAMPER pin*/ PWR_BackupAccessCmd(DISABLE); } if(br) { f_read(&FATFS_logfile, (void*)(&shutdown_lock),sizeof(shutdown_lock),&br);/*This needs to be set with the same magic flag value*/ if(br==2) { PWR_BackupAccessCmd(ENABLE);/* Allow access to BKP Domain */ BKP_WriteBackupRegister(BKP_DR3,shutdown_lock);//Wipe the shutdown lock setting PWR_BackupAccessCmd(DISABLE); } } if(br==2) { //Read was successful, next try to read 5 bytes of packet header f_read(&FATFS_logfile, (void*)(silabs_header),5,&br); if(br!=5) silabs_header_=silabs_header; } f_close(&FATFS_logfile); //Close the settings.dat file } #ifndef SINGLE_LOGFILE rtc_gettime(&RTC_time); //Get the RTC time and put a timestamp on the start of the file rprintfInit(__str_print_char); //Print to the string printf("%02d-%02d-%02dT%02d-%02d-%02d-%s.csv",RTC_time.year,RTC_time.month,RTC_time.mday,RTC_time.hour,RTC_time.min,RTC_time.sec,"Log");//Timestamp name rprintfInit(__usart_send_char); //Printf over the bluetooth #endif Watchdog_Reset(); //Card Init can take a second or two if((f_err_code=f_open(&FATFS_logfile,(TCHAR*)LOGFILE_NAME,FA_CREATE_ALWAYS | FA_WRITE))) {//Present Delay(10000); if((f_err_code=f_open(&FATFS_logfile,(TCHAR*)LOGFILE_NAME,FA_CREATE_ALWAYS | FA_WRITE))) {//Try again printf("FatFs drive error %d\r\n",f_err_code); if(f_err_code==FR_DISK_ERR || f_err_code==FR_NOT_READY) Usart_Send_Str((char*)"No uSD card inserted?\r\n"); } } else { Watchdog_Reset(); //Card Init can take a second or two print_string[strlen(print_string)-4]=0x00;//Wipe the .csv off the string strcat(print_string,"_gyro.wav"); if((f_err_code=f_open(&FATFS_wavfile_gyro,(TCHAR*)LOGFILE_NAME,FA_CREATE_ALWAYS | FA_WRITE))) {//Present printf("FatFs drive error %d\r\n",f_err_code); if(f_err_code==FR_DISK_ERR || f_err_code==FR_NOT_READY) Usart_Send_Str((char*)"No uSD card inserted?\r\n"); } else { //We have a mounted card f_err_code=f_lseek(&FATFS_logfile, PRE_SIZE);// Pre-allocate clusters if (f_err_code || f_tell(&FATFS_logfile) != PRE_SIZE)// Check if the file size has been increased correctly Usart_Send_Str((char*)"Pre-Allocation error\r\n"); else { if((f_err_code=f_lseek(&FATFS_logfile, 0)))//Seek back to start of file to start writing Usart_Send_Str((char*)"Seek error\r\n"); else rprintfInit(__str_print_char);//Printf to the logfile } if(f_err_code) f_close(&FATFS_logfile);//Close the already opened file on error else file_opened=1; //So we know to close the file properly on shutdown if(file_opened==1) { Watchdog_Reset(); //Card Init can take a second or two if (f_err_code || f_tell(&FATFS_wavfile_gyro) != PRE_SIZE)// Check if the file size has been increased correctly Usart_Send_Str((char*)"Pre-Allocation error\r\n"); else { if((f_err_code=f_lseek(&FATFS_logfile, 0)))//Seek back to start of file to start writing Usart_Send_Str((char*)"Seek error\r\n"); else rprintfInit(__str_print_char);//Printf to the logfile } if(f_err_code) f_close(&FATFS_wavfile_gyro);//Close the already opened file on error else file_opened|=2; //So we know to close the file properly on shutdown } } } } f_err_code|=write_wave_header(&FATFS_wavfile_gyro, 4, 100, 16);//4 channels, last channel is for the current rpm Watchdog_Reset(); //Card Init can take a second or two //Setup and test the silabs radio silab=si446x_setup(silabs_header_); if(silab!=0x44) { //Should return the device code print_string[0]=0x00; printf("Silabs: %02x\n",silab); f_puts("Silabs detect error, got:",&FATFS_logfile); f_puts(print_string,&FATFS_logfile); shutdown_filesystem(ERR, file_opened);//So we log that something went wrong in the logfile shutdown(); } }//Context
int main(void) { uint32_t ppg; //PPG channel uint32_t data_counter=0; //used as data timestamp uint8_t system_state=0; //used to track button press functionality float sensor_data; //used for handling data passed back from sensors RTC_t RTC_time; _REENT_INIT_PTR(&my_reent); _impure_ptr = &my_reent; SystemInit(); //Sets up the clk setup_gpio(); //Initialised pins, and detects boot source DBGMCU_Config(DBGMCU_IWDG_STOP, ENABLE); //Watchdog stopped during JTAG halt if(RCC->CSR&RCC_CSR_IWDGRSTF) { //Watchdog reset, turn off RCC->CSR|=RCC_CSR_RMVF; //Reset the reset flags shutdown(); } SysTick_Configuration(); //Start up system timer at 100Hz for uSD card functionality Watchdog_Config(WATCHDOG_TIMEOUT); //Set the watchdog Watchdog_Reset(); //Reset watchdog as soon as possible incase it is still running at power on rtc_init(); //Real time clock initialise - (keeps time unchanged if set) Usarts_Init(); ISR_Config(); rprintfInit(__usart_send_char); //Printf over the bluetooth if(USB_SOURCE==bootsource) { Set_System(); //This actually just inits the storage layer Set_USBClock(); USB_Interrupts_Config(); USB_Init(); uint32_t nojack=0x000FFFFF; //Countdown timer - a few hundered ms of 0v on jack detect forces a shutdown while (bDeviceState != CONFIGURED) { //Wait for USB config - timeout causes shutdown if(Millis>10000 || !nojack) //No USB cable - shutdown (Charger pin will be set to open drain, cant be disabled without usb) shutdown(); if(GET_VBUS_STATE) //Jack detect resets the countdown nojack=0x0FFFFF; nojack--; Watchdog_Reset(); //Reset watchdog here, if we are stalled here the Millis timeout should catch us } USB_Configured_LED(); EXTI_ONOFF_EN(); //Enable the off interrupt - allow some time for debouncing while(1) { //If running off USB (mounted as mass storage), stay in this loop - dont turn on anything if(Millis%1000>500) //1Hz on/off flashing switch_leds_on(); //Flash the LED(s) else switch_leds_off(); Watchdog_Reset(); } } if(!GET_PWR_STATE) //Check here to make sure the power button is still pressed, if not, sleep shutdown(); //This means a glitch on the supply line, or a power glitch results in sleep for(uint8_t n=0;n<PPG_CHANNELS;n++) init_buffer(&(Buff[n]),PPG_BUFFER_SIZE);//Enough for ~0.25S of data setup_pwm(); //Enable the PWM outputs on all three channels Delay(100000); //Sensor+inst amplifier takes about 100ms to stabilise after power on ADC_Configuration(); //We leave this a bit later to allow stabilisation calibrate_sensor(); //Calibrate the offset on the diff pressure sensor EXTI_ONOFF_EN(); //Enable the off interrupt - allow some time for debouncing I2C_Config(); //Setup the I2C bus uint8_t sensors_=detect_sensors(); //Search for connected sensors sensor_data=GET_BATTERY_VOLTAGE; //Have to flush adc for some reason Delay(10000); if(!(sensors_&~(1<<PRESSURE_HOSE))||GET_BATTERY_VOLTAGE<BATTERY_STARTUP_LIMIT) {//We will have to turn off Watchdog_Reset(); //LED flashing takes a while if(abs(Reported_Pressure)>PRESSURE_MARGIN) Set_Motor(-1); //If the is air backpressure, dump to rapidly drop to zero pressure before turnoff if(file_opened) f_close(&FATFS_logfile); //be sure to terminate file neatly red_flash(); Delay(400000); red_flash(); //Two flashes means battery abort -----------------ABORT 2 if(sensors_&~(1<<PRESSURE_HOSE)) shutdown(); Delay(400000); red_flash(); //Three flashes means no sensors abort ------------ABORT 3 shutdown(); } if((f_err_code = f_mount(0, &FATFS_Obj)))Usart_Send_Str((char*)"FatFs mount error\r\n");//This should only error if internal error else { //FATFS initialised ok, try init the card, this also sets up the SPI1 if(!f_open(&FATFS_logfile,"time.txt",FA_OPEN_EXISTING | FA_READ | FA_WRITE)) {//Try and open a time file to get the system time if(!f_stat((const TCHAR *)"time.txt",&FATFS_info)) {//Get file info if(!FATFS_info.fsize) { //Empty file RTC_time.year=(FATFS_info.fdate>>9)+1980;//populate the time struct (FAT start==1980, RTC.year==0) RTC_time.month=(FATFS_info.fdate>>5)&0x000F; RTC_time.mday=FATFS_info.fdate&0x001F; RTC_time.hour=(FATFS_info.ftime>>11)&0x001F; RTC_time.min=(FATFS_info.ftime>>5)&0x003F; RTC_time.sec=(FATFS_info.ftime<<1)&0x003E; rtc_settime(&RTC_time); rprintfInit(__fat_print_char);//printf to the open file printf("RTC set to %d/%d/%d %d:%d:%d\n",RTC_time.mday,RTC_time.month,RTC_time.year,\ RTC_time.hour,RTC_time.min,RTC_time.sec); } } f_close(&FATFS_logfile); //Close the time.txt file } #ifndef SINGLE_LOGFILE rtc_gettime(&RTC_time); //Get the RTC time and put a timestamp on the start of the file rprintfInit(__str_print_char); //Print to the string printf("%d-%d-%dT%d-%d-%d.txt",RTC_time.year,RTC_time.month,RTC_time.mday,RTC_time.hour,RTC_time.min,RTC_time.sec);//Timestamp name rprintfInit(__usart_send_char); //Printf over the bluetooth #endif if((f_err_code=f_open(&FATFS_logfile,LOGFILE_NAME,FA_CREATE_ALWAYS | FA_WRITE))) {//Present printf("FatFs drive error %d\r\n",f_err_code); if(f_err_code==FR_DISK_ERR || f_err_code==FR_NOT_READY) Usart_Send_Str((char*)"No uSD card inserted?\r\n"); } else { //We have a mounted card f_err_code=f_lseek(&FATFS_logfile, PRE_SIZE);// Pre-allocate clusters if (f_err_code || f_tell(&FATFS_logfile) != PRE_SIZE)// Check if the file size has been increased correctly Usart_Send_Str((char*)"Pre-Allocation error\r\n"); else { if((f_err_code=f_lseek(&FATFS_logfile, 0)))//Seek back to start of file to start writing Usart_Send_Str((char*)"Seek error\r\n"); else rprintfInit(__str_print_char);//Printf to the logfile } if(f_err_code) f_close(&FATFS_logfile);//Close the already opened file on error else file_opened=1; //So we know to close the file properly on shutdown } }