Separate logic for secondary fuel and ignition tables

This commit is contained in:
Josh Stewart 2020-10-22 11:21:48 +11:00
parent e4ecd00618
commit 61cef9451c
7 changed files with 238 additions and 154 deletions

View File

@ -153,7 +153,7 @@
#define BIT_SPARK2_FLATSH 0 //Flat shift hard cut
#define BIT_SPARK2_FLATSS 1 //Flat shift soft cut
#define BIT_SPARK2_UNUSED3 2
#define BIT_SPARK2_SPARK2_ACTIVE 2
#define BIT_SPARK2_UNUSED4 3
#define BIT_SPARK2_UNUSED5 4
#define BIT_SPARK2_UNUSED6 5
@ -259,11 +259,22 @@
#define FUEL2_MODE_CONDITIONAL_SWITCH 3
#define FUEL2_MODE_INPUT_SWITCH 4
#define SPARK2_MODE_OFF 0
#define SPARK2_MODE_MULTIPLY 1
#define SPARK2_MODE_ADD 2
#define SPARK2_MODE_CONDITIONAL_SWITCH 3
#define SPARK2_MODE_INPUT_SWITCH 4
#define FUEL2_CONDITION_RPM 0
#define FUEL2_CONDITION_MAP 1
#define FUEL2_CONDITION_TPS 2
#define FUEL2_CONDITION_ETH 3
#define SPARK2_CONDITION_RPM 0
#define SPARK2_CONDITION_MAP 1
#define SPARK2_CONDITION_TPS 2
#define SPARK2_CONDITION_ETH 3
#define RESET_CONTROL_DISABLED 0
#define RESET_CONTROL_PREVENT_WHEN_RUNNING 1
#define RESET_CONTROL_PREVENT_ALWAYS 2
@ -1289,6 +1300,7 @@ extern byte pinIdle2; //2 wire idle control (Not currently used)
extern byte pinIdleUp; //Input for triggering Idle Up
extern byte pinCTPS; //Input for triggering closed throttle state
extern byte pinFuel2Input; //Input for switching to the 2nd fuel table
extern byte pinSpark2Input; //Input for switching to the 2nd ignition table
extern byte pinSpareTemp1; // Future use only
extern byte pinSpareTemp2; // Future use only
extern byte pinSpareOut1; //Generic output

View File

@ -187,6 +187,7 @@ byte pinIdle2; //2 wire idle control (Not currently used)
byte pinIdleUp; //Input for triggering Idle Up
byte pinCTPS; //Input for triggering closed throttle state
byte pinFuel2Input; //Input for switching to the 2nd fuel table
byte pinSpark2Input; //Input for switching to the 2nd ignition table
byte pinSpareTemp1; // Future use only
byte pinSpareTemp2; // Future use only
byte pinSpareOut1; //Generic output

View File

@ -2399,6 +2399,7 @@ void setPinMapping(byte boardID)
if ( (configPage6.useExtBaro != 0) && (configPage6.baroPin < BOARD_NR_GPIO_PINS) ) { pinBaro = configPage6.baroPin + A0; }
if ( (configPage6.useEMAP != 0) && (configPage10.EMAPPin < BOARD_NR_GPIO_PINS) ) { pinEMAP = configPage10.EMAPPin + A0; }
if ( (configPage10.fuel2InputPin != 0) && (configPage10.fuel2InputPin < BOARD_NR_GPIO_PINS) ) { pinFuel2Input = pinTranslate(configPage10.fuel2InputPin); }
if ( (configPage10.spark2InputPin != 0) && (configPage10.spark2InputPin < BOARD_NR_GPIO_PINS) ) { pinSpark2Input = pinTranslate(configPage10.spark2InputPin); }
if ( (configPage2.vssPin != 0) && (configPage2.vssPin < BOARD_NR_GPIO_PINS) ) { pinVSS = pinTranslate(configPage2.vssPin); }
if ( (configPage10.fuelPressurePin != 0) && (configPage10.fuelPressurePin < BOARD_NR_GPIO_PINS) ) { pinFuelPressure = configPage10.fuelPressurePin + A0; }
if ( (configPage10.oilPressurePin != 0) && (configPage10.oilPressurePin < BOARD_NR_GPIO_PINS) ) { pinOilPressure = configPage10.oilPressurePin + A0; }
@ -2568,6 +2569,11 @@ void setPinMapping(byte boardID)
if (configPage10.fuel2InputPullup == true) { pinMode(pinFuel2Input, INPUT_PULLUP); } //With pullup
else { pinMode(pinFuel2Input, INPUT); } //Normal input
}
if(configPage10.spark2Mode == SPARK2_MODE_INPUT_SWITCH)
{
if (configPage10.spark2InputPullup == true) { pinMode(pinSpark2Input, INPUT_PULLUP); } //With pullup
else { pinMode(pinSpark2Input, INPUT); } //Normal input
}
if(configPage10.fuelPressureEnable > 0)
{
pinMode(pinFuelPressure, INPUT);

View File

@ -0,0 +1,4 @@
void calculateSecondaryFuel();
void calculateSecondarySpark();
byte getVE2();
byte getAdvance2();

View File

@ -0,0 +1,211 @@
#include "globals.h"
#include "secondaryTables.h"
#include "corrections.h"
void calculateSecondaryFuel()
{
//If the secondary fuel table is in use, also get the VE value from there
BIT_CLEAR(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Clear the bit indicating that the 2nd fuel table is in use.
if(configPage10.fuel2Mode > 0)
{
if(configPage10.fuel2Mode == FUEL2_MODE_MULTIPLY)
{
currentStatus.VE2 = getVE2();
//Fuel 2 table is treated as a % value. Table 1 and 2 are multiplied together and divded by 100
uint16_t combinedVE = ((uint16_t)currentStatus.VE1 * (uint16_t)currentStatus.VE2) / 100;
if(combinedVE <= 255) { currentStatus.VE = combinedVE; }
else { currentStatus.VE = 255; }
}
else if(configPage10.fuel2Mode == FUEL2_MODE_ADD)
{
currentStatus.VE2 = getVE2();
//Fuel tables are added together, but a check is made to make sure this won't overflow the 8-bit VE value
uint16_t combinedVE = (uint16_t)currentStatus.VE1 + (uint16_t)currentStatus.VE2;
if(combinedVE <= 255) { currentStatus.VE = combinedVE; }
else { currentStatus.VE = 255; }
}
else if(configPage10.fuel2Mode == FUEL2_MODE_CONDITIONAL_SWITCH )
{
if(configPage10.fuel2SwitchVariable == FUEL2_CONDITION_RPM)
{
if(currentStatus.RPM > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
}
}
else if(configPage10.fuel2SwitchVariable == FUEL2_CONDITION_MAP)
{
if(currentStatus.MAP > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
}
}
else if(configPage10.fuel2SwitchVariable == FUEL2_CONDITION_TPS)
{
if(currentStatus.TPS > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
}
}
else if(configPage10.fuel2SwitchVariable == FUEL2_CONDITION_ETH)
{
if(currentStatus.ethanolPct > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
}
}
}
else if(configPage10.fuel2Mode == FUEL2_MODE_INPUT_SWITCH)
{
if(digitalRead(pinFuel2Input) == configPage10.fuel2InputPolarity)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
}
}
}
}
void calculateSecondarySpark()
{
//Same as above but for the secondary ignition table
BIT_CLEAR(currentStatus.spark2, BIT_SPARK2_SPARK2_ACTIVE); //Clear the bit indicating that the 2nd spark table is in use.
if(configPage10.spark2Mode > 0)
{
if(configPage10.spark2Mode == SPARK2_MODE_MULTIPLY)
{
currentStatus.advance2 = getAdvance2();
//Spark 2 table is treated as a % value. Table 1 and 2 are multiplied together and divded by 100
uint16_t combinedadvance = ((uint16_t)currentStatus.advance1 * (uint16_t)currentStatus.advance2) / 100;
if(combinedadvance <= 255) { currentStatus.advance = combinedadvance; }
else { currentStatus.advance = 255; }
}
else if(configPage10.spark2Mode == SPARK2_MODE_ADD)
{
BIT_SET(currentStatus.spark2, BIT_SPARK2_SPARK2_ACTIVE); //Set the bit indicating that the 2nd spark table is in use.
currentStatus.advance2 = getAdvance2();
//Spark tables are added together, but a check is made to make sure this won't overflow the 8-bit VE value
uint16_t combinedadvance = (uint16_t)currentStatus.advance1 + (uint16_t)currentStatus.advance2;
if(combinedadvance <= 255) { currentStatus.advance = combinedadvance; }
else { currentStatus.advance = 255; }
}
else if(configPage10.spark2Mode == SPARK2_MODE_CONDITIONAL_SWITCH )
{
if(configPage10.spark2SwitchVariable == SPARK2_CONDITION_RPM)
{
if(currentStatus.RPM > configPage10.spark2SwitchValue)
{
BIT_SET(currentStatus.spark2, BIT_SPARK2_SPARK2_ACTIVE); //Set the bit indicating that the 2nd spark table is in use.
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
else if(configPage10.fuel2SwitchVariable == FUEL2_CONDITION_MAP)
{
if(currentStatus.MAP > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.spark2, BIT_SPARK2_SPARK2_ACTIVE); //Set the bit indicating that the 2nd spark table is in use.
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
else if(configPage10.spark2SwitchVariable == SPARK2_CONDITION_TPS)
{
if(currentStatus.TPS > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.spark2, BIT_SPARK2_SPARK2_ACTIVE); //Set the bit indicating that the 2nd spark table is in use.
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
else if(configPage10.spark2SwitchVariable == SPARK2_CONDITION_ETH)
{
if(currentStatus.ethanolPct > configPage10.spark2SwitchValue)
{
BIT_SET(currentStatus.spark2, BIT_SPARK2_SPARK2_ACTIVE); //Set the bit indicating that the 2nd spark table is in use.
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
}
else if(configPage10.spark2Mode == SPARK2_MODE_INPUT_SWITCH)
{
if(digitalRead(pinSpark2Input) == configPage10.spark2InputPolarity)
{
BIT_SET(currentStatus.spark2, BIT_SPARK2_SPARK2_ACTIVE); //Set the bit indicating that the 2nd spark table is in use.
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
}
}
/**
* @brief Looks up and returns the VE value from the secondary fuel table
*
* This performs largely the same operations as getVE() however the lookup is of the secondary fuel table and uses the secondary load source
* @return byte
*/
byte getVE2()
{
byte tempVE = 100;
if( configPage10.fuel2Algorithm == LOAD_SOURCE_MAP)
{
//Speed Density
currentStatus.fuelLoad2 = currentStatus.MAP;
}
else if (configPage10.fuel2Algorithm == LOAD_SOURCE_TPS)
{
//Alpha-N
currentStatus.fuelLoad2 = currentStatus.TPS;
}
else if (configPage10.fuel2Algorithm == LOAD_SOURCE_IMAPEMAP)
{
//IMAP / EMAP
currentStatus.fuelLoad2 = (currentStatus.MAP * 100) / currentStatus.EMAP;
}
else { currentStatus.fuelLoad2 = currentStatus.MAP; } //Fallback position
tempVE = get3DTableValue(&fuelTable2, currentStatus.fuelLoad2, currentStatus.RPM); //Perform lookup into fuel map for RPM vs MAP value
return tempVE;
}
/**
* @brief Performs a lookup of the second ignition advance table. The values used to look this up will be RPM and whatever load source the user has configured
*
* @return byte The current target advance value in degrees
*/
byte getAdvance2()
{
byte tempAdvance = 0;
if (configPage2.ignAlgorithm == LOAD_SOURCE_MAP) //Check which fuelling algorithm is being used
{
//Speed Density
currentStatus.ignLoad = currentStatus.MAP;
}
else if(configPage2.ignAlgorithm == LOAD_SOURCE_TPS)
{
//Alpha-N
currentStatus.ignLoad = currentStatus.TPS;
}
else if (configPage2.fuelAlgorithm == LOAD_SOURCE_IMAPEMAP)
{
//IMAP / EMAP
currentStatus.ignLoad = (currentStatus.MAP * 100) / currentStatus.EMAP;
}
tempAdvance = get3DTableValue(&ignitionTable2, currentStatus.ignLoad, currentStatus.RPM) - OFFSET_IGNITION; //As above, but for ignition advance
tempAdvance = correctionsIgn(tempAdvance);
return tempAdvance;
}

View File

@ -15,9 +15,7 @@
uint16_t PW(int REQ_FUEL, byte VE, long MAP, uint16_t corrections, int injOpen);
byte getVE1();
byte getVE2();
byte getAdvance1();
byte getAdvance2();
uint16_t calculateInjectorStartAngle(uint16_t, int16_t);
void calculateIgnitionAngles(int);

View File

@ -37,6 +37,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "init.h"
#include "utilities.h"
#include "engineProtection.h"
#include "secondaryTables.h"
#include BOARD_H //Note that this is not a real file, it is defined in globals.h.
int ignition1StartAngle = 0;
@ -373,97 +374,8 @@ void loop()
currentStatus.advance1 = getAdvance1();
currentStatus.advance = currentStatus.advance1; //Set the final advance value to be advance 1 as a default. This may be changed in the section below
//If the secondary fuel table is in use, also get the VE value from there
BIT_CLEAR(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Clear the bit indicating that the 2nd fuel table is in use.
if(configPage10.fuel2Mode > 0)
{
if(configPage10.fuel2Mode == FUEL2_MODE_MULTIPLY)
{
currentStatus.VE2 = getVE2();
//Fuel 2 table is treated as a % value. Table 1 and 2 are multiplied together and divded by 100
uint16_t combinedVE = ((uint16_t)currentStatus.VE1 * (uint16_t)currentStatus.VE2) / 100;
if(combinedVE <= 255) { currentStatus.VE = combinedVE; }
else { currentStatus.VE = 255; }
currentStatus.advance2 = getAdvance2();
//Spark 2 table is treated as a % value. Table 1 and 2 are multiplied together and divded by 100
uint16_t combinedadvance = ((uint16_t)currentStatus.advance1 * (uint16_t)currentStatus.advance2) / 100;
if(combinedadvance <= 255) { currentStatus.advance = combinedadvance; }
else { currentStatus.advance = 255; }
}
else if(configPage10.fuel2Mode == FUEL2_MODE_ADD)
{
currentStatus.VE2 = getVE2();
//Fuel tables are added together, but a check is made to make sure this won't overflow the 8-bit VE value
uint16_t combinedVE = (uint16_t)currentStatus.VE1 + (uint16_t)currentStatus.VE2;
if(combinedVE <= 255) { currentStatus.VE = combinedVE; }
else { currentStatus.VE = 255; }
currentStatus.advance2 = getAdvance2();
//Spark tables are added together, but a check is made to make sure this won't overflow the 8-bit VE value
uint16_t combinedadvance = (uint16_t)currentStatus.advance1 + (uint16_t)currentStatus.advance2;
if(combinedadvance <= 255) { currentStatus.advance = combinedadvance; }
else { currentStatus.advance = 255; }
}
else if(configPage10.fuel2Mode == FUEL2_MODE_CONDITIONAL_SWITCH )
{
if(configPage10.fuel2SwitchVariable == FUEL2_CONDITION_RPM)
{
if(currentStatus.RPM > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
else if(configPage10.fuel2SwitchVariable == FUEL2_CONDITION_MAP)
{
if(currentStatus.MAP > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
else if(configPage10.fuel2SwitchVariable == FUEL2_CONDITION_TPS)
{
if(currentStatus.TPS > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
else if(configPage10.fuel2SwitchVariable == FUEL2_CONDITION_ETH)
{
if(currentStatus.ethanolPct > configPage10.fuel2SwitchValue)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
}
else if(configPage10.fuel2Mode == FUEL2_MODE_INPUT_SWITCH)
{
if(digitalRead(pinFuel2Input) == configPage10.fuel2InputPolarity)
{
BIT_SET(currentStatus.status3, BIT_STATUS3_FUEL2_ACTIVE); //Set the bit indicating that the 2nd fuel table is in use.
currentStatus.VE2 = getVE2();
currentStatus.VE = currentStatus.VE2;
currentStatus.advance2 = getAdvance2();
currentStatus.advance = currentStatus.advance2;
}
}
}
calculateSecondaryFuel();
calculateSecondarySpark();
//Always check for sync
//Main loop runs within this clause
@ -1343,36 +1255,6 @@ byte getVE1()
return tempVE;
}
/**
* @brief Looks up and returns the VE value from the secondary fuel table
*
* This performs largely the same operations as getVE() however the lookup is of the secondary fuel table and uses the secondary load source
* @return byte
*/
byte getVE2()
{
byte tempVE = 100;
if( configPage10.fuel2Algorithm == LOAD_SOURCE_MAP)
{
//Speed Density
currentStatus.fuelLoad2 = currentStatus.MAP;
}
else if (configPage10.fuel2Algorithm == LOAD_SOURCE_TPS)
{
//Alpha-N
currentStatus.fuelLoad2 = currentStatus.TPS;
}
else if (configPage10.fuel2Algorithm == LOAD_SOURCE_IMAPEMAP)
{
//IMAP / EMAP
currentStatus.fuelLoad2 = (currentStatus.MAP * 100) / currentStatus.EMAP;
}
else { currentStatus.fuelLoad2 = currentStatus.MAP; } //Fallback position
tempVE = get3DTableValue(&fuelTable2, currentStatus.fuelLoad2, currentStatus.RPM); //Perform lookup into fuel map for RPM vs MAP value
return tempVE;
}
/**
* @brief Performs a lookup of the ignition advance table. The values used to look this up will be RPM and whatever load source the user has configured
*
@ -1403,36 +1285,6 @@ byte getAdvance1()
return tempAdvance;
}
/**
* @brief Performs a lookup of the second ignition advance table. The values used to look this up will be RPM and whatever load source the user has configured
*
* @return byte The current target advance value in degrees
*/
byte getAdvance2()
{
byte tempAdvance = 0;
if (configPage2.ignAlgorithm == LOAD_SOURCE_MAP) //Check which fuelling algorithm is being used
{
//Speed Density
currentStatus.ignLoad = currentStatus.MAP;
}
else if(configPage2.ignAlgorithm == LOAD_SOURCE_TPS)
{
//Alpha-N
currentStatus.ignLoad = currentStatus.TPS;
}
else if (configPage2.fuelAlgorithm == LOAD_SOURCE_IMAPEMAP)
{
//IMAP / EMAP
currentStatus.ignLoad = (currentStatus.MAP * 100) / currentStatus.EMAP;
}
tempAdvance = get3DTableValue(&ignitionTable2, currentStatus.ignLoad, currentStatus.RPM) - OFFSET_IGNITION; //As above, but for ignition advance
tempAdvance = correctionsIgn(tempAdvance);
return tempAdvance;
}
uint16_t calculateInjectorStartAngle(uint16_t PWdivTimerPerDegree, int16_t injChannelDegrees)
{
uint16_t tempInjectorStartAngle = (currentStatus.injAngle + injChannelDegrees);