Jon Freeman / Mbed 2 deprecated Alternator2020_06

Dependencies:   mbed BufferedSerial Servo2 PCT2075 I2CEeprom FastPWM

Committer:
JonFreeman
Date:
Sat Dec 05 12:40:17 2020 +0000
Revision:
5:6ca3e7ffc553
Parent:
4:28cc0cf01570
Code for 'Smart Regulator' to August 2020, published as is. Basic low-level functions all thoroughly tested and debugged, top level algorithms have scope for further development - over to you! For help contact jon @ jons-workshop[.com

Who changed what in which revision?

UserRevisionLine numberNew contents of line
JonFreeman 5:6ca3e7ffc553 1 /*******************************************************************************
JonFreeman 5:6ca3e7ffc553 2 DON'T FORGET TO REMOVE SOLDER LINKS SB16 AND SB18 ON NUCLEO-L432KC BOARD
JonFreeman 5:6ca3e7ffc553 3 *******************************************************************************/
JonFreeman 0:77803b3ee157 4 #include "mbed.h"
JonFreeman 0:77803b3ee157 5 #include "Alternator.h"
JonFreeman 3:43cb067ecd00 6 #include "BufferedSerial.h"
JonFreeman 3:43cb067ecd00 7 #include "I2CEeprom.h"
JonFreeman 3:43cb067ecd00 8 #include "LM75B.h" // New I2C temp sensor code March 2020 (to suit possible next board issue, harmless otherwise)
JonFreeman 3:43cb067ecd00 9 #include "rpm.h"
JonFreeman 3:43cb067ecd00 10 #include "field.h"
JonFreeman 4:28cc0cf01570 11 #include "gps_mod.h"
JonFreeman 5:6ca3e7ffc553 12
JonFreeman 3:43cb067ecd00 13 //#include "baro.h"
JonFreeman 3:43cb067ecd00 14
JonFreeman 3:43cb067ecd00 15 #ifdef TARGET_NUCLEO_L432KC // 24LC and LM75 work
JonFreeman 3:43cb067ecd00 16 // #define SDA_PIN D0 // good
JonFreeman 3:43cb067ecd00 17 // #define SCL_PIN D1
JonFreeman 3:43cb067ecd00 18 #define SDA_PIN D4 // good
JonFreeman 3:43cb067ecd00 19 #define SCL_PIN D5
JonFreeman 3:43cb067ecd00 20 #endif
JonFreeman 3:43cb067ecd00 21
JonFreeman 3:43cb067ecd00 22 /*******************************************************************************
JonFreeman 3:43cb067ecd00 23 DON'T FORGET TO REMOVE SOLDER LINKS SB16 AND SB18 ON L432KC BOARD
JonFreeman 3:43cb067ecd00 24 *******************************************************************************/
JonFreeman 3:43cb067ecd00 25 //During test LED across field has been useful visual aid. Incorporate similar on new board.
JonFreeman 2:8e7b51353f32 26 /*
JonFreeman 2:8e7b51353f32 27 * May 2020 NOTE input circuit to analogue in driver pot zeners input to 3v6, then pot reduces by about 1/3.
JonFreeman 2:8e7b51353f32 28 * This makes input reading only about 0.0 to 0.66
JonFreeman 2:8e7b51353f32 29 * Temp bodge, mult by 1.5
JonFreeman 3:43cb067ecd00 30
JonFreeman 3:43cb067ecd00 31 * Two voltages now measured. Link voltage (alternator output), and field supply (which may come from battery when main output low)
JonFreeman 2:8e7b51353f32 32 */
JonFreeman 0:77803b3ee157 33
JonFreeman 0:77803b3ee157 34 /*
JonFreeman 0:77803b3ee157 35 Alternator Regulator
JonFreeman 0:77803b3ee157 36 Jon Freeman
JonFreeman 3:43cb067ecd00 37 June 2019 - June 2020
JonFreeman 1:450090bdb6f4 38
JonFreeman 3:43cb067ecd00 39 ** Prototype built using Nucleo L432KC. Having solved i2c problem, this looks good for final product
JonFreeman 0:77803b3ee157 40
JonFreeman 1:450090bdb6f4 41 ** main loop frequency upped from 32Hz to 100Hz **
JonFreeman 1:450090bdb6f4 42
JonFreeman 1:450090bdb6f4 43 WHAT THIS PROGRAMME DOES - Controls 4 stroke petrol engine driving vehicle alternator with new custom regulator
JonFreeman 1:450090bdb6f4 44
JonFreeman 3:43cb067ecd00 45 Electronics powered by higher voltage of small 12v backup battery, or alternator output
JonFreeman 1:450090bdb6f4 46 Note only Field+ and MAX5035 supplied thus, all else powered from MAX outputs.
JonFreeman 1:450090bdb6f4 47 Starting engine provides rectified tickle from magneto to enable MAX5035 creating +5 and +3v3 supplies.
JonFreeman 3:43cb067ecd00 48 Alternative, selected by jumper position, is external switch - battery+ to MAX enable circuit. ** Review this **
JonFreeman 3:43cb067ecd00 49 Anytime engine revs measured < TICKOVER_RPM (or some such) RPM, field current OFF (by pwm 0) , see speed related pwm limit table
JonFreeman 0:77803b3ee157 50
JonFreeman 0:77803b3ee157 51 BEGIN
JonFreeman 1:450090bdb6f4 52 Loop forever at 100 Hz {
JonFreeman 1:450090bdb6f4 53 Read engine RPM by monitoring engine tacho signal present on engine On/Off switch line
JonFreeman 1:450090bdb6f4 54 Adjust Alternator field current max limit according to RPM (analogue regulator limits output voltage)
JonFreeman 0:77803b3ee157 55 Measure system voltage (just in case this is ever useful)
JonFreeman 0:77803b3ee157 56 Respond to any commands arriving at serial port (setup and test link to laptop)
JonFreeman 0:77803b3ee157 57 Flash LED at 8 Hz as proof of life
JonFreeman 0:77803b3ee157 58 }
JonFreeman 0:77803b3ee157 59 END
JonFreeman 0:77803b3ee157 60
JonFreeman 0:77803b3ee157 61 INPUTS AnalogIn x 2 - Ammeter chip - current and offset AnalogIns
JonFreeman 0:77803b3ee157 62 INPUT AnalogIn - System voltage for info only.
JonFreeman 0:77803b3ee157 63 INPUT AnalogIn - ExtRevDemand
JonFreeman 0:77803b3ee157 64 INPUT AnalogIn - DriverPot
JonFreeman 0:77803b3ee157 65 INPUT Pulse engine speed indicator, speed checked against EEPROM data to select max pwm duty ratio for this speed
JonFreeman 0:77803b3ee157 66 INPUT Final pwm gate drive wired back to InterruptIn ** MAYBE USEFUL OR NOT ** Could read this back via serial to laptop
JonFreeman 0:77803b3ee157 67 OUTPUT pwm to MCP1630. This is clock to pwm chip. Also limits max duty ratio
JonFreeman 0:77803b3ee157 68 RS232 serial via USB to setup eeprom data
JonFreeman 0:77803b3ee157 69 */
JonFreeman 0:77803b3ee157 70
JonFreeman 0:77803b3ee157 71 /**
JonFreeman 0:77803b3ee157 72 * Jumpers fitted to small mbed Nucleo boards - D5 - A5 and D4 - A4 CHECK - yes
JonFreeman 0:77803b3ee157 73 */
JonFreeman 3:43cb067ecd00 74 //#ifdef TARGET_NUCLEO_L432KC // Has to be, quite settled now on this, having solved i2c problems
JonFreeman 3:43cb067ecd00 75 BufferedSerial pc (USBTX, USBRX, 4096, 4, NULL); // Comms port to pc or terminal using USB lead
JonFreeman 2:8e7b51353f32 76 //BufferedSerial LocalCom (PA_9, PA_10); // New March 2019 - Taken out for i2c test 6/6/2020
JonFreeman 2:8e7b51353f32 77
JonFreeman 0:77803b3ee157 78 // INPUTS :
JonFreeman 3:43cb067ecd00 79 AnalogIn Ain_Link_Volts (A6); // Sniff of alternator output, not used in control loop as done using analogue MCP1630
JonFreeman 4:28cc0cf01570 80 AnalogIn Ammeter_In (A0); // Output of ASC709LLFTR ammeter chip (pin 20), used to increase engine revs if need be
JonFreeman 1:450090bdb6f4 81
JonFreeman 3:43cb067ecd00 82 // Nov 2019. Not convinced Ext_Rev_Demand is useful ** July 2020 - repurposed, voltmeter Field_Supply_V
JonFreeman 2:8e7b51353f32 83 //AnalogIn Ext_Rev_Demand (D3); // Servo determines engine revs, servo out to be higher of Ext_Rev_Demand and internal calc
JonFreeman 3:43cb067ecd00 84 AnalogIn Field_Supply_V (D3); // Servo determines engine revs, servo out to be higher of Ext_Rev_Demand and internal calc
JonFreeman 1:450090bdb6f4 85
JonFreeman 4:28cc0cf01570 86 AnalogIn Driver_Pot (A1); // Moved 31/07/2020 from A3 to free up A3 for use as AnalogOut
JonFreeman 0:77803b3ee157 87
JonFreeman 3:43cb067ecd00 88 BufferedSerial gps_module (D1, D0, 2048, 4, NULL); // For gps - added July 2020
JonFreeman 3:43cb067ecd00 89
JonFreeman 0:77803b3ee157 90 /*
JonFreeman 4:28cc0cf01570 91 MODULE PIN USAGE - Updated Aug 2020
JonFreeman 4:28cc0cf01570 92 1 PA_9 D1 LocalCom Tx
JonFreeman 4:28cc0cf01570 93 2 PA_10 D0 LocalCom Rx GPS maybe
JonFreeman 0:77803b3ee157 94 3 NRST
JonFreeman 0:77803b3ee157 95 4 GND
JonFreeman 4:28cc0cf01570 96 5 PA12_D2 InterruptIn VEXT PWM controller output folded back for cpu to monitor, useful on test to read what pwm required to do what
JonFreeman 4:28cc0cf01570 97 6 PB_0 D3 AnalogIn Field supply voltage
JonFreeman 0:77803b3ee157 98 7 PB_7 D4 SDA i2c to 24LC memory
JonFreeman 0:77803b3ee157 99 8 PB_6 D5 SCL i2c to 24LC memory
JonFreeman 4:28cc0cf01570 100 9 PB_12 D6 DigitalOut CHARGE_PUMP new Aug 2020
JonFreeman 0:77803b3ee157 101 10 N.C.
JonFreeman 0:77803b3ee157 102 11 N.C.
JonFreeman 1:450090bdb6f4 103 12 PA_8 D9 InterruptIn pulse_tacho from engine magneto, used to measure rpm
JonFreeman 5:6ca3e7ffc553 104 13 PA_11 D10 Servo
JonFreeman 4:28cc0cf01570 105 14 PB_5 D11 NEW June 2019 - Output engine tacho cleaned-up, brought out to testpoint 4 NOT REALLY USEFUL
JonFreeman 4:28cc0cf01570 106 15 PB_4 D12 Scope_probe NOT REALLY USEFUL
JonFreeman 4:28cc0cf01570 107 16 PB_3 D13 LED Onboard LED
JonFreeman 0:77803b3ee157 108 17 3V3
JonFreeman 0:77803b3ee157 109 18 AREF
JonFreeman 4:28cc0cf01570 110 19 PA_0 A0 AnalogIn Driver Pot
JonFreeman 4:28cc0cf01570 111 20 PA_1 A1 AnalogIn Ammeter_In
JonFreeman 4:28cc0cf01570 112 21 PA_3 A2 PwmOut PWM_OSC_IN Timebase for pwm, also determines max duty ratio
JonFreeman 4:28cc0cf01570 113 //22 PA_4 A3 AnalogOut A_OUT control signal to following traction motor ESC
JonFreeman 4:28cc0cf01570 114 22 PA_4 A3 AnalogOut REF_VAR reference voltage to MCP1630, allows software to set alternator output voltage
JonFreeman 4:28cc0cf01570 115 23 PA_5 A4 AnalogOut A_OUT control signal to following traction motor ESC
JonFreeman 4:28cc0cf01570 116 24 PA_6 A5 Spare
JonFreeman 4:28cc0cf01570 117 25 PA_7 A6 AnalogIn V_Sample system link voltage
JonFreeman 4:28cc0cf01570 118 26 PA_2 A7 Not useable, taken by uart
JonFreeman 0:77803b3ee157 119 27 5V
JonFreeman 0:77803b3ee157 120 28 NRST
JonFreeman 0:77803b3ee157 121 29 GND
JonFreeman 0:77803b3ee157 122 30 VIN
JonFreeman 0:77803b3ee157 123 */
JonFreeman 0:77803b3ee157 124
JonFreeman 2:8e7b51353f32 125 // Test 6/6/2020 to get i2c working
JonFreeman 3:43cb067ecd00 126 //I2C i2c (D0, D1); // For 24LC64 eeprom correct
JonFreeman 2:8e7b51353f32 127 //I2C i2c (D1, D0); // For 24LC64 eeprom DEFINITELY WRONG
JonFreeman 2:8e7b51353f32 128 // Test 6/6/2020 to get i2c working
JonFreeman 2:8e7b51353f32 129
JonFreeman 3:43cb067ecd00 130 //InterruptIn pulse_tacho (D9); // Signal from engine magneto (clipped by I limit resistor and 3v3 zener)
JonFreeman 3:43cb067ecd00 131 // Note D9 still used but taken to rpm class object
JonFreeman 3:43cb067ecd00 132 //InterruptIn VEXT (D2); // PWM controller output folded back for cpu to monitor, useful on test to read what pwm required to do what
JonFreeman 3:43cb067ecd00 133 // Note D2 still used but taken to field class object
JonFreeman 0:77803b3ee157 134 // OUTPUTS :
JonFreeman 4:28cc0cf01570 135 AnalogOut REF_VAR (A4); // Variable REF to MCP1630 enables software control of output voltage - NEW Aug 2020
JonFreeman 4:28cc0cf01570 136 AnalogOut A_OUT (A3); // Control voltage out to traction motor ESCs
JonFreeman 1:450090bdb6f4 137 DigitalOut Scope_probe (D12); // Handy pin to hang scope probe onto while developing code
JonFreeman 1:450090bdb6f4 138 DigitalOut myled (LED1); // Green LED on board is PB_3 D13
JonFreeman 3:43cb067ecd00 139 //PwmOut PWM_OSC_IN (A2); // Can alter prescaler can not use A5 NOW DONE IN CLASS
JonFreeman 1:450090bdb6f4 140 //PwmOut A_OUT (A2); // Can alter prescaler can not use A5 PIN STOLEN BY PWM_OSC_IN
JonFreeman 1:450090bdb6f4 141
JonFreeman 3:43cb067ecd00 142 //PwmOut Test_RPM (PA_6);
JonFreeman 2:8e7b51353f32 143 Timer microsecs; // 64 bit counter, rolls over in half million years
JonFreeman 0:77803b3ee157 144 Ticker loop_timer; // Device to cause periodic interrupts, used to sync iterations of main programme loop - slow
JonFreeman 0:77803b3ee157 145
JonFreeman 3:43cb067ecd00 146 extern char * get_mode_text (uint32_t mode) ;
JonFreeman 3:43cb067ecd00 147
JonFreeman 4:28cc0cf01570 148 DigitalOut CHARGE_PUMP (D6);
JonFreeman 3:43cb067ecd00 149 I2CEeprom eeprom (SDA_PIN, SCL_PIN, 0xa0, eeprom_page_size, 8192, 100000);
JonFreeman 3:43cb067ecd00 150 extern ee_settings_2020 user_settings ;
JonFreeman 4:28cc0cf01570 151 Engine_Manager Engine (D9, D11, D10); // Pins are magneto in, cleaned magneto out, servo
JonFreeman 4:28cc0cf01570 152 FieldControl Field (A2, D2); // PWM pin for MCP1630 PWM_OSC_IN, InterruptIn for signal out of MCP1630 VEXTFB
JonFreeman 3:43cb067ecd00 153 PCT2075 temp_sensor( SDA_PIN, SCL_PIN ); // or LM75B temp_sensor( p?, p? ); Added March 2020
JonFreeman 3:43cb067ecd00 154
JonFreeman 3:43cb067ecd00 155 //class MPL3115A2 baro ;
JonFreeman 3:43cb067ecd00 156
JonFreeman 0:77803b3ee157 157 // SYSTEM CONSTANTS
JonFreeman 0:77803b3ee157 158 /* Please Do Not Alter these */
JonFreeman 1:450090bdb6f4 159 const int MAIN_LOOP_REPEAT_TIME_US = 10000; // 10000 us, with TACHO_TAB_SIZE = 100 means tacho_ticks_per_time is tacho_ticks_per_second
JonFreeman 0:77803b3ee157 160 /* End of Please Do Not Alter these */
JonFreeman 0:77803b3ee157 161 /* Global variable declarations */
JonFreeman 3:43cb067ecd00 162 uint32_t sys_timer100Hz = 0; // gets incremented by our Ticker ISR every MAIN_LOOP_REPEAT_TIME_US
JonFreeman 3:43cb067ecd00 163 uint32_t seconds = 0;
JonFreeman 3:43cb067ecd00 164 double link_volt_reading = 0.0; // Global updated by interrupt driven read of Battery Volts at rate of 100 Hz
JonFreeman 3:43cb067ecd00 165 double field_volt_reading = 0.0; // Global updated by interrupt driven read of Battery Volts at rate of 100 Hz
JonFreeman 3:43cb067ecd00 166 double amp_reading = 0.0;
JonFreeman 0:77803b3ee157 167 bool loop_flag = false; // made true in ISR_loop_timer, picked up and made false again in main programme loop
JonFreeman 1:450090bdb6f4 168 bool flag_25Hz = false; // As loop_flag but repeats 25 times per sec
JonFreeman 1:450090bdb6f4 169 bool flag_12Hz5 = false; // As loop_flag but repeats 12.5 times per sec
JonFreeman 1:450090bdb6f4 170 bool flag_1Hz = false; // As loop_flag but repeats 1 times per sec
JonFreeman 1:450090bdb6f4 171 bool query_toggle = false;
JonFreeman 0:77803b3ee157 172
JonFreeman 3:43cb067ecd00 173 bool flag_link_V_rd = false;
JonFreeman 3:43cb067ecd00 174 bool flag_field_V_rd = false;
JonFreeman 3:43cb067ecd00 175 bool flag_A_rd = false;
JonFreeman 2:8e7b51353f32 176 bool flag_Pot_rd = false;
JonFreeman 0:77803b3ee157 177
JonFreeman 3:43cb067ecd00 178 bool auto_test_flag = false;
JonFreeman 3:43cb067ecd00 179
JonFreeman 5:6ca3e7ffc553 180 bool charge_pump_enable = true;
JonFreeman 5:6ca3e7ffc553 181
JonFreeman 3:43cb067ecd00 182 enum {SAFE_NOTHING, POT_SERVO_DIRECT, VARIABLE_VOLTAGE, FIXED_VOLTAGE, ENG_REVS_CTRL, POT_SETS_ENGINE_RPM, CURRENT_FEEDBACK_CTRL, AUTO_TEST} ;
JonFreeman 0:77803b3ee157 183 /* End of Global variable declarations */
JonFreeman 0:77803b3ee157 184
JonFreeman 1:450090bdb6f4 185 //void ISR_fast_interrupt () { // here at 10 times main loop repeat rate (i.e. 1000Hz, 1.0ms)
JonFreeman 1:450090bdb6f4 186 void ISR_fast_interrupt () {
JonFreeman 3:43cb067ecd00 187 static uint32_t t = 0, u25 = 0;
JonFreeman 1:450090bdb6f4 188 Scope_probe = 1; // To show how much time spent in interrupt handler
JonFreeman 5:6ca3e7ffc553 189 if (charge_pump_enable)
JonFreeman 5:6ca3e7ffc553 190 CHARGE_PUMP = !CHARGE_PUMP;
JonFreeman 0:77803b3ee157 191 switch (t) {
JonFreeman 4:28cc0cf01570 192 case 0: // Alternator output voltage
JonFreeman 3:43cb067ecd00 193 flag_link_V_rd = true;
JonFreeman 0:77803b3ee157 194 break;
JonFreeman 4:28cc0cf01570 195 case 1: // Ammeter
JonFreeman 3:43cb067ecd00 196 flag_A_rd = true;
JonFreeman 3:43cb067ecd00 197 break;
JonFreeman 4:28cc0cf01570 198 case 2: // Driver's Pot
JonFreeman 2:8e7b51353f32 199 flag_Pot_rd = true;
JonFreeman 0:77803b3ee157 200 break;
JonFreeman 4:28cc0cf01570 201 case 3: // Field supply voltage
JonFreeman 3:43cb067ecd00 202 flag_field_V_rd = true;
JonFreeman 3:43cb067ecd00 203 break;
JonFreeman 3:43cb067ecd00 204 // case 4:
JonFreeman 2:8e7b51353f32 205 // driver_reading >>= 1; // Result = Result / 2
JonFreeman 2:8e7b51353f32 206 // driver_reading += Driver_Pot.read_u16();
JonFreeman 1:450090bdb6f4 207 // break;
JonFreeman 3:43cb067ecd00 208 case 5:
JonFreeman 0:77803b3ee157 209 loop_flag = true; // set flag to allow main programme loop to proceed
JonFreeman 1:450090bdb6f4 210 sys_timer100Hz++; // Just a handy measure of elapsed time for anything to use
JonFreeman 3:43cb067ecd00 211 if ((sys_timer100Hz & 0x03) == 0) { // is now 12.5Hz, not 8
JonFreeman 1:450090bdb6f4 212 flag_25Hz = true; // flag gets set 25 times per sec. Other code may clear flag and make use of this
JonFreeman 3:43cb067ecd00 213 u25++;
JonFreeman 3:43cb067ecd00 214 if (u25 == 25) {
JonFreeman 3:43cb067ecd00 215 u25 = 0;
JonFreeman 3:43cb067ecd00 216 flag_1Hz = true;
JonFreeman 3:43cb067ecd00 217 seconds++;
JonFreeman 3:43cb067ecd00 218 }
JonFreeman 3:43cb067ecd00 219 }
JonFreeman 1:450090bdb6f4 220 default:
JonFreeman 0:77803b3ee157 221 break;
JonFreeman 0:77803b3ee157 222 }
JonFreeman 0:77803b3ee157 223 t++;
JonFreeman 0:77803b3ee157 224 if (t > 9)
JonFreeman 0:77803b3ee157 225 t = 0;
JonFreeman 1:450090bdb6f4 226 Scope_probe = 0; // To show how much time spent in interrupt handler
JonFreeman 0:77803b3ee157 227 }
JonFreeman 0:77803b3ee157 228
JonFreeman 0:77803b3ee157 229 // **** End of Interrupt Service Routines ****
JonFreeman 0:77803b3ee157 230
JonFreeman 1:450090bdb6f4 231 /*double Read_Ext_Rev_Req ()
JonFreeman 1:450090bdb6f4 232 {
JonFreeman 1:450090bdb6f4 233 double rv = (double) ext_rev_req;
JonFreeman 1:450090bdb6f4 234 return rv / 4096.0;
JonFreeman 1:450090bdb6f4 235 }*/
JonFreeman 3:43cb067ecd00 236 /*
JonFreeman 1:450090bdb6f4 237 double Read_Driver_Pot ()
JonFreeman 1:450090bdb6f4 238 {
JonFreeman 1:450090bdb6f4 239 double rv = (double) driver_reading;
JonFreeman 1:450090bdb6f4 240 return rv / 4096.0;
JonFreeman 3:43cb067ecd00 241 }*/
JonFreeman 0:77803b3ee157 242
JonFreeman 3:43cb067ecd00 243 double Read_Link_Volts ()
JonFreeman 3:43cb067ecd00 244 {
JonFreeman 3:43cb067ecd00 245 return link_volt_reading * 39.9; // divisor fiddled to make voltage reading correct !
JonFreeman 0:77803b3ee157 246 }
JonFreeman 0:77803b3ee157 247
JonFreeman 3:43cb067ecd00 248 double Read_Field_Volts ()
JonFreeman 3:43cb067ecd00 249 {
JonFreeman 5:6ca3e7ffc553 250 // return field_volt_reading * 42.85; // divisor fiddled to make voltage reading correct !
JonFreeman 5:6ca3e7ffc553 251 return field_volt_reading * 40.12; // divisor fiddled to make voltage reading correct !
JonFreeman 0:77803b3ee157 252 }
JonFreeman 0:77803b3ee157 253
JonFreeman 3:43cb067ecd00 254 double Read_Ammeter ()
JonFreeman 3:43cb067ecd00 255 {
JonFreeman 3:43cb067ecd00 256 return amp_reading * 93.28; // Amp range corrected here
JonFreeman 1:450090bdb6f4 257 }
JonFreeman 1:450090bdb6f4 258
JonFreeman 1:450090bdb6f4 259
JonFreeman 5:6ca3e7ffc553 260 void query_system (parameters & a) {
JonFreeman 1:450090bdb6f4 261 query_toggle = !query_toggle;
JonFreeman 3:43cb067ecd00 262 }
JonFreeman 3:43cb067ecd00 263
JonFreeman 5:6ca3e7ffc553 264 void set_v_out_opamp (double a) { // 0 to 1.0 sets opamp output in range 0 to 5v, charge pump permitting
JonFreeman 5:6ca3e7ffc553 265 A_OUT = a;
JonFreeman 5:6ca3e7ffc553 266 }
JonFreeman 5:6ca3e7ffc553 267 void set_v_out_opamp (parameters & a) { // 0 to 1.0 sets opamp output in range 0 to 5v, charge pump permitting
JonFreeman 5:6ca3e7ffc553 268 A_OUT = a.dbl[0] / 100.0;
JonFreeman 5:6ca3e7ffc553 269 }
JonFreeman 5:6ca3e7ffc553 270
JonFreeman 5:6ca3e7ffc553 271 void charge_pump_override (int a) { // 0 disables, !0 enables charge pump
JonFreeman 5:6ca3e7ffc553 272 if (a == 0)
JonFreeman 5:6ca3e7ffc553 273 charge_pump_enable = false;
JonFreeman 5:6ca3e7ffc553 274 else
JonFreeman 5:6ca3e7ffc553 275 charge_pump_enable = true;
JonFreeman 5:6ca3e7ffc553 276 }
JonFreeman 5:6ca3e7ffc553 277 void charge_pump_override (parameters & a) { // 0 disables, !0 enables charge pump
JonFreeman 5:6ca3e7ffc553 278 charge_pump_override ((int)a.dbl[0]);
JonFreeman 5:6ca3e7ffc553 279 }
JonFreeman 5:6ca3e7ffc553 280
JonFreeman 3:43cb067ecd00 281 void set_pwm (double d) { // Range 0.0 to 1.0 called from cli
JonFreeman 3:43cb067ecd00 282 Field.set_pwm (d);
JonFreeman 2:8e7b51353f32 283 }
JonFreeman 2:8e7b51353f32 284
JonFreeman 3:43cb067ecd00 285 double get_temperature () {
JonFreeman 3:43cb067ecd00 286 return (double) temp_sensor;
JonFreeman 3:43cb067ecd00 287 }
JonFreeman 3:43cb067ecd00 288
JonFreeman 3:43cb067ecd00 289 void maketable () {
JonFreeman 3:43cb067ecd00 290 Field.maketable ();
JonFreeman 2:8e7b51353f32 291 }
JonFreeman 2:8e7b51353f32 292
JonFreeman 3:43cb067ecd00 293 int32_t set_engine_RPM_lit (uint32_t RPMrequest) { // Returns actual speed
JonFreeman 3:43cb067ecd00 294 return Engine.set_RPM_literal (RPMrequest);
JonFreeman 3:43cb067ecd00 295 }
JonFreeman 2:8e7b51353f32 296
JonFreeman 3:43cb067ecd00 297 int32_t set_engine_RPM_pct (uint32_t RPMrequest) { // Returns actual speed
JonFreeman 3:43cb067ecd00 298 return Engine.set_RPM_percent (RPMrequest);
JonFreeman 3:43cb067ecd00 299 }
JonFreeman 2:8e7b51353f32 300
JonFreeman 3:43cb067ecd00 301 void auto_test_initiate (int bulb_count) {
JonFreeman 3:43cb067ecd00 302 if (Engine.running()) {
JonFreeman 3:43cb067ecd00 303 auto_test_flag = true;
JonFreeman 3:43cb067ecd00 304 pc.printf ("Requesting Auto-Test for load of %d lamps\r\n", bulb_count);
JonFreeman 3:43cb067ecd00 305 }
JonFreeman 3:43cb067ecd00 306 else {
JonFreeman 3:43cb067ecd00 307 pc.printf ("Engine not running. Can't perform auto test\r\n");
JonFreeman 3:43cb067ecd00 308 auto_test_flag = false;
JonFreeman 2:8e7b51353f32 309 }
JonFreeman 1:450090bdb6f4 310 }
JonFreeman 1:450090bdb6f4 311
JonFreeman 3:43cb067ecd00 312 void is_eng_running () {
JonFreeman 3:43cb067ecd00 313 pc.printf ("Engine%sRunning\r\n", Engine.running() ? " IS " : " NOT ");
JonFreeman 3:43cb067ecd00 314 }
JonFreeman 3:43cb067ecd00 315
JonFreeman 0:77803b3ee157 316 extern void command_line_interpreter () ; // Comms with optional pc or device using serial port through board USB socket
JonFreeman 3:43cb067ecd00 317
JonFreeman 3:43cb067ecd00 318 enum {AUTO_TEST_INACTIVE, AUTO_TEST_BEGIN, AUTO_TEST_ABORT, AUTO_TEST_IN_PROGRESS } ;
JonFreeman 0:77803b3ee157 319
JonFreeman 0:77803b3ee157 320 // Programme Entry Point
JonFreeman 0:77803b3ee157 321 int main()
JonFreeman 0:77803b3ee157 322 {
JonFreeman 4:28cc0cf01570 323 const double PI = (2.0 * acos(0.0));
JonFreeman 2:8e7b51353f32 324 const double filt = 0.2;
JonFreeman 3:43cb067ecd00 325 const double ampfilt = 0.2;
JonFreeman 3:43cb067ecd00 326 const double vfilt = 0.2;
JonFreeman 0:77803b3ee157 327 // local variable declarations
JonFreeman 3:43cb067ecd00 328 double driver_pot = 0.0, dtmp;
JonFreeman 4:28cc0cf01570 329 // double theta = 0.0;
JonFreeman 3:43cb067ecd00 330 int32_t temp, startup_delay, print_position = 0;
JonFreeman 3:43cb067ecd00 331 int32_t field_pct = 0, auto_test_timer = 0, auto_test_state = AUTO_TEST_INACTIVE, auto_test_step = 0;
JonFreeman 3:43cb067ecd00 332 bool up_and_running = false;
JonFreeman 3:43cb067ecd00 333 char text[64];
JonFreeman 4:28cc0cf01570 334
JonFreeman 4:28cc0cf01570 335 A_OUT = 0.0;
JonFreeman 4:28cc0cf01570 336 REF_VAR = 0.0;
JonFreeman 0:77803b3ee157 337 microsecs.reset() ; // timer = 0
JonFreeman 0:77803b3ee157 338 microsecs.start () ; // 64 bit, counts micro seconds and times out in half million years
JonFreeman 1:450090bdb6f4 339
JonFreeman 3:43cb067ecd00 340 #ifdef GPS_
JonFreeman 3:43cb067ecd00 341 gps_mod gps;
JonFreeman 1:450090bdb6f4 342 #endif
JonFreeman 3:43cb067ecd00 343 //- Clear the screen, move to (0,0):
JonFreeman 3:43cb067ecd00 344 // \033[2J
JonFreeman 3:43cb067ecd00 345 pc.printf ("\033[2JAlternator Regulator 2020, Jon Freeman\r\n");
JonFreeman 3:43cb067ecd00 346 user_settings.load () ; // Fetch values from eeprom
JonFreeman 0:77803b3ee157 347 // Setup Complete ! Can now start main control forever loop.
JonFreeman 1:450090bdb6f4 348 loop_timer.attach_us (&ISR_fast_interrupt, MAIN_LOOP_REPEAT_TIME_US / 10); // Start periodic interrupt generator 1000us at Feb 2020
JonFreeman 0:77803b3ee157 349
JonFreeman 3:43cb067ecd00 350 Field.maketable () ; // Here to ensure eeprom has been setup
JonFreeman 3:43cb067ecd00 351 Field.set_for_speed (0);
JonFreeman 5:6ca3e7ffc553 352 Engine.Set_Speed_Lever (((double)user_settings.rd(WARMUP_SERVO_POS)) / 100.0);
JonFreeman 3:43cb067ecd00 353 startup_delay = user_settings.rd(WARM_UP_DELAY);
JonFreeman 3:43cb067ecd00 354 pc.printf ("Operating Mode is [%s]\r\n", get_mode_text (user_settings.rd(OP_MODE)));
JonFreeman 3:43cb067ecd00 355
JonFreeman 2:8e7b51353f32 356
JonFreeman 0:77803b3ee157 357 //***** START OF MAIN LOOP
JonFreeman 0:77803b3ee157 358 while (1) { // Loop forever, repeats synchroised by waiting for ticker Interrupt Service Routine to set 'loop_flag' true
JonFreeman 0:77803b3ee157 359 while (!loop_flag) { // Most of the time is spent in this loop, repeatedly re-checking for commands from pc port
JonFreeman 3:43cb067ecd00 360 #ifdef GPS_
JonFreeman 4:28cc0cf01570 361 // while (gps_module.readable())
JonFreeman 4:28cc0cf01570 362 // pc.putc (gps_module.getc());
JonFreeman 3:43cb067ecd00 363 #endif
JonFreeman 0:77803b3ee157 364 command_line_interpreter () ; // Proceed beyond here once loop_timer ticker ISR has set loop_flag true
JonFreeman 3:43cb067ecd00 365 // A to D converters all read at 100 Hz
JonFreeman 5:6ca3e7ffc553 366 if (flag_link_V_rd) { // Reads main alternator output and/or traction battery voltage
JonFreeman 3:43cb067ecd00 367 flag_link_V_rd = false;
JonFreeman 3:43cb067ecd00 368 link_volt_reading *= (1.0 - vfilt); //
JonFreeman 3:43cb067ecd00 369 link_volt_reading += vfilt * (double) Ain_Link_Volts.read(); // Volt fiddle factor NOT corrected here
JonFreeman 2:8e7b51353f32 370 }
JonFreeman 5:6ca3e7ffc553 371 if (flag_Pot_rd) { // Reads Driver's speed control potentiometer
JonFreeman 2:8e7b51353f32 372 flag_Pot_rd = false;
JonFreeman 3:43cb067ecd00 373 driver_pot *= (1.0 - filt);
JonFreeman 3:43cb067ecd00 374 driver_pot += filt * ((double)Driver_Pot.read() * 1.5); // Includes bodge around zener over-clipping input
JonFreeman 3:43cb067ecd00 375 }
JonFreeman 5:6ca3e7ffc553 376 if (flag_A_rd) { // Reads ammeter - user wires this to suit their purpose
JonFreeman 3:43cb067ecd00 377 flag_A_rd = false;
JonFreeman 3:43cb067ecd00 378 amp_reading *= (1.0 - ampfilt);
JonFreeman 5:6ca3e7ffc553 379 amp_reading += ampfilt * ((double) Ammeter_In.read() - 0.495); // Amp range NOT corrected here BUT OFFSET IS
JonFreeman 3:43cb067ecd00 380 }
JonFreeman 5:6ca3e7ffc553 381 if (flag_field_V_rd) { // Reads 'Field Positive' supply - from battery via diode, also alternator rectifier out
JonFreeman 3:43cb067ecd00 382 flag_field_V_rd = false;
JonFreeman 3:43cb067ecd00 383 field_volt_reading *= (1.0 - vfilt); //
JonFreeman 3:43cb067ecd00 384 field_volt_reading += vfilt * (double) Field_Supply_V.read(); // Volt fiddle factor NOT corrected here
JonFreeman 2:8e7b51353f32 385 }
JonFreeman 1:450090bdb6f4 386 } // Jun 2019 pass here 100 times per sec
JonFreeman 1:450090bdb6f4 387 // BEGIN 100Hz stuff
JonFreeman 3:43cb067ecd00 388 loop_flag = false; // Clear flag set by ticker interrupt handler
JonFreeman 3:43cb067ecd00 389 Engine.manager_core (); // This belongs right here, update regularly, keeps 'filtered()' fresh and keeps engine to set rpm
JonFreeman 3:43cb067ecd00 390 #ifdef GPS_
JonFreeman 3:43cb067ecd00 391 gps.update ();
JonFreeman 3:43cb067ecd00 392 #endif
JonFreeman 4:28cc0cf01570 393 /* theta += 0.05;
JonFreeman 4:28cc0cf01570 394 if (theta > PI)
JonFreeman 4:28cc0cf01570 395 theta -= 2.0 * PI;
JonFreeman 4:28cc0cf01570 396 sinout = 0.5 + sin(theta) / 2.0;
JonFreeman 4:28cc0cf01570 397 cosout = 0.5 + cos(theta) / 2.0;
JonFreeman 4:28cc0cf01570 398 */
JonFreeman 1:450090bdb6f4 399 // END 100Hz stuff
JonFreeman 1:450090bdb6f4 400 if (flag_25Hz) {
JonFreeman 1:450090bdb6f4 401 flag_25Hz = false;
JonFreeman 1:450090bdb6f4 402 // BEGIN 25Hz stuff
JonFreeman 0:77803b3ee157 403
JonFreeman 1:450090bdb6f4 404 // END 25Hz stuff
JonFreeman 1:450090bdb6f4 405 // BEGIN 12.5Hz stuff
JonFreeman 1:450090bdb6f4 406 flag_12Hz5 = !flag_12Hz5;
JonFreeman 1:450090bdb6f4 407 if (flag_12Hz5) { // Do any even stuff to be done 12.5 times per second
JonFreeman 3:43cb067ecd00 408 // if (up_and_running && Engine.running()) {
JonFreeman 3:43cb067ecd00 409 if (up_and_running) {
JonFreeman 3:43cb067ecd00 410 switch (user_settings.rd(OP_MODE)) {
JonFreeman 3:43cb067ecd00 411 /*
JonFreeman 3:43cb067ecd00 412 enum {SAFE_NOTHING, //
JonFreeman 3:43cb067ecd00 413 POT_SERVO_DIRECT, //
JonFreeman 3:43cb067ecd00 414 VARIABLE_VOLTAGE, // Batteryless, controllerless Low Cost Loco - alternator connects direct to DC motors
JonFreeman 3:43cb067ecd00 415 FIXED_VOLTAGE, //
JonFreeman 3:43cb067ecd00 416 ENG_REVS_CTRL, //
JonFreeman 3:43cb067ecd00 417 POT_SETS_ENGINE_RPM, //
JonFreeman 3:43cb067ecd00 418 CURRENT_FEEDBACK_CTRL, //
JonFreeman 3:43cb067ecd00 419 AUTO_TEST }; //
JonFreeman 3:43cb067ecd00 420 "0\tSafe nothing mode for cli cmd testing",
JonFreeman 3:43cb067ecd00 421 "1\tPot to Servo direct, field OFF",
JonFreeman 3:43cb067ecd00 422 "2\tVariable voltage",
JonFreeman 3:43cb067ecd00 423 "3\tFixed voltage",
JonFreeman 3:43cb067ecd00 424 "4\tEngine Revs Control",
JonFreeman 3:43cb067ecd00 425 "5\tSet Engine to Driver's Pot",
JonFreeman 3:43cb067ecd00 426 "6\tControl Engine by Current Load",
JonFreeman 3:43cb067ecd00 427 */
JonFreeman 3:43cb067ecd00 428 case SAFE_NOTHING: // Safe nothing mode for cli cmd testing
JonFreeman 5:6ca3e7ffc553 429 // Use this to test command line commands e.g. Set_Speed_Lever, direct field setting etc
JonFreeman 3:43cb067ecd00 430 break;
JonFreeman 3:43cb067ecd00 431
JonFreeman 3:43cb067ecd00 432 case POT_SERVO_DIRECT: // Driver_pot --> servo direct. Field OFF
JonFreeman 5:6ca3e7ffc553 433 // Engine.Set_Speed_Lever (driver_pot);
JonFreeman 5:6ca3e7ffc553 434 Engine.Set_Speed_Lever (driver_pot);
JonFreeman 5:6ca3e7ffc553 435 REF_VAR = driver_pot;
JonFreeman 5:6ca3e7ffc553 436 // Field.set_for_speed (0); // Safe, no output
JonFreeman 5:6ca3e7ffc553 437 Field.set_for_speed (3000); // Safe, no output
JonFreeman 3:43cb067ecd00 438 break;
JonFreeman 3:43cb067ecd00 439
JonFreeman 3:43cb067ecd00 440 case VARIABLE_VOLTAGE: // Variable Voltage
JonFreeman 5:6ca3e7ffc553 441 Engine.Set_Speed_Lever (driver_pot); // Driver_pot --> servo direct. Field ON
JonFreeman 3:43cb067ecd00 442 if (driver_pot > DRIVER_NEUTRAL) // if pot not close to zero
JonFreeman 3:43cb067ecd00 443 Field.set_for_speed (Engine.RPM_latest()); // according to RPM
JonFreeman 3:43cb067ecd00 444 else
JonFreeman 3:43cb067ecd00 445 Field.set_for_speed (0); // Field OFF
JonFreeman 3:43cb067ecd00 446 break;
JonFreeman 3:43cb067ecd00 447
JonFreeman 3:43cb067ecd00 448 case FIXED_VOLTAGE: // Fixed Voltage
JonFreeman 3:43cb067ecd00 449 Field.set_for_speed (Engine.RPM_latest()); // according to RPM
JonFreeman 3:43cb067ecd00 450 break;
JonFreeman 3:43cb067ecd00 451
JonFreeman 3:43cb067ecd00 452 case ENG_REVS_CTRL: // Engine revs control - Pot to control revs over range tickover to MAX_RPM_LIMIT
JonFreeman 3:43cb067ecd00 453 Field.set_for_speed (Engine.RPM_latest());
JonFreeman 3:43cb067ecd00 454 break;
JonFreeman 3:43cb067ecd00 455
JonFreeman 3:43cb067ecd00 456 case POT_SETS_ENGINE_RPM: // Set engine to driver pot
JonFreeman 3:43cb067ecd00 457 dtmp = driver_pot * (MAX_RPM_LIMIT - TICKOVER_RPM) + TICKOVER_RPM;
JonFreeman 3:43cb067ecd00 458 temp = (int32_t) dtmp;
JonFreeman 3:43cb067ecd00 459 Engine.set_RPM_literal (temp); // this sets engine speed controller
JonFreeman 3:43cb067ecd00 460 Field.set_for_speed (Engine.RPM_latest()); // according to RPM
JonFreeman 3:43cb067ecd00 461 break;
JonFreeman 3:43cb067ecd00 462
JonFreeman 3:43cb067ecd00 463 // case CURRENT_MODE: // Set engine speed determined by current drawn
JonFreeman 3:43cb067ecd00 464 case CURRENT_FEEDBACK_CTRL: // Set engine speed determined by current drawn
JonFreeman 3:43cb067ecd00 465 temp = 0; // an integer. Engine set to tickover when no power demand
JonFreeman 3:43cb067ecd00 466 if (driver_pot > DRIVER_NEUTRAL) // if pot not close to zero
JonFreeman 3:43cb067ecd00 467 temp = 1 + (int32_t)abs(Read_Ammeter() * 8.0); // Sets max amps to 100 / 8.0
JonFreeman 3:43cb067ecd00 468 Engine.set_RPM_percent (temp); // this sets engine speed controller
JonFreeman 3:43cb067ecd00 469 Field.set_for_speed (Engine.RPM_latest()); // according to RPM
JonFreeman 3:43cb067ecd00 470 break;
JonFreeman 3:43cb067ecd00 471
JonFreeman 3:43cb067ecd00 472 case AUTO_TEST: // cli command may initiate test sequence implemented here. Wait for flag to proceed.
JonFreeman 3:43cb067ecd00 473 switch (auto_test_state) {
JonFreeman 3:43cb067ecd00 474 case AUTO_TEST_INACTIVE:
JonFreeman 3:43cb067ecd00 475 if (auto_test_flag) // cli has requested auto test sequence
JonFreeman 3:43cb067ecd00 476 auto_test_state = AUTO_TEST_BEGIN;
JonFreeman 3:43cb067ecd00 477 break;
JonFreeman 3:43cb067ecd00 478
JonFreeman 3:43cb067ecd00 479 case AUTO_TEST_BEGIN: // set engine, field etc, then initiate settling time delay
JonFreeman 3:43cb067ecd00 480 Engine.set_RPM_percent (1); // this sets engine speed controller for min useful revs
JonFreeman 3:43cb067ecd00 481 Field.set_for_speed (0);
JonFreeman 3:43cb067ecd00 482 pc.printf ("Starting auto test sequence, user field limit values :\r\n");
JonFreeman 3:43cb067ecd00 483 for (int i = 0; i < 21; i++)
JonFreeman 3:43cb067ecd00 484 pc.printf ("%d, ", user_settings.rd(i));
JonFreeman 3:43cb067ecd00 485 pc.printf ("\r\n");
JonFreeman 3:43cb067ecd00 486 auto_test_step = 0;
JonFreeman 3:43cb067ecd00 487 auto_test_timer = 0;
JonFreeman 3:43cb067ecd00 488 auto_test_state = AUTO_TEST_IN_PROGRESS;
JonFreeman 3:43cb067ecd00 489 break;
JonFreeman 3:43cb067ecd00 490
JonFreeman 3:43cb067ecd00 491 case AUTO_TEST_IN_PROGRESS: // take sets of readings, then timeout back to INACTIVE
JonFreeman 3:43cb067ecd00 492 field_pct = Field.set_for_speed (Engine.RPM_latest()); // according to RPM
JonFreeman 3:43cb067ecd00 493 switch (auto_test_timer++) { // When active, get here @ 12.5Hz
JonFreeman 3:43cb067ecd00 494 case 30: case 40: case 50: case 60: // take readings at these times
JonFreeman 3:43cb067ecd00 495 case 35: case 45: case 55: case 65:
JonFreeman 3:43cb067ecd00 496 // pc.printf ("\tTaking auto_test readings %d, Volts, Amps, RPM req, RPM got, servo position, measured duty ratio\r\n", auto_test_timer);
JonFreeman 3:43cb067ecd00 497 /*
JonFreeman 3:43cb067ecd00 498 Need to collect here,
JonFreeman 3:43cb067ecd00 499 Volts, Amps, RPM got latest, RPM got filtered, servo position, measured duty ratio, lut pcent
JonFreeman 3:43cb067ecd00 500 */
JonFreeman 3:43cb067ecd00 501 pc.printf ("\t%.2f, %.2f, %.2f, %d, %d, %.2f, %.3f, %d\r\n", Read_Link_Volts(), Read_Field_Volts(),
JonFreeman 3:43cb067ecd00 502 Read_Ammeter(), Engine.RPM_latest(), Engine.RPM_filtered(),
JonFreeman 3:43cb067ecd00 503 Engine.get_servo_position(), Field.get_duty_ratio(), field_pct);
JonFreeman 3:43cb067ecd00 504 break;
JonFreeman 3:43cb067ecd00 505 case 66: // After final set of readings
JonFreeman 3:43cb067ecd00 506 auto_test_step++;
JonFreeman 3:43cb067ecd00 507 if (auto_test_step > 10)
JonFreeman 3:43cb067ecd00 508 auto_test_state = AUTO_TEST_ABORT;
JonFreeman 3:43cb067ecd00 509 else { // set conditions for next set of readings
JonFreeman 3:43cb067ecd00 510 temp = Engine.RPM_percent_to_actual(auto_test_step * 10);
JonFreeman 3:43cb067ecd00 511 Engine.set_RPM_percent (auto_test_step * 10);
JonFreeman 3:43cb067ecd00 512 auto_test_timer = 0;
JonFreeman 3:43cb067ecd00 513 pc.printf ("Setting rig for %d percent, %d RPM\r\n", auto_test_step * 10, temp);
JonFreeman 3:43cb067ecd00 514 }
JonFreeman 3:43cb067ecd00 515 break;
JonFreeman 3:43cb067ecd00 516 default:
JonFreeman 3:43cb067ecd00 517 break;
JonFreeman 3:43cb067ecd00 518 }
JonFreeman 3:43cb067ecd00 519 break;
JonFreeman 3:43cb067ecd00 520
JonFreeman 3:43cb067ecd00 521 case AUTO_TEST_ABORT: // Here at test end or because auto_test_flag made false somewhere somehow
JonFreeman 3:43cb067ecd00 522 Engine.set_RPM_percent (0); // this sets engine speed controller
JonFreeman 3:43cb067ecd00 523 Field.set_for_speed (0);
JonFreeman 3:43cb067ecd00 524 auto_test_state = AUTO_TEST_INACTIVE;
JonFreeman 3:43cb067ecd00 525 auto_test_flag = false;
JonFreeman 3:43cb067ecd00 526 pc.printf ("Ending auto test sequence\r\n");
JonFreeman 3:43cb067ecd00 527 break;
JonFreeman 3:43cb067ecd00 528 default:
JonFreeman 3:43cb067ecd00 529 break;
JonFreeman 3:43cb067ecd00 530 } // END OF SWITCH auto_test_state
JonFreeman 3:43cb067ecd00 531 break;
JonFreeman 3:43cb067ecd00 532 default:
JonFreeman 3:43cb067ecd00 533 user_settings.wr (0, OP_MODE); // set to safe non-mode 0
JonFreeman 3:43cb067ecd00 534 break;
JonFreeman 1:450090bdb6f4 535 }
JonFreeman 1:450090bdb6f4 536 }
JonFreeman 3:43cb067ecd00 537 else { // Engine not running
JonFreeman 3:43cb067ecd00 538 Field.set_for_speed (0); // according to RPM
JonFreeman 3:43cb067ecd00 539 }
JonFreeman 1:450090bdb6f4 540 }
JonFreeman 1:450090bdb6f4 541 else { // Do odd 12.5 times per sec stuff
JonFreeman 1:450090bdb6f4 542 flag_12Hz5 = false;
JonFreeman 1:450090bdb6f4 543 myled = !myled;
JonFreeman 1:450090bdb6f4 544 } // End of if(flag_12Hz5)
JonFreeman 1:450090bdb6f4 545 // END 12.5Hz stuff
JonFreeman 3:43cb067ecd00 546 if (flag_1Hz) {
JonFreeman 1:450090bdb6f4 547 // BEGIN 1Hz stuff
JonFreeman 3:43cb067ecd00 548 flag_1Hz = false;
JonFreeman 3:43cb067ecd00 549 if (!up_and_running) {
JonFreeman 3:43cb067ecd00 550 if (startup_delay == 0) {
JonFreeman 3:43cb067ecd00 551 up_and_running = true;
JonFreeman 3:43cb067ecd00 552 pc.printf ("Warmup ended, starting proper ops\r\n");
JonFreeman 5:6ca3e7ffc553 553 Engine.Set_Speed_Lever (0.0);
JonFreeman 3:43cb067ecd00 554 }
JonFreeman 3:43cb067ecd00 555 else {
JonFreeman 3:43cb067ecd00 556 pc.printf ("In Startup warmup delay %d\r", startup_delay--);
JonFreeman 3:43cb067ecd00 557 }
JonFreeman 3:43cb067ecd00 558 }
JonFreeman 1:450090bdb6f4 559 if (query_toggle) {
JonFreeman 3:43cb067ecd00 560 sprintf (text, "\033[%d;0HI=%.1fA, V=%.2fV, ", 20 + print_position, Read_Ammeter() , Read_Link_Volts());
JonFreeman 3:43cb067ecd00 561 pc.printf ("%sRPM %d, rpm_set %d, pot %.3f, servo %.3f \r\n", text, Engine.RPM_latest(), Engine.get_RPM_requested (), driver_pot, Engine.get_servo_position());
JonFreeman 3:43cb067ecd00 562 print_position++;
JonFreeman 3:43cb067ecd00 563 if (print_position > 10)
JonFreeman 3:43cb067ecd00 564 print_position = 0;
JonFreeman 1:450090bdb6f4 565 }
JonFreeman 3:43cb067ecd00 566 //printf("\033[6;3HHello\n");
JonFreeman 3:43cb067ecd00 567 // pc.printf ("\033[0;1HSecs %d \r\n", seconds);
JonFreeman 3:43cb067ecd00 568 // pc.printf ("Temp = %.1f\r", get_temperature());
JonFreeman 3:43cb067ecd00 569 // gps.update();
JonFreeman 3:43cb067ecd00 570 #ifdef GPS_
JonFreeman 3:43cb067ecd00 571 if (gps.new_data()) {
JonFreeman 3:43cb067ecd00 572 myled = !myled;
JonFreeman 3:43cb067ecd00 573 pc.printf("\033[0;1H%s, %s, %s \r\n", gps.time(), gps.latitude(), gps.longitude());
JonFreeman 3:43cb067ecd00 574 pc.printf("alt ^%s^, sats %s lat mer %f, lon mer %f \r\n", gps.altitude(), gps.sat_count(), gps.lat_merged(), gps.lon_merged());
JonFreeman 3:43cb067ecd00 575 pc.printf("%s, heading %s, mph %s \r\n", gps.date(), gps.heading(), gps.mph());
JonFreeman 3:43cb067ecd00 576 pc.printf("%s\r\n \n .\r\n ", gps.message(1));
JonFreeman 3:43cb067ecd00 577 }
JonFreeman 3:43cb067ecd00 578 #endif
JonFreeman 3:43cb067ecd00 579 // while (gps_module.readable())
JonFreeman 3:43cb067ecd00 580 // pc.putc (gps_module.getc());
JonFreeman 1:450090bdb6f4 581 // END 1Hz stuff
JonFreeman 0:77803b3ee157 582 } // eo once per second stuff
JonFreeman 1:450090bdb6f4 583 } // End of 100Hz stuff
JonFreeman 0:77803b3ee157 584 } // End of main programme loop
JonFreeman 0:77803b3ee157 585 } // End of main function - end of programme
JonFreeman 3:43cb067ecd00 586