Sync with last changes

This commit is contained in:
VitorBoss 2017-08-28 01:35:49 -03:00
parent e01dccc6b8
commit c10a637853
14 changed files with 458 additions and 278 deletions

View File

@ -30,12 +30,29 @@ void initialiseFan();
#define VVT_TIMER_COUNTER FTM1_CNT
#elif defined(CORE_STM32)
#define ENABLE_VVT_TIMER()
#define DISABLE_VVT_TIMER()
#if defined(ARDUINO_ARCH_STM32) // STM32GENERIC core
#define ENABLE_BOOST_TIMER() (TIM1)->CCER |= TIM_CCER_CC2E
#define DISABLE_BOOST_TIMER() (TIM1)->CCER &= ~TIM_CCER_CC2E
#define ENABLE_BOOST_TIMER()
#define DISABLE_BOOST_TIMER()
#define ENABLE_VVT_TIMER() (TIM1)->CCER |= TIM_CCER_CC3E
#define DISABLE_VVT_TIMER() (TIM1)->CCER &= ~TIM_CCER_CC3E
#define BOOST_TIMER_COMPARE (TIM1)->CCR2
#define BOOST_TIMER_COUNTER (TIM1)->CNT
#define VVT_TIMER_COMPARE (TIM1)->CCR3
#define VVT_TIMER_COUNTER (TIM1)->CNT
#else //libmaple core aka STM32DUINO
#define ENABLE_BOOST_TIMER() (TIMER1->regs).gen->CCER |= TIMER_CCER_CC2E
#define DISABLE_BOOST_TIMER() (TIMER1->regs).gen->CCER &= ~TIMER_CCER_CC2E
#define ENABLE_VVT_TIMER() (TIMER1->regs).gen->CCER |= TIMER_CCER_CC3E
#define DISABLE_VVT_TIMER() (TIMER1->regs).gen->CCER &= ~TIMER_CCER_CC3E
#define BOOST_TIMER_COMPARE (TIMER1->regs).gen->CCR2
#define BOOST_TIMER_COUNTER (TIMER1->regs).gen->CNT
#define VVT_TIMER_COMPARE (TIMER1->regs).gen->CCR3
#define VVT_TIMER_COUNTER (TIMER1->regs).gen->CNT
#endif
#endif
#define BOOST_PIN_LOW() *boost_pin_port &= ~(boost_pin_mask)
@ -64,6 +81,10 @@ volatile bool vvt_pwm_state;
unsigned int vvt_pwm_max_count; //Used for variable PWM frequency
volatile unsigned int vvt_pwm_cur_value;
long vvt_pwm_target_value;
#if defined (CORE_TEENSY) || defined(CORE_STM32)
static inline void boostInterrupt();
static inline void vvtInterrupt();
#endif
#endif

View File

@ -30,7 +30,6 @@ void fanControl()
}
}
#if defined(CORE_AVR) || defined(CORE_TEENSY)
void initialiseAuxPWM()
{
#if defined(CORE_AVR)
@ -41,6 +40,10 @@ void initialiseAuxPWM()
TCCR1B = (1 << CS12); //Timer1 Control Reg B: Timer Prescaler set to 256. 1 tick = 16uS. Refer to http://www.instructables.com/files/orig/F3T/TIKL/H3WSA4V7/F3TTIKLH3WSA4V7.jpg
#elif defined(CORE_TEENSY)
//REALLY NEED TO DO THIS!
#elif defined(CORE_STM32)
Timer1.attachInterrupt(2, boostInterrupt);
Timer1.attachInterrupt(3, vvtInterrupt);
Timer1.resume();
#endif
boost_pin_port = portOutputRegister(digitalPinToPort(pinBoost));
@ -48,8 +51,13 @@ void initialiseAuxPWM()
vvt_pin_port = portOutputRegister(digitalPinToPort(pinVVT_1));
vvt_pin_mask = digitalPinToBitMask(pinVVT_1);
boost_pwm_max_count = 1000000L / (16 * configPage3.boostFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle. The x2 is there because the frequency is stored at half value (in a byte) to allow freqneucies up to 511Hz
vvt_pwm_max_count = 1000000L / (16 * configPage3.vvtFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle
#if defined(CORE_STM32) //2uS resolution Min 8Hz, Max 5KHz
boost_pwm_max_count = 1000000L / (configPage3.boostFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle. The x2 is there because the frequency is stored at half value (in a byte) to allow freqneucies up to 511Hz
vvt_pwm_max_count = 1000000L / (configPage3.vvtFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle
#else
boost_pwm_max_count = 1000000L / (16 * configPage3.boostFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle. The x2 is there because the frequency is stored at half value (in a byte) to allow freqneucies up to 511Hz
vvt_pwm_max_count = 1000000L / (16 * configPage3.vvtFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle
#endif
//TIMSK1 |= (1 << OCIE1A); <---- Not required as compare A is turned on when needed by boost control
ENABLE_VVT_TIMER(); //Turn on the B compare unit (ie turn on the interrupt)
@ -139,7 +147,7 @@ void vvtControl()
//The interrupt to control the Boost PWM
#if defined(CORE_AVR)
ISR(TIMER1_COMPA_vect)
#elif defined (CORE_TEENSY)
#elif defined (CORE_TEENSY) || defined(CORE_STM32)
static inline void boostInterrupt() //Most ARM chips can simply call a function
#endif
{
@ -161,7 +169,7 @@ void vvtControl()
//The interrupt to control the VVT PWM
#if defined(CORE_AVR)
ISR(TIMER1_COMPB_vect)
#elif defined (CORE_TEENSY)
#elif defined (CORE_TEENSY) || defined(CORE_STM32)
static inline void vvtInterrupt() //Most ARM chips can simply call a function
#endif
{
@ -180,10 +188,3 @@ void vvtControl()
}
}
#elif defined(CORE_STM32)
//YET TO BE IMPLEMENTED ON STM32
void initialiseAuxPWM() { }
void boostControl() { }
void vvtControl() { }
#endif

View File

@ -15,7 +15,11 @@ uint8_t Glow, Ghigh;
#if defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__)
HardwareSerial &CANSerial = Serial3;
#elif defined(CORE_STM32)
HardwareSerial &CANSerial = Serial2;
#if defined(ARDUINO_ARCH_STM32) // STM32GENERIC core
SerialUART &CANSerial = Serial2;
#else //libmaple core aka STM32DUINO
HardwareSerial &CANSerial = Serial2;
#endif
#elif defined(CORE_TEENSY)
HardwareSerial &CANSerial = Serial2;
#endif

View File

@ -9,14 +9,25 @@
#define CORE_AVR
#elif defined(CORE_TEENSY)
#define BOARD_NR_GPIO_PINS 34
#elif defined(STM32_MCU_SERIES) || defined(_VARIANT_ARDUINO_STM32_)
#elif defined(STM32_MCU_SERIES) || defined(ARDUINO_ARCH_STM32) || defined(__STM32F1__) || defined(STM32F4) || defined(STM32)
#define CORE_STM32
#define LED_BUILTIN 33
#if defined (STM32F1) || defined(__STM32F1__)
#define BOARD_NR_GPIO_PINS 34
#define LED_BUILTIN 33
#elif defined(ARDUINO_BLACK_F407VE) || defined(STM32F4)
#define BOARD_NR_GPIO_PINS 80
#define LED_BUILTIN PA7
#endif
extern "C" char* sbrk(int incr); //Used to freeRam
inline unsigned char digitalPinToInterrupt(unsigned char Interrupt_pin) { return Interrupt_pin; } //This isn't included in the stm32duino libs (yet)
#define portOutputRegister(port) (volatile byte *)( &(port->regs->ODR) ) //These are defined in STM32F1/variants/generic_stm32f103c/variant.h but return a non byte* value
#define portInputRegister(port) (volatile byte *)( &(port->regs->IDR) ) //These are defined in STM32F1/variants/generic_stm32f103c/variant.h but return a non byte* value
#if defined(ARDUINO_ARCH_STM32) // STM32GENERIC core
#define portOutputRegister(port) (volatile byte *)( &(port->ODR) )
#define portInputRegister(port) (volatile byte *)( &(port->IDR) )
#else //libmaple core aka STM32DUINO
#define portOutputRegister(port) (volatile byte *)( &(port->regs->ODR) ) //These are defined in STM32F1/variants/generic_stm32f103c/variant.h but return a non byte* value
#define portInputRegister(port) (volatile byte *)( &(port->regs->IDR) ) //These are defined in STM32F1/variants/generic_stm32f103c/variant.h but return a non byte* value
#endif
#else
#error Incorrect board selected. Please select the correct board (Usually Mega 2560) and upload again
#endif
@ -72,6 +83,12 @@
#define BIT_SPARK2_UNUSED7 6
#define BIT_SPARK2_UNUSED8 7
#define BIT_TIMER_1HZ 0
#define BIT_TIMER_4HZ 1
#define BIT_TIMER_10HZ 2
#define BIT_TIMER_15HZ 3
#define BIT_TIMER_30HZ 4
#define VALID_MAP_MAX 1022 //The largest ADC value that is valid for the MAP sensor
#define VALID_MAP_MIN 2 //The smallest ADC value that is valid for the MAP sensor

View File

@ -40,14 +40,19 @@ struct StepperIdle
#define IDLE_TIMER_DISABLE() FTM2_C0SC &= ~FTM_CSC_CHIE
#elif defined(CORE_STM32)
#if defined(ARDUINO_ARCH_STM32) // STM32GENERIC core
#define IDLE_COUNTER (TIM1)->CNT
#define IDLE_COMPARE (TIM1)->CCR4
//Placeholders only
#define IDLE_COUNTER 0
#define IDLE_COMPARE 0
#define IDLE_TIMER_ENABLE()
#define IDLE_TIMER_DISABLE()
#define IDLE_TIMER_ENABLE() (TIM1)->CCER |= TIM_CCER_CC4E
#define IDLE_TIMER_DISABLE() (TIM1)->CCER &= ~TIM_CCER_CC4E
#else //libmaple core aka STM32DUINO
#define IDLE_COUNTER (TIMER1->regs).gen->CNT
#define IDLE_COMPARE (TIMER1->regs).gen->CCR4
#define IDLE_TIMER_ENABLE() (TIMER1->regs).gen->CCER |= TIMER_CCER_CC4E
#define IDLE_TIMER_DISABLE() (TIMER1->regs).gen->CCER &= ~TIMER_CCER_CC4E
#endif
#endif
struct table2D iacClosedLoopTable;
@ -81,5 +86,8 @@ static inline void enableIdle();
static inline byte isStepperHomed();
static inline byte checkForStepping();
static inline void doStep();
#if defined (CORE_TEENSY) || defined(CORE_STM32)
static inline void idleInterrupt();
#endif
#endif

View File

@ -78,8 +78,9 @@ void initialiseIdle()
NVIC_ENABLE_IRQ(IRQ_FTM2);
}
#elif defined(MCU_STM32F103RB)
#elif defined(CORE_STM32)
Timer1.attachInterrupt(4, idleInterrupt);
Timer1.resume();
#endif
//Initialising comprises of setting the 2D tables with the relevant values from the config pages
@ -114,7 +115,11 @@ void initialiseIdle()
idle_pin_mask = digitalPinToBitMask(pinIdle1);
idle2_pin_port = portOutputRegister(digitalPinToPort(pinIdle2));
idle2_pin_mask = digitalPinToBitMask(pinIdle2);
idle_pwm_max_count = 1000000L / (16 * configPage3.idleFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle. Note that the frequency is divided by 2 coming from TS to allow for up to 512hz
#if defined(CORE_STM32)
idle_pwm_max_count = 1000000L / (configPage3.idleFreq * 2); //Converts the frequency in Hz to the number of ticks (at 2uS) it takes to complete 1 cycle. Note that the frequency is divided by 2 coming from TS to allow for up to 5KHz
#else
idle_pwm_max_count = 1000000L / (16 * configPage3.idleFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle. Note that the frequency is divided by 2 coming from TS to allow for up to 512hz
#endif
enableIdle();
break;
@ -134,7 +139,11 @@ void initialiseIdle()
idle_pin_mask = digitalPinToBitMask(pinIdle1);
idle2_pin_port = portOutputRegister(digitalPinToPort(pinIdle2));
idle2_pin_mask = digitalPinToBitMask(pinIdle2);
idle_pwm_max_count = 1000000L / (16 * configPage3.idleFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle. Note that the frequency is divided by 2 coming from TS to allow for up to 512hz
#if defined(CORE_STM32)
idle_pwm_max_count = 1000000L / (configPage3.idleFreq * 2); //Converts the frequency in Hz to the number of ticks (at 2uS) it takes to complete 1 cycle. Note that the frequency is divided by 2 coming from TS to allow for up to 5KHz
#else
idle_pwm_max_count = 1000000L / (16 * configPage3.idleFreq * 2); //Converts the frequency in Hz to the number of ticks (at 16uS) it takes to complete 1 cycle. Note that the frequency is divided by 2 coming from TS to allow for up to 512hz
#endif
idlePID.SetOutputLimits(percentage(configPage1.iacCLminDuty, idle_pwm_max_count), percentage(configPage1.iacCLmaxDuty, idle_pwm_max_count));
idlePID.SetTunings(configPage3.idleKP, configPage3.idleKI, configPage3.idleKD);
idlePID.SetMode(AUTOMATIC); //Turn PID on
@ -407,7 +416,6 @@ ISR(TIMER4_COMPC_vect)
#elif defined (CORE_TEENSY) || defined (CORE_STM32)
static inline void idleInterrupt() //Most ARM chips can simply call a function
#endif
#if defined(CORE_AVR) || defined (CORE_TEENSY)
{
if (idle_pwm_state)
{
@ -446,8 +454,3 @@ static inline void idleInterrupt() //Most ARM chips can simply call a function
}
}
#elif defined (CORE_STM32)
{
//No PWM idle for STM32 yet
}
#endif

View File

@ -162,59 +162,103 @@ See page 136 of the processors datasheet: http://www.atmel.com/Images/doc2549.pd
#define uS_TO_TIMER_COMPARE_SLOW(uS) ((uS * 15) >> 5)
#elif defined(CORE_STM32)
//Placeholders ONLY!
//https://github.com/rogerclarkmelbourne/Arduino_STM32/blob/master/STM32F4/cores/maple/libmaple/timer.h#L51
#define MAX_TIMER_PERIOD 131070 //The longest period of time (in uS) that the timer can permit (IN this case it is 65535 * 2, as each timer tick is 2uS)
#define uS_TO_TIMER_COMPARE(uS) (uS >> 1) //Converts a given number of uS into the required number of timer ticks until that time has passed.
#define uS_TO_TIMER_COMPARE_SLOW(uS) (uS >> 1) //Converts a given number of uS into the required number of timer ticks until that time has passed.
#if defined(ARDUINO_ARCH_STM32) // STM32GENERIC core
#include "HardwareTimer.h"
#define FUEL1_COUNTER (TIM2)->CNT
#define FUEL2_COUNTER (TIM2)->CNT
#define FUEL3_COUNTER (TIM2)->CNT
#define FUEL4_COUNTER (TIM2)->CNT
#define FUEL5_COUNTER (TIM2)->CNT
#define FUEL1_COUNTER (TIMER2->regs).gen->CNT
#define FUEL2_COUNTER (TIMER2->regs).gen->CNT
#define FUEL3_COUNTER (TIMER2->regs).gen->CNT
#define FUEL4_COUNTER (TIMER2->regs).gen->CNT
#define FUEL5_COUNTER (TIMER1->regs).gen->CNT
#define IGN1_COUNTER (TIM3)->CNT
#define IGN2_COUNTER (TIM3)->CNT
#define IGN3_COUNTER (TIM3)->CNT
#define IGN4_COUNTER (TIM3)->CNT
#define IGN5_COUNTER (TIM3)->CNT
#define IGN1_COUNTER (TIMER3->regs).gen->CNT
#define IGN2_COUNTER (TIMER3->regs).gen->CNT
#define IGN3_COUNTER (TIMER3->regs).gen->CNT
#define IGN4_COUNTER (TIMER3->regs).gen->CNT
#define IGN5_COUNTER (TIMER1->regs).gen->CNT
#define FUEL1_COMPARE (TIM2)->CCR1
#define FUEL2_COMPARE (TIM2)->CCR2
#define FUEL3_COMPARE (TIM2)->CCR3
#define FUEL4_COMPARE (TIM2)->CCR4
#define FUEL1_COMPARE (TIMER2->regs).gen->CCR1
#define FUEL2_COMPARE (TIMER2->regs).gen->CCR2
#define FUEL3_COMPARE (TIMER2->regs).gen->CCR3
#define FUEL4_COMPARE (TIMER2->regs).gen->CCR4
#define IGN1_COMPARE (TIM3)->CCR1
#define IGN2_COMPARE (TIM3)->CCR2
#define IGN3_COMPARE (TIM3)->CCR3
#define IGN4_COMPARE (TIM3)->CCR4
#define IGN5_COMPARE (TIM3)->CCR1
#define IGN1_COMPARE (TIMER3->regs).gen->CCR1
#define IGN2_COMPARE (TIMER3->regs).gen->CCR2
#define IGN3_COMPARE (TIMER3->regs).gen->CCR3
#define IGN4_COMPARE (TIMER3->regs).gen->CCR4
#define IGN5_COMPARE (TIMER1->regs).gen->CCR1
//https://github.com/rogerclarkmelbourne/Arduino_STM32/blob/754bc2969921f1ef262bd69e7faca80b19db7524/STM32F1/system/libmaple/include/libmaple/timer.h#L444
#define FUEL1_TIMER_ENABLE() (TIM2)->CCER |= TIM_CCER_CC1E
#define FUEL2_TIMER_ENABLE() (TIM2)->CCER |= TIM_CCER_CC2E
#define FUEL3_TIMER_ENABLE() (TIM2)->CCER |= TIM_CCER_CC3E
#define FUEL4_TIMER_ENABLE() (TIM2)->CCER |= TIM_CCER_CC4E
//https://github.com/rogerclarkmelbourne/Arduino_STM32/blob/754bc2969921f1ef262bd69e7faca80b19db7524/STM32F1/system/libmaple/include/libmaple/timer.h#L444
#define FUEL1_TIMER_ENABLE() (TIMER2->regs).gen->CCER |= TIMER_CCER_CC1E
#define FUEL2_TIMER_ENABLE() (TIMER2->regs).gen->CCER |= TIMER_CCER_CC2E
#define FUEL3_TIMER_ENABLE() (TIMER2->regs).gen->CCER |= TIMER_CCER_CC3E
#define FUEL4_TIMER_ENABLE() (TIMER2->regs).gen->CCER |= TIMER_CCER_CC4E
#define IGN1_TIMER_ENABLE() (TIM3)->CCER |= TIM_CCER_CC1E
#define IGN2_TIMER_ENABLE() (TIM3)->CCER |= TIM_CCER_CC2E
#define IGN3_TIMER_ENABLE() (TIM3)->CCER |= TIM_CCER_CC3E
#define IGN4_TIMER_ENABLE() (TIM3)->CCER |= TIM_CCER_CC4E
#define IGN5_TIMER_ENABLE() (TIM1)->CCER |= TIM_CCER_CC1E
#define IGN1_TIMER_ENABLE() (TIMER3->regs).gen->CCER |= TIMER_CCER_CC1E
#define IGN2_TIMER_ENABLE() (TIMER3->regs).gen->CCER |= TIMER_CCER_CC2E
#define IGN3_TIMER_ENABLE() (TIMER3->regs).gen->CCER |= TIMER_CCER_CC3E
#define IGN4_TIMER_ENABLE() (TIMER3->regs).gen->CCER |= TIMER_CCER_CC4E
#define IGN5_TIMER_ENABLE() (TIMER1->regs).gen->CCER |= TIMER_CCER_CC1E
#define FUEL1_TIMER_DISABLE() (TIM2)->CCER &= ~TIM_CCER_CC1E
#define FUEL2_TIMER_DISABLE() (TIM2)->CCER &= ~TIM_CCER_CC2E
#define FUEL3_TIMER_DISABLE() (TIM2)->CCER &= ~TIM_CCER_CC3E
#define FUEL4_TIMER_DISABLE() (TIM2)->CCER &= ~TIM_CCER_CC4E
#define FUEL1_TIMER_DISABLE() (TIMER2->regs).gen->CCER &= ~TIMER_CCER_CC1E
#define FUEL2_TIMER_DISABLE() (TIMER2->regs).gen->CCER &= ~TIMER_CCER_CC2E
#define FUEL3_TIMER_DISABLE() (TIMER2->regs).gen->CCER &= ~TIMER_CCER_CC3E
#define FUEL4_TIMER_DISABLE() (TIMER2->regs).gen->CCER &= ~TIMER_CCER_CC4E
#define IGN1_TIMER_DISABLE() (TIM3)->CCER &= ~TIM_CCER_CC1E
#define IGN2_TIMER_DISABLE() (TIM3)->CCER &= ~TIM_CCER_CC2E
#define IGN3_TIMER_DISABLE() (TIM3)->CCER &= ~TIM_CCER_CC3E
#define IGN4_TIMER_DISABLE() (TIM3)->CCER &= ~TIM_CCER_CC4E
#define IGN5_TIMER_DISABLE() (TIM1)->CCER &= ~TIM_CCER_CC1E
#else //libmaple core aka STM32DUINO
#define FUEL1_COUNTER (TIMER2->regs).gen->CNT
#define FUEL2_COUNTER (TIMER2->regs).gen->CNT
#define FUEL3_COUNTER (TIMER2->regs).gen->CNT
#define FUEL4_COUNTER (TIMER2->regs).gen->CNT
#define FUEL5_COUNTER (TIMER1->regs).gen->CNT
#define IGN1_TIMER_DISABLE() (TIMER3->regs).gen->CCER &= ~TIMER_CCER_CC1E
#define IGN2_TIMER_DISABLE() (TIMER3->regs).gen->CCER &= ~TIMER_CCER_CC2E
#define IGN3_TIMER_DISABLE() (TIMER3->regs).gen->CCER &= ~TIMER_CCER_CC3E
#define IGN4_TIMER_DISABLE() (TIMER3->regs).gen->CCER &= ~TIMER_CCER_CC4E
#define IGN5_TIMER_DISABLE() (TIMER1->regs).gen->CCER &= ~TIMER_CCER_CC1E
#define IGN1_COUNTER (TIMER3->regs).gen->CNT
#define IGN2_COUNTER (TIMER3->regs).gen->CNT
#define IGN3_COUNTER (TIMER3->regs).gen->CNT
#define IGN4_COUNTER (TIMER3->regs).gen->CNT
#define IGN5_COUNTER (TIMER1->regs).gen->CNT
#define FUEL1_COMPARE (TIMER2->regs).gen->CCR1
#define FUEL2_COMPARE (TIMER2->regs).gen->CCR2
#define FUEL3_COMPARE (TIMER2->regs).gen->CCR3
#define FUEL4_COMPARE (TIMER2->regs).gen->CCR4
#define IGN1_COMPARE (TIMER3->regs).gen->CCR1
#define IGN2_COMPARE (TIMER3->regs).gen->CCR2
#define IGN3_COMPARE (TIMER3->regs).gen->CCR3
#define IGN4_COMPARE (TIMER3->regs).gen->CCR4
#define IGN5_COMPARE (TIMER1->regs).gen->CCR1
//https://github.com/rogerclarkmelbourne/Arduino_STM32/blob/754bc2969921f1ef262bd69e7faca80b19db7524/STM32F1/system/libmaple/include/libmaple/timer.h#L444
#define FUEL1_TIMER_ENABLE() (TIMER2->regs).gen->CCER |= TIMER_CCER_CC1E
#define FUEL2_TIMER_ENABLE() (TIMER2->regs).gen->CCER |= TIMER_CCER_CC2E
#define FUEL3_TIMER_ENABLE() (TIMER2->regs).gen->CCER |= TIMER_CCER_CC3E
#define FUEL4_TIMER_ENABLE() (TIMER2->regs).gen->CCER |= TIMER_CCER_CC4E
#define IGN1_TIMER_ENABLE() (TIMER3->regs).gen->CCER |= TIMER_CCER_CC1E
#define IGN2_TIMER_ENABLE() (TIMER3->regs).gen->CCER |= TIMER_CCER_CC2E
#define IGN3_TIMER_ENABLE() (TIMER3->regs).gen->CCER |= TIMER_CCER_CC3E
#define IGN4_TIMER_ENABLE() (TIMER3->regs).gen->CCER |= TIMER_CCER_CC4E
#define IGN5_TIMER_ENABLE() (TIMER1->regs).gen->CCER |= TIMER_CCER_CC1E
#define FUEL1_TIMER_DISABLE() (TIMER2->regs).gen->CCER &= ~TIMER_CCER_CC1E
#define FUEL2_TIMER_DISABLE() (TIMER2->regs).gen->CCER &= ~TIMER_CCER_CC2E
#define FUEL3_TIMER_DISABLE() (TIMER2->regs).gen->CCER &= ~TIMER_CCER_CC3E
#define FUEL4_TIMER_DISABLE() (TIMER2->regs).gen->CCER &= ~TIMER_CCER_CC4E
#define IGN1_TIMER_DISABLE() (TIMER3->regs).gen->CCER &= ~TIMER_CCER_CC1E
#define IGN2_TIMER_DISABLE() (TIMER3->regs).gen->CCER &= ~TIMER_CCER_CC2E
#define IGN3_TIMER_DISABLE() (TIMER3->regs).gen->CCER &= ~TIMER_CCER_CC3E
#define IGN4_TIMER_DISABLE() (TIMER3->regs).gen->CCER &= ~TIMER_CCER_CC4E
#define IGN5_TIMER_DISABLE() (TIMER1->regs).gen->CCER &= ~TIMER_CCER_CC1E
#endif
#endif
void initialiseSchedulers();

View File

@ -161,23 +161,40 @@ void initialiseSchedulers()
NVIC_ENABLE_IRQ(IRQ_FTM1);
#elif defined(CORE_STM32)
//see https://github.com/rogerclarkmelbourne/Arduino_STM32/blob/754bc2969921f1ef262bd69e7faca80b19db7524/STM32F1/system/libmaple/include/libmaple/timer.h#L444
(TIMER1->regs).bas->PSC = (CYCLES_PER_MICROSECOND << 1) - 1; //2us resolution
(TIMER2->regs).bas->PSC = (CYCLES_PER_MICROSECOND << 1) - 1; //2us resolution
(TIMER3->regs).bas->PSC = (CYCLES_PER_MICROSECOND << 1) - 1; //2us resolution
// Alternative 2us resolution:
//TimerX.setPrescaleFactor(CYCLES_PER_MICROSECOND * 2U);
#if defined(ARDUINO_ARCH_STM32) // STM32GENERIC core
//see https://github.com/rogerclarkmelbourne/Arduino_STM32/blob/754bc2969921f1ef262bd69e7faca80b19db7524/STM32F1/system/libmaple/include/libmaple/timer.h#L444
Timer1.setPrescaleFactor((HAL_RCC_GetHCLKFreq() * 2U)-1); //2us resolution
Timer2.setPrescaleFactor((HAL_RCC_GetHCLKFreq() * 2U)-1); //2us resolution
Timer3.setPrescaleFactor((HAL_RCC_GetHCLKFreq() * 2U)-1); //2us resolution
Timer2.setMode(1, TIMER_OUTPUT_COMPARE);
Timer2.setMode(2, TIMER_OUTPUT_COMPARE);
Timer2.setMode(3, TIMER_OUTPUT_COMPARE);
Timer2.setMode(4, TIMER_OUTPUT_COMPARE);
Timer2.setMode(TIMER_CH1, TIMER_OUTPUT_COMPARE);
Timer2.setMode(TIMER_CH2, TIMER_OUTPUT_COMPARE);
Timer2.setMode(TIMER_CH3, TIMER_OUTPUT_COMPARE);
Timer2.setMode(TIMER_CH4, TIMER_OUTPUT_COMPARE);
Timer3.setMode(1, TIMER_OUTPUT_COMPARE);
Timer3.setMode(2, TIMER_OUTPUT_COMPARE);
Timer3.setMode(3, TIMER_OUTPUT_COMPARE);
Timer3.setMode(4, TIMER_OUTPUT_COMPARE);
Timer1.setMode(1, TIMER_OUTPUT_COMPARE);
Timer3.setMode(TIMER_CH1, TIMER_OUTPUT_COMPARE);
Timer3.setMode(TIMER_CH2, TIMER_OUTPUT_COMPARE);
Timer3.setMode(TIMER_CH3, TIMER_OUTPUT_COMPARE);
Timer3.setMode(TIMER_CH4, TIMER_OUTPUT_COMPARE);
#else //libmaple core aka STM32DUINO
//see https://github.com/rogerclarkmelbourne/Arduino_STM32/blob/754bc2969921f1ef262bd69e7faca80b19db7524/STM32F1/system/libmaple/include/libmaple/timer.h#L444
//(CYCLES_PER_MICROSECOND == 72, APB2 at 72MHz, APB1 at 36MHz).
//Timer2 to 4 is on APB1, Timer1 on APB2. http://www.st.com/resource/en/datasheet/stm32f103cb.pdf sheet 12
Timer1.setPrescaleFactor((72 * 2U)-1); //2us resolution
Timer2.setPrescaleFactor((36 * 2U)-1); //2us resolution
Timer3.setPrescaleFactor((36 * 2U)-1); //2us resolution
Timer2.setMode(TIMER_CH1, TIMER_OUTPUT_COMPARE);
Timer2.setMode(TIMER_CH2, TIMER_OUTPUT_COMPARE);
Timer2.setMode(TIMER_CH3, TIMER_OUTPUT_COMPARE);
Timer2.setMode(TIMER_CH4, TIMER_OUTPUT_COMPARE);
Timer3.setMode(TIMER_CH1, TIMER_OUTPUT_COMPARE);
Timer3.setMode(TIMER_CH2, TIMER_OUTPUT_COMPARE);
Timer3.setMode(TIMER_CH3, TIMER_OUTPUT_COMPARE);
Timer3.setMode(TIMER_CH4, TIMER_OUTPUT_COMPARE);
#endif
Timer2.attachInterrupt(1, fuelSchedule1Interrupt);
Timer2.attachInterrupt(2, fuelSchedule2Interrupt);
Timer2.attachInterrupt(3, fuelSchedule3Interrupt);
@ -187,7 +204,11 @@ void initialiseSchedulers()
Timer3.attachInterrupt(2, ignitionSchedule2Interrupt);
Timer3.attachInterrupt(3, ignitionSchedule3Interrupt);
Timer3.attachInterrupt(4, ignitionSchedule4Interrupt);
Timer1.attachInterrupt(1, ignitionSchedule5Interrupt);
Timer1.resume();
Timer2.resume();
Timer3.resume();
#endif
fuelSchedule1.Status = OFF;

View File

@ -144,20 +144,23 @@ void setup()
table3D_setSize(&trim3Table, 6);
table3D_setSize(&trim4Table, 6);
#if defined(CORE_STM32)
EEPROM.init();
#endif
loadConfig();
doUpdates(); //Check if any data items need updating (Occurs ith firmware updates)
Serial.begin(115200);
#if defined(__AVR_ATmega1280__) || defined(__AVR_ATmega2560__) //ATmega2561 does not have Serial3
if (configPage10.enable_canbus == 1) { Serial3.begin(115200); }
if (configPage10.enable_canbus == 1) { CANSerial.begin(115200); }
#elif defined(CORE_STM32)
if (configPage10.enable_canbus == 1) { Serial2.begin(115200); }
if (configPage10.enable_canbus == 1) { CANSerial.begin(115200); }
else if (configPage10.enable_canbus == 2)
{
//enable local can interface
}
#elif defined(CORE_TEENSY)
if (configPage10.enable_canbus == 1) { Serial2.begin(115200); }
if (configPage10.enable_canbus == 1) { CANSerial.begin(115200); }
else if (configPage10.enable_canbus == 2)
{
//Teensy onboard CAN not used currently
@ -635,10 +638,11 @@ void setup()
void loop()
{
mainLoopCount++;
LOOP_TIMER = TIMER_mask;
//Check for any requets from serial. Serial operations are checked under 2 scenarios:
// 1) Every 64 loops (64 Is more than fast enough for TunerStudio). This function is equivalent to ((loopCount % 64) == 1) but is considerably faster due to not using the mod or division operations
// 2) If the amount of data in the serial buffer is greater than a set threhold (See globals.h). This is to avoid serial buffer overflow when large amounts of data is being sent
if ( ((mainLoopCount & 31) == 1) or (Serial.available() > SERIAL_BUFFER_THRESHOLD) )
if ( (BIT_CHECK(LOOP_TIMER, BIT_TIMER_15HZ)) or (Serial.available() > SERIAL_BUFFER_THRESHOLD) )
{
if (Serial.available() > 0)
{
@ -650,7 +654,7 @@ void loop()
//if serial3 interface is enabled then check for serial3 requests.
if (configPage10.enable_canbus == 1)
{
if ( ((mainLoopCount & 31) == 1) or (CANSerial.available() > SERIAL_BUFFER_THRESHOLD) )
if ( (BIT_CHECK(LOOP_TIMER, BIT_TIMER_15HZ)) or (CANSerial.available() > SERIAL_BUFFER_THRESHOLD) )
{
if (CANSerial.available() > 0)
{
@ -659,13 +663,13 @@ void loop()
}
}
#elif defined(CORE_STM32)
#elif defined(CORE_TEENSY) || defined(CORE_STM32)
//if can or secondary serial interface is enabled then check for requests.
if (configPage10.enable_canbus == 1) //secondary serial interface enabled
{
if ( ((mainLoopCount & 31) == 1) or (Serial2.available() > SERIAL_BUFFER_THRESHOLD) )
if ( (BIT_CHECK(LOOP_TIMER, BIT_TIMER_15HZ)) or (CANSerial.available() > SERIAL_BUFFER_THRESHOLD) )
{
if (Serial2.available() > 0)
if (CANSerial.available() > 0)
{
canCommand();
}
@ -674,23 +678,7 @@ void loop()
else if (configPage10.enable_canbus == 2) // can module enabled
{
//check local can module
}
#elif defined(CORE_TEENSY)
//if can or secondary serial interface is enabled then check for requests.
if (configPage10.enable_canbus == 1) //secondary serial interface enabled
{
if ( ((mainLoopCount & 31) == 1) or (Serial2.available() > SERIAL_BUFFER_THRESHOLD) )
{
if (Serial2.available() > 0)
{
canCommand();
}
}
}
else if (configPage10.enable_canbus == 2) // can module enabled
{
//check local can module
// if ( ((mainLoopCount & 31) == 1) or (CANbus0.available())
// if ( (BIT_CHECK(LOOP_TIMER, BIT_TIMER_15HZ)) or (CANbus0.available())
// {
// CANbus0.read(rx_msg);
// }
@ -755,8 +743,9 @@ void loop()
//-----------------------------------------------------------------------------------------------------
readMAP();
if ((mainLoopCount & 31) == 1) //Every 32 loops
if (BIT_CHECK(LOOP_TIMER, BIT_TIMER_15HZ)) //Every 32 loops
{
BIT_CLEAR(TIMER_mask, BIT_TIMER_15HZ);
readTPS(); //TPS reading to be performed every 32 loops (any faster and it can upset the TPSdot sampling time)
//Check for launching/flat shift (clutch) can be done around here too
@ -803,13 +792,15 @@ void loop()
//Most boost tends to run at about 30Hz, so placing it here ensures a new target time is fetched frequently enough
boostControl();
}
if( (mainLoopCount & 63) == 1) //Every 64 loops
if(BIT_CHECK(LOOP_TIMER, BIT_TIMER_30HZ)) //Every 64 loops
{
//Nothing here currently
BIT_CLEAR(TIMER_mask, BIT_TIMER_30HZ);
}
//The IAT and CLT readings can be done less frequently. This still runs about 4 times per second
if ((mainLoopCount & 255) == 1) //Every 256 loops
if (BIT_CHECK(LOOP_TIMER, BIT_TIMER_4HZ)) //Every 256 loops
{
BIT_CLEAR(TIMER_mask, BIT_TIMER_4HZ);
readCLT();
readIAT();
readO2();
@ -869,9 +860,10 @@ void loop()
vvtControl();
idleControl(); //Perform any idle related actions. Even at higher frequencies, running 4x per second is sufficient.
}
if ((mainLoopCount & 1023) == 1) //Every 1024 loops (Approx. 1 per second)
if (BIT_CHECK(LOOP_TIMER, BIT_TIMER_1HZ)) //Every 1024 loops (Approx. 1 per second)
{
//Approx. once per second
BIT_CLEAR(TIMER_mask, BIT_TIMER_1HZ);
readBaro();
}

View File

@ -409,82 +409,103 @@ int get3DTableValue(struct table3D *fromTable, int Y_in, int X_in)
return tableResult;
}
/* Executed a benchmark on all options and this is the results
* Stadard:226224 91 |FP Math:32240 91.89 |Clean code:34056 91, Number of loops:2500
*
* @Mega: Stadard:464276 92 |FP Math:893104 92.57 |Clean code:641280 92 , Number of loops:5000
* @STM32F1: Stadard:21449 92 |FP Math:125707 92.57 |Clean code:11634 92 , Number of loops:5000
* @STM32F4: Stadard:7275 92 |FP Math:5724 92.57 |Clean code:4742 92 , Number of loops:5000
//This function pulls a value from a 3D table given a target for X and Y coordinates.
//It performs a 2D linear interpolation as descibred in: http://www.megamanual.com/v22manual/ve_tuner.pdf
float get3DTableValueF(struct table3D *fromTable, int Y, int X)
{
float m, n, o ,p, q, r;
byte xMin, xMax;
byte yMin, yMax;
int yMaxValue, yMinValue;
int xMaxValue, xMinValue;
float tableResult = 0;
if(fromTable->lastXMin==0) {fromTable->lastXMin = fromTable->xSize-1;}
else {xMin = fromTable->lastXMin;}
if(fromTable->lastYMin==0) {fromTable->lastYMin = fromTable->ySize-1;}
else {yMin = fromTable->lastYMin;}
//yMin = fromTable->lastYMin;
if(xMin>fromTable->xSize-1)
{
fromTable->lastXMin = fromTable->xSize-1;
xMin = fromTable->xSize-1;
}
if(yMin>fromTable->ySize-1)
{
fromTable->lastYMin = fromTable->ySize-1;
yMin = fromTable->ySize-1;
}
xMin = fromTable->lastXMin;
yMin = fromTable->lastYMin;
if(xMin == 0) { xMin = fromTable->xSize-1; }
if(yMin == 0) { yMin = fromTable->ySize-1; }
do //RPM axis
{
if(X>=fromTable->axisX[xMin]) {break;}
if(X == fromTable->axisX[xMin])
{
xMax = xMin;
break;
}
else if(X > fromTable->axisX[xMin])
{
if (xMin == fromTable->xSize-1) { xMax = xMin; } //Overflow protection
else { xMax = xMin + 1; }
break;
}
xMin--;
}while(1);
fromTable->lastXMin = xMin + 1;
}while(true);
do //MAP axis
{
if(Y<=fromTable->axisY[yMin]) {break;}
if(Y == fromTable->axisY[yMin])
{
yMax = yMin;
break;
}
else if(Y < fromTable->axisY[yMin])
{
if (yMin == fromTable->ySize-1) { yMax = yMin; } //Overflow protection
else { yMax = yMin + 1; }
break;
}
yMin--;
}while(1);
fromTable->lastYMin = yMin + 1;
}while(true);
xMax = xMin + 1;
yMax = yMin + 1;
if (xMax>fromTable->xSize-1) //Overflow protection
{
xMax = fromTable->xSize-1;
xMin = xMax - 1;
}
if (yMax>fromTable->ySize-1) //Overflow protection
{
yMax = fromTable->ySize-1;
yMin = yMax - 1;
}
yMaxValue = fromTable->axisY[yMax];
yMinValue = fromTable->axisY[yMin];
xMaxValue = fromTable->axisX[xMax];
xMinValue = fromTable->axisX[xMin];
fromTable->lastXMin = xMax;
fromTable->lastYMin = yMax;
int A = fromTable->values[yMin][xMin];
int B = fromTable->values[yMin][xMax];
int C = fromTable->values[yMax][xMin];
int D = fromTable->values[yMax][xMax];
if( (A == B) && (A == C) && (A == D) ) { tableResult = A; }
else if(xMin == xMax) // Same RPM axys do a simple 2D (27% faster on Mega on worst case, up to 500%)
{
int yMaxValue = fromTable->axisY[yMax];
int yMinValue = fromTable->axisY[yMin];
float q;
q = ((float)(Y - yMinValue) * (C - A)) / (yMaxValue - yMinValue);
tableResult = A + q;
}
else if(yMin == yMax) // Same MAP axys do a simple 2D (27% faster on Mega on worst case, up to 500%)
{
int xMaxValue = fromTable->axisX[xMax];
int xMinValue = fromTable->axisX[xMin];
float q;
q = ((float)(X - xMinValue) * (B - A)) / (xMaxValue - xMinValue);
tableResult = A + q;
}
else
{
int yMaxValue = fromTable->axisY[yMax];
int yMinValue = fromTable->axisY[yMin];
int xMaxValue = fromTable->axisX[xMax];
int xMinValue = fromTable->axisX[xMin];
float m, n, o , p, q, r;
if (xMaxValue == xMinValue) { p = (float)X - xMinValue; }
else { p = ((float)X - xMinValue) / (xMaxValue - xMinValue); }
if (yMaxValue == yMinValue) { q = (float)Y - yMinValue; }
else { q = ((float)Y - yMinValue) / (yMaxValue - yMinValue); }
p = float(X - xMinValue) / (xMaxValue - xMinValue); //(RPM - RPM[1])/(RPM[2]- RPM[1])
q = float(Y - yMinValue) / (yMaxValue - yMinValue); //(MAP - MAP[1])/(MAP[2]- MAP[1])
m = (1.0-p) * (1.0-q);
n = p * (1-q);
o = (1-p) * q;
r = p * q;
return ( (A * m) + (B * n) + (C * o) + (D * r) );
m = (1.0-p) * (1.0-q);
n = p * (1-q);
o = (1-p) * q;
r = p * q;
tableResult = ( (A * m) + (B * n) + (C * o) + (D * r) );
}
return tableResult;
}
*/
//This function pulls a value from a 3D table given a target for X and Y coordinates.
//It performs a 2D linear interpolation as descibred in: http://www.megamanual.com/v22manual/ve_tuner.pdf
int get3DTableValueS(struct table3D *fromTable, int Y, int X)
{
byte xMin, xMax;
@ -498,68 +519,62 @@ int get3DTableValueS(struct table3D *fromTable, int Y, int X)
do //RPM axis
{
if(X > fromTable->axisX[xMin])
{
if (xMin == (fromTable->xSize-1) ) { xMax = xMin; } //Overflow protection
else { xMax = xMin + 1; }
break;
}
else if(X == fromTable->axisX[xMin])
if(X == fromTable->axisX[xMin])
{
xMax = xMin;
break;
}
else if(X > fromTable->axisX[xMin])
{
if (xMin == fromTable->xSize-1) { xMax = xMin; } //Overflow protection
else { xMax = xMin + 1; }
break;
}
xMin--;
}while(true);
do //MAP axis
{
if(Y < fromTable->axisY[yMin])
{
if (yMin == (fromTable->ySize-1) ) { yMax = yMin; } //Overflow protection
else { yMax = yMin + 1; }
break;
}
else if(Y == fromTable->axisY[yMin])
if(Y == fromTable->axisY[yMin])
{
yMax = yMin;
break;
}
else if(Y < fromTable->axisY[yMin])
{
if (yMin == fromTable->ySize-1) { yMax = yMin; } //Overflow protection
else { yMax = yMin + 1; }
break;
}
yMin--;
}while(true);
fromTable->lastXMin = xMax;
fromTable->lastYMin = yMax;
//Serial.print("xMin, xMax ");Serial.print(xMin);Serial.print(",");Serial.println(xMax);
//Serial.print("yMin, yMax ");Serial.print(yMin);Serial.print(",");Serial.println(yMax);
int A = fromTable->values[yMin][xMin];
if((xMin == xMax) && (yMin == yMax)) { tableResult = A; }
else if(xMin == xMax) // Simple 2D
int B = fromTable->values[yMin][xMax];
int C = fromTable->values[yMax][xMin];
int D = fromTable->values[yMax][xMax];
if( (A == B) && (A == C) && (A == D) ) { tableResult = A; }
else if(xMin == xMax) // Same RPM axys do a simple 2D (27% faster on Mega on worst case, up to 500%)
{
int D = fromTable->values[yMax][xMax];
int yMaxValue = fromTable->axisY[yMax];
int yMinValue = fromTable->axisY[yMin];
long q = (long)Y - yMinValue;
q = ((q << 6) * (D - A)) / (yMaxValue - yMinValue);
long q;
q = (((long)(Y - yMinValue) << 6) * (C - A)) / (yMaxValue - yMinValue);
tableResult = A + (q >> 6);
}
else if(yMin == yMax) // Simple 2D
else if(yMin == yMax) // Same MAP axys do a simple 2D (27% faster on Mega on worst case, up to 500%)
{
int D = fromTable->values[yMax][xMax];
int xMaxValue = fromTable->axisX[xMax];
int xMinValue = fromTable->axisX[xMin];
long q = (long)X - xMinValue;
q = ((q << 6) * (D - A)) / (xMaxValue - xMinValue);
long q;
q = (((long)(X - xMinValue) << 6) * (B - A)) / (xMaxValue - xMinValue);
tableResult = A + (q >> 6);
}
else
{
int B = fromTable->values[yMin][xMax];
int C = fromTable->values[yMax][xMin];
int D = fromTable->values[yMax][xMax];
int yMaxValue = fromTable->axisY[yMax];
int yMinValue = fromTable->axisY[yMin];
int xMaxValue = fromTable->axisX[xMax];
@ -575,6 +590,7 @@ int get3DTableValueS(struct table3D *fromTable, int Y, int X)
q = (long)Y - yMinValue;
q = (q << 8);
}
//Standard case
else
{
q = long(Y) - yMaxValue;
@ -586,6 +602,7 @@ int get3DTableValueS(struct table3D *fromTable, int Y, int X)
int o = ((256-p) * q) >> 8;
int r = (p * q) >> 8;
tableResult = ( (A * m) + (B * n) + (C * o) + (D * r) ) >> 8;
}
}
return tableResult;
}
*/

View File

@ -19,8 +19,10 @@ Hence we will preload the timer with 131 cycles to leave 125 until overflow (1ms
#ifndef TIMERS_H
#define TIMERS_H
volatile int loop100ms;
volatile int loop250ms;
volatile byte loop33ms;
volatile byte loop66ms;
volatile byte loop100ms;
volatile byte loop250ms;
volatile int loopSec;
volatile unsigned int dwellLimit_uS;

View File

@ -42,8 +42,9 @@ void initialiseTimers()
#elif defined(CORE_STM32)
Timer4.setPeriod(1000); // Set up period
// Set up an interrupt
Timer4.setMode(TIMER_CH1, TIMER_OUTPUT_COMPARE);
Timer4.setMode(1, TIMER_OUTPUT_COMPARE);
Timer4.attachInterrupt(1, oneMSInterval);
Timer4.resume(); //Start Timer
#endif
dwellLimit_uS = (1000 * configPage2.dwellLimit);
@ -61,6 +62,8 @@ void oneMSInterval() //Most ARM chips can simply call a function
{
//Increment Loop Counters
loop33ms++;
loop66ms++;
loop100ms++;
loop250ms++;
loopSec++;
@ -78,11 +81,29 @@ void oneMSInterval() //Most ARM chips can simply call a function
if(ignitionSchedule4.Status == RUNNING) { if( (ignitionSchedule4.startTime < targetOverdwellTime) && (configPage2.useDwellLim) && (isCrankLocked != true) ) { endCoil4Charge(); } }
if(ignitionSchedule5.Status == RUNNING) { if( (ignitionSchedule5.startTime < targetOverdwellTime) && (configPage2.useDwellLim) && (isCrankLocked != true) ) { endCoil5Charge(); } }
//15Hz loop
if (loop66ms == 66)
{
loop66ms = 0;
BIT_SET(TIMER_mask, BIT_TIMER_15HZ);
}
//30Hz loop
if (loop33ms == 33)
{
loop33ms = 0;
BIT_SET(TIMER_mask, BIT_TIMER_30HZ);
}
//Loop executed every 100ms loop
//Anything inside this if statement will run every 100ms.
if (loop100ms == 100)
{
loop100ms = 0; //Reset counter
BIT_SET(TIMER_mask, BIT_TIMER_10HZ);
#if defined(CORE_STM32) //debug purpose, only visal for running code
digitalWrite(LED_BUILTIN, !digitalRead(LED_BUILTIN));
#endif
currentStatus.rpmDOT = (currentStatus.RPM - lastRPM_100ms) * 10; //This is the RPM per second that the engine has accelerated/decelleratedin the last loop
lastRPM_100ms = currentStatus.RPM; //Record the current RPM for next calc
@ -93,6 +114,7 @@ void oneMSInterval() //Most ARM chips can simply call a function
if (loop250ms == 250)
{
loop250ms = 0; //Reset Counter
BIT_SET(TIMER_mask, BIT_TIMER_4HZ);
#if defined(CORE_AVR)
//Reset watchdog timer (Not active currently)
@ -107,6 +129,7 @@ void oneMSInterval() //Most ARM chips can simply call a function
if (loopSec == 1000)
{
loopSec = 0; //Reset counter.
BIT_SET(TIMER_mask, BIT_TIMER_1HZ);
dwellLimit_uS = (1000 * configPage2.dwellLimit); //Update uS value incase setting has changed
currentStatus.crankRPM = ((unsigned int)configPage2.crankRPM * 100);

View File

@ -12,4 +12,45 @@ unsigned int PW();
unsigned int PW_SD();
unsigned int PW_AN();
//This is dumb, but it'll do for now to get things compiling
#if defined(CORE_STM32)
//STM32F1/variants/.../board.cpp
#if defined (STM32F4)
#define A0 PA0
#define A1 PA1
#define A2 PA2
#define A3 PA3
#define A4 PA4
#define A5 PA5
#define A6 PA6
#define A7 PA7
#define A8 PB0
#define A9 PB1
#define A10 PC0
#define A11 PC1
#define A12 PC2
#define A13 PC3
#define A14 PC4
#define A15 PC5
#else
#define A0 PB0
#define A1 PA7
#define A2 PA6
#define A3 PA5
#define A4 PA4
#define A5 PA3
#define A6 PA2
#define A7 PA1
#define A8 PA0
//STM32F1 have only 9 12bit adc
#define A9 PB0
#define A10 PA7
#define A11 PA6
#define A12 PA5
#define A13 PA4
#define A14 PA3
#define A15 PA2
#endif
#endif
#endif // UTILS_H

View File

@ -42,28 +42,6 @@ uint16_t freeRam ()
void setPinMapping(byte boardID)
{
//This is dumb, but it'll do for now to get things compiling
#if defined(CORE_STM32)
//STM32F1/variants/.../board.cpp
#define A0 boardADCPins[0]
#define A1 boardADCPins[1]
#define A2 boardADCPins[2]
#define A3 boardADCPins[3]
#define A4 boardADCPins[4]
#define A5 boardADCPins[5]
#define A6 boardADCPins[6]
#define A7 boardADCPins[7]
#define A8 boardADCPins[8]
#define A9 boardADCPins[9]
//STM32F1 have only 9 12bit adc
#define A10 boardADCPins[0]
#define A11 boardADCPins[1]
#define A12 boardADCPins[2]
#define A13 boardADCPins[3]
#define A14 boardADCPins[4]
#define A15 boardADCPins[5]
#endif
switch (boardID)
{
case 0:
@ -168,35 +146,6 @@ void setPinMapping(byte boardID)
pinCoil4 = 21;
pinCoil3 = 30;
pinO2 = A22;
#elif defined(CORE_STM32)
//http://docs.leaflabs.com/static.leaflabs.com/pub/leaflabs/maple-docs/0.0.12/hardware/maple-mini.html#master-pin-map
//pins 23, 24 and 33 couldn't be used
pinInjector1 = 15; //Output pin injector 1 is on
pinInjector2 = 16; //Output pin injector 2 is on
pinInjector3 = 17; //Output pin injector 3 is on
pinInjector4 = 18; //Output pin injector 4 is on
pinCoil1 = 19; //Pin for coil 1
pinCoil2 = 20; //Pin for coil 2
pinCoil3 = 21; //Pin for coil 3
pinCoil4 = 26; //Pin for coil 4
pinCoil5 = 27; //Pin for coil 5
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
pinBat = A5; //Battery reference voltage pin
pinStepperDir = 12; //Direction pin for DRV8825 driver
pinStepperStep = 13; //Step pin for DRV8825 driver
pinStepperEnable = 14; //Enable pin for DRV8825
pinDisplayReset = 2; // OLED reset pin
pinFan = 1; //Pin for the fan output
pinFuelPump = 0; //Fuel pump output
pinTachOut = 31; //Tacho output pin
//external interrupt enabled pins
pinFlex = 32; // Flex sensor (Must be external interrupt enabled)
pinTrigger = 25; //The CAS pin
pinTrigger2 = 22; //The Cam Sensor pin
#endif
break;
@ -245,6 +194,37 @@ void setPinMapping(byte boardID)
pinCoil4 = 29;
pinCoil3 = 30;
pinO2 = A22;
#elif defined(STM32F4)
pinInjector1 = PE7; //Output pin injector 1 is on
pinInjector2 = PE8; //Output pin injector 2 is on
pinInjector3 = PE9; //Output pin injector 3 is on
pinInjector4 = PE10; //Output pin injector 4 is on
pinInjector5 = PE11; //Output pin injector 5 is on
pinCoil1 = PB10; //Pin for coil 1
pinCoil2 = PB11; //Pin for coil 2
pinCoil3 = PB12; //Pin for coil 3
pinCoil4 = PB13; //Pin for coil 4
pinCoil5 = PB14; //Pin for coil 5
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
pinBat = A5; //Battery reference voltage pin
pinBaro = A6;
pinStepperDir = PD8; //Direction pin for DRV8825 driver
pinStepperStep = PB15; //Step pin for DRV8825 driver
pinStepperEnable = PD9; //Enable pin for DRV8825
pinDisplayReset = PE1; // OLED reset pin
pinFan = PE2; //Pin for the fan output
pinFuelPump = PA6; //Fuel pump output
pinTachOut = PA7; //Tacho output pin
//external interrupt enabled pins
pinFlex = PC4; // Flex sensor (Must be external interrupt enabled)
pinTrigger = PC5; //The CAS pin
pinTrigger2 = PC6; //The Cam Sensor pin
pinBoost = PE0; //Boost control
pinVVT_1 = PE1; //Default VVT output
#elif defined(CORE_STM32)
//http://docs.leaflabs.com/static.leaflabs.com/pub/leaflabs/maple-docs/0.0.12/hardware/maple-mini.html#master-pin-map
//pins 23, 24 and 33 couldn't be used
@ -274,6 +254,9 @@ void setPinMapping(byte boardID)
pinFlex = 32; // Flex sensor (Must be external interrupt enabled)
pinTrigger = 25; //The CAS pin
pinTrigger2 = 22; //The Cam Sensor pin
pinBaro = pinMAP;
pinBoost = 1; //Boost control
pinVVT_1 = 0; //Default VVT output
#endif
break;
@ -456,7 +439,7 @@ void setPinMapping(byte boardID)
if ( (configPage4.fanPin != 0) && (configPage4.fanPin < BOARD_NR_GPIO_PINS) ) { pinFan = configPage4.fanPin; }
if ( (configPage3.boostPin != 0) && (configPage3.boostPin < BOARD_NR_GPIO_PINS) ) { pinBoost = configPage3.boostPin; }
if ( (configPage3.vvtPin != 0) && (configPage3.vvtPin < BOARD_NR_GPIO_PINS) ) { pinVVT_1 = configPage3.vvtPin; }
if ( (configPage3.useExtBaro != 0) ) { pinBaro = configPage3.baroPin + A0; }
if ( (configPage3.useExtBaro != 0) && (configPage3.baroPin < BOARD_NR_GPIO_PINS) ) { pinBaro = configPage3.baroPin + A0; }
//Finally, set the relevant pin modes for outputs
pinMode(pinCoil1, OUTPUT);
@ -508,25 +491,28 @@ void setPinMapping(byte boardID)
pump_pin_port = portOutputRegister(digitalPinToPort(pinFuelPump));
pump_pin_mask = digitalPinToBitMask(pinFuelPump);
//And for inputs
//And for inputs
#if defined(CORE_STM32)
pinMode(pinMAP, INPUT_ANALOG);
pinMode(pinO2, INPUT_ANALOG);
pinMode(pinO2_2, INPUT_ANALOG);
pinMode(pinTPS, INPUT_ANALOG);
pinMode(pinIAT, INPUT_ANALOG);
pinMode(pinCLT, INPUT_ANALOG);
pinMode(pinBat, INPUT_ANALOG);
pinMode(pinBaro, INPUT_ANALOG);
#else
pinMode(pinMAP, INPUT);
pinMode(pinO2, INPUT);
pinMode(pinO2_2, INPUT);
pinMode(pinTPS, INPUT);
pinMode(pinIAT, INPUT);
pinMode(pinCLT, INPUT);
pinMode(pinBat, INPUT);
pinMode(pinBaro, INPUT);
#ifndef ARDUINO_ARCH_STM32 //libmaple core aka STM32DUINO
pinMode(pinMAP, INPUT_ANALOG);
pinMode(pinO2, INPUT_ANALOG);
pinMode(pinO2_2, INPUT_ANALOG);
pinMode(pinTPS, INPUT_ANALOG);
pinMode(pinIAT, INPUT_ANALOG);
pinMode(pinCLT, INPUT_ANALOG);
pinMode(pinBat, INPUT_ANALOG);
pinMode(pinBaro, INPUT_ANALOG);
#else
pinMode(pinMAP, INPUT);
pinMode(pinO2, INPUT);
pinMode(pinO2_2, INPUT);
pinMode(pinTPS, INPUT);
pinMode(pinIAT, INPUT);
pinMode(pinCLT, INPUT);
pinMode(pinBat, INPUT);
pinMode(pinBaro, INPUT);
#endif
#endif
pinMode(pinTrigger, INPUT);
pinMode(pinTrigger2, INPUT);