2015-05-28 16:49:44 -07:00
/*
Speeduino - Simple engine management for the Arduino Mega 2560 platform
Copyright ( C ) Josh Stewart
A full copy of the license may be found in the projects root directory
*/
2014-05-11 20:44:23 -07:00
/*
Returns how much free dynamic memory exists ( between heap and stack )
*/
2015-02-14 09:04:00 -08:00
# include "utils.h"
2014-05-11 20:44:23 -07:00
int freeRam ( )
{
extern int __heap_start , * __brkval ;
int v ;
return ( int ) & v - ( __brkval = = 0 ? ( int ) & __heap_start : ( int ) __brkval ) ;
}
2015-03-15 04:54:47 -07:00
void setPinMapping ( byte boardID )
{
switch ( boardID )
{
case 0 :
//Pin mappings as per the v0.1 shield
pinInjector1 = 8 ; //Output pin injector 1 is on
pinInjector2 = 9 ; //Output pin injector 2 is on
pinInjector3 = 11 ; //Output pin injector 3 is on
pinInjector4 = 10 ; //Output pin injector 4 is on
pinCoil1 = 6 ; //Pin for coil 1
pinCoil2 = 7 ; //Pin for coil 2
pinCoil3 = 12 ; //Pin for coil 3
pinCoil4 = 13 ; //Pin for coil 4
pinTrigger = 2 ; //The CAS pin
pinTPS = A0 ; //TPS input pin
pinMAP = A1 ; //MAP sensor pin
pinIAT = A2 ; //IAT sensor pin
pinCLT = A3 ; //CLS sensor pin
pinO2 = A4 ; //O2 Sensor pin
break ;
case 1 :
//Pin mappings as per the v0.2 shield
pinInjector1 = 8 ; //Output pin injector 1 is on
pinInjector2 = 9 ; //Output pin injector 2 is on
pinInjector3 = 10 ; //Output pin injector 3 is on
pinInjector4 = 11 ; //Output pin injector 4 is on
pinCoil1 = 28 ; //Pin for coil 1
pinCoil2 = 24 ; //Pin for coil 2
pinCoil3 = 40 ; //Pin for coil 3
pinCoil4 = 36 ; //Pin for coil 4
pinTrigger = 20 ; //The CAS pin
pinTrigger2 = 21 ; //The Cam Sensor pin
pinTPS = A2 ; //TPS input pin
pinMAP = A3 ; //MAP sensor pin
pinIAT = A0 ; //IAT sensor pin
pinCLT = A1 ; //CLS sensor pin
pinO2 = A8 ; //O2 Sensor pin
2015-03-19 06:35:41 -07:00
pinBat = A4 ; //Battery reference voltage pin
2015-03-15 04:54:47 -07:00
pinDisplayReset = 48 ; // OLED reset pin
break ;
case 2 :
//Pin mappings as per the v0.3 shield
pinInjector1 = 8 ; //Output pin injector 1 is on
pinInjector2 = 9 ; //Output pin injector 2 is on
pinInjector3 = 10 ; //Output pin injector 3 is on
pinInjector4 = 11 ; //Output pin injector 4 is on
pinCoil1 = 28 ; //Pin for coil 1
pinCoil2 = 24 ; //Pin for coil 2
pinCoil3 = 40 ; //Pin for coil 3
pinCoil4 = 36 ; //Pin for coil 4
2015-08-11 23:12:14 -07:00
pinTrigger = 19 ; //The CAS pin
pinTrigger2 = 18 ; //The Cam Sensor pin
2015-03-15 04:54:47 -07:00
pinTPS = A2 ; //TPS input pin
pinMAP = A3 ; //MAP sensor pin
pinIAT = A0 ; //IAT sensor pin
pinCLT = A1 ; //CLS sensor pin
pinO2 = A8 ; //O2 Sensor pin
2015-03-19 06:35:41 -07:00
pinBat = A4 ; //Battery reference voltage pin
2015-03-15 04:54:47 -07:00
pinDisplayReset = 48 ; // OLED reset pin
2015-04-13 21:41:44 -07:00
pinTachOut = 49 ; //Tacho output pin
2015-05-16 04:06:23 -07:00
pinIdle1 = 5 ; //Single wire idle control
pinFuelPump = 4 ; //Fuel pump output
2015-03-15 04:54:47 -07:00
break ;
2015-04-13 21:41:44 -07:00
case 3 :
//Pin mappings as per the v0.4 shield
pinInjector1 = 8 ; //Output pin injector 1 is on
pinInjector2 = 9 ; //Output pin injector 2 is on
pinInjector3 = 10 ; //Output pin injector 3 is on
pinInjector4 = 11 ; //Output pin injector 4 is on
pinCoil1 = 28 ; //Pin for coil 1
pinCoil2 = 24 ; //Pin for coil 2
pinCoil3 = 40 ; //Pin for coil 3
pinCoil4 = 36 ; //Pin for coil 4
2015-08-11 21:15:39 -07:00
pinTrigger = 19 ; //The CAS pin
pinTrigger2 = 18 ; //The Cam Sensor pin
2015-04-13 21:41:44 -07:00
pinTPS = A2 ; //TPS input pin
pinMAP = A3 ; //MAP sensor pin
pinIAT = A0 ; //IAT sensor pin
pinCLT = A1 ; //CLS sensor pin
pinO2 = A8 ; //O2 Sensor pin
pinBat = A4 ; //Battery reference voltage pin
pinDisplayReset = 48 ; // OLED reset pin
pinTachOut = 49 ; //Tacho output pin
break ;
2015-03-15 04:54:47 -07:00
2015-03-19 06:35:41 -07:00
case 10 :
//Pin mappings for user turtanas PCB
pinInjector1 = 4 ; //Output pin injector 1 is on
pinInjector2 = 5 ; //Output pin injector 2 is on
pinInjector3 = 6 ; //Output pin injector 3 is on
pinInjector4 = 7 ; //Output pin injector 4 is on
pinInjector5 = 8 ; //Placeholder only - NOT USED
pinInjector6 = 9 ; //Placeholder only - NOT USED
pinInjector7 = 10 ; //Placeholder only - NOT USED
pinInjector8 = 11 ; //Placeholder only - NOT USED
pinCoil1 = 24 ; //Pin for coil 1
pinCoil2 = 28 ; //Pin for coil 2
pinCoil3 = 36 ; //Pin for coil 3
pinCoil4 = 40 ; //Pin for coil 4
pinTrigger = 18 ; //The CAS pin
pinTrigger2 = 19 ; //The Cam Sensor pin
pinTPS = A2 ; //TPS input pin
pinMAP = A3 ; //MAP sensor pin
pinMAP2 = A8 ; //MAP2 sensor pin
pinIAT = A0 ; //IAT sensor pin
pinCLT = A1 ; //CLS sensor pin
pinO2 = A4 ; //O2 Sensor pin
pinBat = A7 ; //Battery reference voltage pin
pinDisplayReset = 48 ; // OLED reset pin
pinSpareTemp1 = A6 ;
pinSpareTemp2 = A5 ;
2015-07-12 03:34:19 -07:00
pinTachOut = 41 ; //Tacho output pin transistori puuttuu 2n2222 tähän ja 1k 12v
pinFuelPump = 42 ; //Fuel pump output 2n2222
2015-03-19 06:35:41 -07:00
break ;
2015-03-23 19:11:34 -07:00
case 20 :
//Pin mappings as per the Plazomat In/Out shields Rev 0.1
pinInjector1 = 8 ; //Output pin injector 1 is on
pinInjector2 = 9 ; //Output pin injector 2 is on
pinInjector3 = 10 ; //Output pin injector 3 is on
pinInjector4 = 11 ; //Output pin injector 4 is on
pinCoil1 = 28 ; //Pin for coil 1
pinCoil2 = 24 ; //Pin for coil 2
pinCoil3 = 40 ; //Pin for coil 3
pinCoil4 = 36 ; //Pin for coil 4
pinSpareOut1 = 4 ; //Spare LSD Output 1(PWM)
pinSpareOut2 = 5 ; //Spare LSD Output 2(PWM)
pinSpareOut3 = 6 ; //Spare LSD Output 3(PWM)
pinSpareOut4 = 7 ; //Spare LSD Output 4(PWM)
pinSpareOut5 = 50 ; //Spare LSD Output 5(digital)
pinSpareOut6 = 52 ; //Spare LSD Output 6(digital)
pinTrigger = 20 ; //The CAS pin
pinTrigger2 = 21 ; //The Cam Sensor pin
pinSpareTemp2 = A15 ; //spare Analog input 2
pinSpareTemp1 = A14 ; //spare Analog input 1
pinO2 = A8 ; //O2 Sensor pin
pinBat = A4 ; //Battery reference voltage pin
pinMAP = A3 ; //MAP sensor pin
pinTPS = A2 ; //TPS input pin
pinCLT = A1 ; //CLS sensor pin
pinIAT = A0 ; //IAT sensor pin
2015-03-15 04:54:47 -07:00
default :
//Pin mappings as per the v0.2 shield
pinInjector1 = 8 ; //Output pin injector 1 is on
pinInjector2 = 9 ; //Output pin injector 2 is on
pinInjector3 = 10 ; //Output pin injector 3 is on
pinInjector4 = 11 ; //Output pin injector 4 is on
pinCoil1 = 28 ; //Pin for coil 1
pinCoil2 = 24 ; //Pin for coil 2
pinCoil3 = 40 ; //Pin for coil 3
pinCoil4 = 36 ; //Pin for coil 4
pinTrigger = 20 ; //The CAS pin
pinTrigger2 = 21 ; //The Cam Sensor pin
pinTPS = A2 ; //TPS input pin
pinMAP = A3 ; //MAP sensor pin
pinIAT = A0 ; //IAT sensor pin
pinCLT = A1 ; //CLS sensor pin
pinO2 = A8 ; //O2 Sensor pin
2015-03-19 06:35:41 -07:00
pinBat = A4 ; //Battery reference voltage pin
2015-03-15 04:54:47 -07:00
pinDisplayReset = 48 ; // OLED reset pin
break ;
}
2015-05-16 04:06:23 -07:00
//Finally, set the relevant pin modes for outputs
pinMode ( pinCoil1 , OUTPUT ) ;
pinMode ( pinCoil2 , OUTPUT ) ;
pinMode ( pinCoil3 , OUTPUT ) ;
pinMode ( pinCoil4 , OUTPUT ) ;
pinMode ( pinInjector1 , OUTPUT ) ;
pinMode ( pinInjector2 , OUTPUT ) ;
pinMode ( pinInjector3 , OUTPUT ) ;
pinMode ( pinInjector4 , OUTPUT ) ;
pinMode ( pinTachOut , OUTPUT ) ;
pinMode ( pinIdle1 , OUTPUT ) ;
pinMode ( pinIdle2 , OUTPUT ) ;
pinMode ( pinFuelPump , OUTPUT ) ;
//And for inputs
pinMode ( pinMAP , INPUT ) ;
pinMode ( pinO2 , INPUT ) ;
pinMode ( pinTPS , INPUT ) ;
pinMode ( pinIAT , INPUT ) ;
pinMode ( pinCLT , INPUT ) ;
//
digitalWrite ( pinMAP , HIGH ) ;
//digitalWrite(pinO2, LOW);
digitalWrite ( pinTPS , LOW ) ;
2015-03-15 04:54:47 -07:00
}
2013-02-04 03:43:38 -08:00
/*
2014-05-06 04:07:49 -07:00
This function retuns a pulsewidth time ( in us ) using a either Alpha - N or Speed Density algorithms , given the following :
2013-02-04 03:43:38 -08:00
REQ_FUEL
VE : Lookup from the main MAP vs RPM fuel table
MAP : In KPa , read from the sensor
GammaE : Sum of Enrichment factors ( Cold start , acceleration ) . This is a multiplication factor ( Eg to add 10 % , this should be 110 )
2013-12-22 04:44:25 -08:00
injDT : Injector dead time . The time the injector take to open minus the time it takes to close ( Both in uS )
TPS : Throttle position ( 0 % to 100 % )
This function is called by PW_SD and PW_AN for speed0density and pure Alpha - N calculations respectively .
2013-02-04 03:43:38 -08:00
*/
2014-09-21 12:52:32 -07:00
unsigned int PW ( int REQ_FUEL , byte VE , byte MAP , int corrections , int injOpen , byte TPS )
2013-02-04 03:43:38 -08:00
{
2013-07-03 03:56:33 -07:00
//Standard float version of the calculation
2014-09-20 15:46:25 -07:00
//return (REQ_FUEL * (float)(VE/100.0) * (float)(MAP/100.0) * (float)(TPS/100.0) * (float)(corrections/100.0) + injOpen);
2015-02-06 02:30:19 -08:00
//Note: The MAP and TPS portions are currently disabled, we use VE and corrections only
2013-07-03 03:56:33 -07:00
2015-01-02 14:09:19 -08:00
//100% float free version, does sacrifice a little bit of accuracy.
2013-07-09 17:26:16 -07:00
int iVE = ( ( int ) VE < < 7 ) / 100 ;
2015-02-06 18:50:23 -08:00
//int iVE = divs100( ((int)VE << 7));
2015-02-06 02:30:19 -08:00
//int iMAP = ((int)MAP << 7) / 100;
2014-01-29 17:17:50 -08:00
int iCorrections = ( corrections < < 7 ) / 100 ;
2015-02-06 02:30:19 -08:00
//int iTPS = ((int)TPS << 7) / 100;
2013-07-09 17:26:16 -07:00
unsigned long intermediate = ( ( long ) REQ_FUEL * ( long ) iVE ) > > 7 ; //Need to use an intermediate value to avoid overflowing the long
2015-02-06 02:30:19 -08:00
//intermediate = (intermediate * iMAP) >> 7;
2014-01-29 17:17:50 -08:00
intermediate = ( intermediate * iCorrections ) > > 7 ;
2015-02-06 02:30:19 -08:00
//intermediate = (intermediate * iTPS) >> 7;
2015-02-03 16:52:01 -08:00
intermediate + = injOpen ; //Add the injector opening time
if ( intermediate > 65535 ) { intermediate = 65535 ; } //Make sure this won't overflow when we convert to uInt. This means the maximum pulsewidth possible is 65.535mS
return ( unsigned int ) ( intermediate ) ;
2013-07-09 17:26:16 -07:00
2013-02-04 03:43:38 -08:00
}
2013-12-22 04:44:25 -08:00
2014-05-06 04:07:49 -07:00
//Convenience functions for Speed Density and Alpha-N
2014-09-21 12:52:32 -07:00
unsigned int PW_SD ( int REQ_FUEL , byte VE , byte MAP , int corrections , int injOpen )
2013-12-22 04:44:25 -08:00
{
2014-12-29 21:23:18 -08:00
//return PW(REQ_FUEL, VE, MAP, corrections, injOpen, 100); //Just use 1 in place of the TPS
return PW ( REQ_FUEL , VE , 100 , corrections , injOpen , 100 ) ; //Just use 1 in place of the TPS
2013-12-22 04:44:25 -08:00
}
2014-09-21 12:52:32 -07:00
unsigned int PW_AN ( int REQ_FUEL , byte VE , byte TPS , int corrections , int injOpen )
2013-12-22 04:44:25 -08:00
{
2014-10-09 22:39:21 -07:00
//Sanity check
if ( TPS > 100 ) { TPS = 100 ; }
2014-12-29 21:23:18 -08:00
//return PW(REQ_FUEL, VE, 100, corrections, injOpen, TPS); //Just use 1 in place of the MAP
return PW ( REQ_FUEL , VE , 100 , corrections , injOpen , 100 ) ; //Just use 1 in place of the MAP
2013-12-22 04:44:25 -08:00
}