From 2351096c2190f5e280b594d5581c71956c734495 Mon Sep 17 00:00:00 2001 From: Fabiano Frizzo Date: Mon, 30 Oct 2023 11:31:44 -0300 Subject: [PATCH] Update routine that send AC request to active eFan deactivation --- src/main.cpp | 141 ++++++++++++++++++++++++++++++++------------------- src/main.h | 5 +- 2 files changed, 94 insertions(+), 52 deletions(-) diff --git a/src/main.cpp b/src/main.cpp index 6fa14d3..9b77667 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -1,16 +1,20 @@ #include "main.h" -const byte FAN_STAGE_TO_HEX[16] = {0x0, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x70, 0x80, 0x90, 0xA0, 0xB0, 0xC0, 0xD0, 0xE0, 0xF0}; +const byte LED_ON_STATE = LOW; +const byte LED_OFF_STATE = HIGH; +const byte FAN_STAGE_TO_HEX[16] = {0x00, 0x10, 0x20, 0x30, 0x40, 0x50, 0x60, 0x70, 0x80, 0x90, 0xA0, 0xB0, 0xC0, 0xD0, 0xE0, 0xF0}; STM32_CAN Can1(CAN1, DEF); CAN_message_t canMsgRx; CAN_message_t canMsgTx; +unsigned long previousCanReadMillis = 0; unsigned long previousCanICLMillis = 0; -bool engineIsRunning = true; +bool engineIsRunning = false; int previousACStatus = LOW; +int acSignalRequest = 0; void setup() { initialize(); @@ -35,34 +39,47 @@ void initialize() { pinMode(EXTERNAL_TEMPERATURE_SENSOR, INPUT_ANALOG); + pinMode(LED_BUILTIN, OUTPUT); + digitalWrite(LED_BUILTIN, LED_OFF_STATE); + Can1.begin(); Can1.setBaudRate(500000); } void processCan(long currentMillis) { - // if (Can1.read(canMsgRx)) { - // switch (canMsgRx.id) { - // case DME2: - // processCanReadDME2(canMsgRx); - // break; - // } - // } - + processCanRead(currentMillis); processCanWriteICL(currentMillis); } +void processCanRead(long currentMillis) { + if ((currentMillis - previousCanReadMillis) < CAN_READ_INTERVAL) { + return; + } + + if (Can1.read(canMsgRx)) { + char idHex[3] = ""; + int canMsgId = atoi(itoa(canMsgRx.id, idHex, 16)); + switch (canMsgId) { + case DME2: + processCanReadDME2(canMsgRx); + break; + } + } + + previousCanReadMillis = currentMillis; +} + void processCanReadDME2(CAN_message_t msg) { byte byte3 = msg.buf[3]; - engineIsRunning = bitRead(byte3, 3) == 1; - Serial.printf("Engine is running %s\n", engineIsRunning); + engineIsRunning = bitRead(byte3, 3) == HIGH; + digitalWrite(LED_BUILTIN, engineIsRunning ? LED_ON_STATE : LED_OFF_STATE); } void processCanWriteICL(long currentMillis) { - if ((currentMillis - previousCanICLMillis) < CAN_INTERVAL) { + if ((currentMillis - previousCanICLMillis) < CAN_ICL_WRITE_INTERVAL) { return; } - Serial.println("Processing ICL CAN Messages..."); processCanWriteICL2(); processCanWriteICL3(); previousCanICLMillis = currentMillis; @@ -83,43 +100,66 @@ void processCanWriteICL2() { } void processCanWriteICL3() { - int acStatus = digitalRead(AC_INPUT); - Serial.printf("AC status is: %s\n", acStatus == 1 ? "on" : "off"); + int currentACStatusRequest = digitalRead(AC_INPUT); + Serial.printf("AC status is: %s\n", currentACStatusRequest == HIGH ? "on" : "off"); canMsgTx.id = CAN_ICL3; canMsgTx.len = 8; - if (engineIsRunning) { - if (acStatus != previousACStatus) { - // E46 sends a signal of ac requesting before sending the actual request for compressor activation - // this is valid for both states on/off - canMsgTx.buf[0] = 0x80; - canMsgTx.buf[1] = calculateFanStage(previousACStatus); - } else { - switch (acStatus) { - case HIGH: - canMsgTx.buf[0] = 0xD9; // E36 AC Compressor does not have variable control - break; - default: // OFF - canMsgTx.buf[0] = 0x00; - break; - } - - canMsgTx.buf[1] = calculateFanStage(acStatus); - } - - previousACStatus = acStatus; - } else { - canMsgTx.buf[0] = 0x00; - canMsgTx.buf[1] = 0x00; - } - canMsgTx.buf[2] = 0x00; canMsgTx.buf[3] = readTemperatureSensor(); canMsgTx.buf[4] = 0x00; canMsgTx.buf[5] = 0x00; canMsgTx.buf[6] = 0x00; canMsgTx.buf[7] = 0x00; + + if (!engineIsRunning) { + canMsgTx.buf[0] = 0x00; + canMsgTx.buf[1] = 0x00; + Can1.write(canMsgTx); + return; + } + + if (currentACStatusRequest != previousACStatus) { + byte fanStage = FAN_STAGE_TO_HEX[0]; + + switch (currentACStatusRequest) { + case HIGH: + if (acSignalRequest > 1) { + previousACStatus = currentACStatusRequest; + } + break; + default: // OFF + if (acSignalRequest > 3) { + previousACStatus = currentACStatusRequest; + } + + if (acSignalRequest <= 1) { + canMsgTx.buf[1] = calculateFanStage(HIGH); + } + break; + } + + acSignalRequest++; + // E46 sends a signal of ac requesting before sending the actual request for compressor state change + // this is valid for both states on/off + canMsgTx.buf[0] = 0x80; + canMsgTx.buf[1] = fanStage; + Can1.write(canMsgTx); + return; + } + + acSignalRequest = 0; + switch (currentACStatusRequest) { + case HIGH: + canMsgTx.buf[0] = 0xD2; // Torque request for ac activation + break; + default: // OFF + canMsgTx.buf[0] = 0x00; + break; + } + + canMsgTx.buf[1] = calculateFanStage(currentACStatusRequest); Can1.write(canMsgTx); } @@ -167,13 +207,14 @@ byte calculateFanStateWithPressureSensor(int acStatus) { byte calculateFanStageWithPressureSwitch(int acStatus) { int stage = 0; if (acStatus == HIGH) { - // Pressure switch works with ground to provide a signal for second stage relay - bool pressureIsHigh = digitalRead(AC_PRESSURE_SWITCH_HIGH) == LOW; - if (pressureIsHigh) { - stage = FAN_STAGE_AT_HIGH_PRESSURE; - } else { - // If AC is ON eFan should run at the FAN_STAGE_LOW_PRESSURE - stage = FAN_STAGE_AT_LOW_PRESSURE; + switch (digitalRead(AC_PRESSURE_SWITCH_HIGH)) { + case LOW: // Pressure switch works with ground to provide a signal for second stage relay + stage = FAN_STAGE_AT_HIGH_PRESSURE; + break; + default: + // If AC is ON eFan should run at the FAN_STAGE_LOW_PRESSURE + stage = FAN_STAGE_AT_LOW_PRESSURE; + break; } } @@ -183,7 +224,5 @@ byte calculateFanStageWithPressureSwitch(int acStatus) { byte readTemperatureSensor() { long tempSensor = analogRead(EXTERNAL_TEMPERATURE_SENSOR); - Serial.printf("External temperature sensor %d\n", tempSensor); - - return 0x1E; // Temperature Fixed in 30C + return 0x1B; // Temperature Fixed in 27C } diff --git a/src/main.h b/src/main.h index 1b1cff5..adaf754 100644 --- a/src/main.h +++ b/src/main.h @@ -18,7 +18,8 @@ #define CAN_ICL2 0x613 #define CAN_ICL3 0x615 -#define CAN_INTERVAL 200 // milliseconds +#define CAN_READ_INTERVAL 10 // milliseconds +#define CAN_ICL_WRITE_INTERVAL 200 // milliseconds #define MIN_FAN_STAGE 1 #define MAX_FAN_STAGE 15 @@ -29,6 +30,8 @@ void initialize(); void processCan(long currentMillis); +void processCanRead(long currentMillis); + // DME2 t/index.php?title=Siemens_MS43_CAN_Bus#DME2_0x329 void processCanReadDME2(CAN_message_t msg);