From 30cdeb0d7fae93de0d63a891aabe31a8d37990b7 Mon Sep 17 00:00:00 2001 From: Matthew Kennedy Date: Thu, 19 Mar 2020 11:01:07 -0700 Subject: [PATCH] split out can tx logic (#1197) * move to can folder * split out can rx * only print in debug mode * guard on feature flag * split out tx * headers * headers Co-authored-by: Matthew Kennedy --- firmware/controllers/can/can.h | 8 ++ firmware/controllers/can/can_dash.cpp | 143 +++++++++++++++++++++++ firmware/controllers/can/can_dash.h | 13 +++ firmware/controllers/can/can_tx.cpp | 48 ++++++++ firmware/controllers/controllers.mk | 4 +- firmware/hw_layer/drivers/can/can_hw.cpp | 125 +------------------- firmware/hw_layer/drivers/can/can_hw.h | 25 ---- 7 files changed, 216 insertions(+), 150 deletions(-) create mode 100644 firmware/controllers/can/can_dash.cpp create mode 100644 firmware/controllers/can/can_dash.h create mode 100644 firmware/controllers/can/can_tx.cpp diff --git a/firmware/controllers/can/can.h b/firmware/controllers/can/can.h index 3f9f766a0c..d49705b853 100644 --- a/firmware/controllers/can/can.h +++ b/firmware/controllers/can/can.h @@ -9,5 +9,13 @@ #include "hal.h" +#include "periodic_thread_controller.h" + class Logging; void processCanRxMessage(const CANRxFrame& msg, Logging* logger); + +class CanWrite final : public PeriodicController<256> { +public: + CanWrite(); + void PeriodicTask(efitime_t nowNt) override; +}; diff --git a/firmware/controllers/can/can_dash.cpp b/firmware/controllers/can/can_dash.cpp new file mode 100644 index 0000000000..e7ea76d26e --- /dev/null +++ b/firmware/controllers/can/can_dash.cpp @@ -0,0 +1,143 @@ +/** + * @file can_dash.cpp + * + * This file handles transmission of ECU data to various OE dashboards. + * + * @date Mar 19, 2020 + * @author Matthew Kennedy, (c) 2020 + */ + +#include "globalaccess.h" +#if EFI_CAN_SUPPORT + +#include "engine.h" +#include "can.h" +#include "can_hw.h" +#include "can_dash.h" + + +#include "allsensors.h" +#include "vehicle_speed.h" + +EXTERN_ENGINE; + +// CAN Bus ID for broadcast +/** + * e46 data is from http://forums.bimmerforums.com/forum/showthread.php?1887229 + * + * Same for Mini Cooper? http://vehicle-reverse-engineering.wikia.com/wiki/MINI + * + * All the below packets are using 500kb/s + * + */ +#define CAN_BMW_E46_SPEED 0x153 +#define CAN_BMW_E46_RPM 0x316 +#define CAN_BMW_E46_DME2 0x329 +#define CAN_BMW_E46_CLUSTER_STATUS 0x613 +#define CAN_BMW_E46_CLUSTER_STATUS_2 0x615 +#define CAN_FIAT_MOTOR_INFO 0x561 +#define CAN_MAZDA_RX_RPM_SPEED 0x201 +#define CAN_MAZDA_RX_STEERING_WARNING 0x300 +#define CAN_MAZDA_RX_STATUS_1 0x212 +#define CAN_MAZDA_RX_STATUS_2 0x420 +// https://wiki.openstreetmap.org/wiki/VW-CAN +#define CAN_VAG_RPM 0x280 +#define CAN_VAG_CLT 0x288 +#define CAN_VAG_CLT_V2 0x420 +#define CAN_VAG_IMMO 0x3D0 + +extern CANTxFrame txmsg; + +static void setShortValue(CANTxFrame *txmsg, int value, int offset) { + txmsg->data8[offset] = value; + txmsg->data8[offset + 1] = value >> 8; +} + +void canDashboardBMW(void) { + //BMW Dashboard + commonTxInit(CAN_BMW_E46_SPEED); + setShortValue(&txmsg, 10 * 8, 1); + sendCanMessage(); + + commonTxInit(CAN_BMW_E46_RPM); + setShortValue(&txmsg, (int) (GET_RPM() * 6.4), 2); + sendCanMessage(); + + commonTxInit(CAN_BMW_E46_DME2); + setShortValue(&txmsg, (int) ((getCoolantTemperature() + 48.373) / 0.75), 1); + sendCanMessage(); +} + +void canMazdaRX8(void) { + commonTxInit(CAN_MAZDA_RX_STEERING_WARNING); + // todo: something needs to be set here? see http://rusefi.com/wiki/index.php?title=Vehicle:Mazda_Rx8_2004 + sendCanMessage(); + + commonTxInit(CAN_MAZDA_RX_RPM_SPEED); + + float kph = getVehicleSpeed(); + + setShortValue(&txmsg, SWAP_UINT16(GET_RPM() * 4), 0); + setShortValue(&txmsg, 0xFFFF, 2); + setShortValue(&txmsg, SWAP_UINT16((int )(100 * kph + 10000)), 4); + setShortValue(&txmsg, 0, 6); + sendCanMessage(); + + commonTxInit(CAN_MAZDA_RX_STATUS_1); + txmsg.data8[0] = 0xFE; //Unknown + txmsg.data8[1] = 0xFE; //Unknown + txmsg.data8[2] = 0xFE; //Unknown + txmsg.data8[3] = 0x34; //DSC OFF in combo with byte 5 Live data only seen 0x34 + txmsg.data8[4] = 0x00; // B01000000; // Brake warning B00001000; //ABS warning + txmsg.data8[5] = 0x40; // TCS in combo with byte 3 + txmsg.data8[6] = 0x00; // Unknown + txmsg.data8[7] = 0x00; // Unused + sendCanMessage(); + + commonTxInit(CAN_MAZDA_RX_STATUS_2); + txmsg.data8[0] = (uint8_t)(getCoolantTemperature() + 69); //temp gauge //~170 is red, ~165 last bar, 152 centre, 90 first bar, 92 second bar + txmsg.data8[1] = ((int16_t)(engine->engineState.vssEventCounter*(engineConfiguration->vehicleSpeedCoef*0.277*2.58))) & 0xff; + txmsg.data8[2] = 0x00; // unknown + txmsg.data8[3] = 0x00; //unknown + txmsg.data8[4] = 0x01; //Oil Pressure (not really a gauge) + txmsg.data8[5] = 0x00; //check engine light + txmsg.data8[6] = 0x00; //Coolant, oil and battery + if ((GET_RPM()>0) && (engine->sensors.vBatt<13)) { + setTxBit(6, 6); // battery light + } + if (getCoolantTemperature() > 105) { + setTxBit(6, 1); // coolant light, 101 - red zone, light means its get too hot + } + //oil pressure warning lamp bit is 7 + txmsg.data8[7] = 0x00; //unused + sendCanMessage(); +} + +void canDashboardFiat(void) { + //Fiat Dashboard + commonTxInit(CAN_FIAT_MOTOR_INFO); + setShortValue(&txmsg, (int) (getCoolantTemperature() - 40), 3); //Coolant Temp + setShortValue(&txmsg, GET_RPM() / 32, 6); //RPM + sendCanMessage(); +} + +void canDashboardVAG(void) { + //VAG Dashboard + commonTxInit(CAN_VAG_RPM); + setShortValue(&txmsg, GET_RPM() * 4, 2); //RPM + sendCanMessage(); + + commonTxInit(CAN_VAG_CLT); + setShortValue(&txmsg, (int) ((getCoolantTemperature() + 48.373) / 0.75), 1); //Coolant Temp + sendCanMessage(); + + commonTxInit(CAN_VAG_CLT_V2); + setShortValue(&txmsg, (int) ((getCoolantTemperature() + 48.373) / 0.75), 4); //Coolant Temp + sendCanMessage(); + + commonTxInit(CAN_VAG_IMMO); + setShortValue(&txmsg, 0x80, 1); + sendCanMessage(); +} + +#endif // EFI_CAN_SUPPORT diff --git a/firmware/controllers/can/can_dash.h b/firmware/controllers/can/can_dash.h new file mode 100644 index 0000000000..234cf8692f --- /dev/null +++ b/firmware/controllers/can/can_dash.h @@ -0,0 +1,13 @@ +/** + * @file can_dash.h + * + * @date Mar 19, 2020 + * @author Matthew Kennedy, (c) 2020 + */ + +#pragma once + +void canDashboardBMW(); +void canDashboardFiat(); +void canDashboardVAG(); +void canMazdaRX8(); diff --git a/firmware/controllers/can/can_tx.cpp b/firmware/controllers/can/can_tx.cpp new file mode 100644 index 0000000000..a4dfac4be2 --- /dev/null +++ b/firmware/controllers/can/can_tx.cpp @@ -0,0 +1,48 @@ +/** + * @file can_tx.cpp + * + * CAN transmission handling. This file handles the dispatch of various outgoing regularly scheduled CAN message types. + * + * @date Mar 19, 2020 + * @author Matthew Kennedy, (c) 2020 + */ + +#include "globalaccess.h" +#if EFI_CAN_SUPPORT + +#include "engine.h" +#include "can.h" +#include "can_hw.h" +#include "can_dash.h" +#include "obd2.h" + +EXTERN_ENGINE; + +CanWrite::CanWrite() + : PeriodicController("CAN TX", NORMALPRIO, 50) +{ +} + +void CanWrite::PeriodicTask(efitime_t nowNt) { + UNUSED(nowNt); + + // Transmit dash data, if enabled + switch (CONFIG(canNbcType)) { + case CAN_BUS_NBC_BMW: + canDashboardBMW(); + break; + case CAN_BUS_NBC_FIAT: + canDashboardFiat(); + break; + case CAN_BUS_NBC_VAG: + canDashboardVAG(); + break; + case CAN_BUS_MAZDA_RX8: + canMazdaRX8(); + break; + default: + break; + } +} + +#endif // EFI_CAN_SUPPORT diff --git a/firmware/controllers/controllers.mk b/firmware/controllers/controllers.mk index 2ca5197ff8..b2b3bda907 100644 --- a/firmware/controllers/controllers.mk +++ b/firmware/controllers/controllers.mk @@ -36,9 +36,11 @@ CONTROLLERS_SRC_CPP = \ $(CONTROLLERS_DIR)/injector_central.cpp \ $(CONTROLLERS_DIR)/can/obd2.cpp \ $(CONTROLLERS_DIR)/can/can_rx.cpp \ + $(CONTROLLERS_DIR)/can/can_tx.cpp \ + $(CONTROLLERS_DIR)/can/can_dash.cpp \ $(CONTROLLERS_DIR)/engine_controller.cpp \ $(CONTROLLERS_DIR)/persistent_store.cpp \ - + CONTROLLERS_INC=\ $(CONTROLLERS_DIR) \ diff --git a/firmware/hw_layer/drivers/can/can_hw.cpp b/firmware/hw_layer/drivers/can/can_hw.cpp index 5f4a79defe..9133266841 100644 --- a/firmware/hw_layer/drivers/can/can_hw.cpp +++ b/firmware/hw_layer/drivers/can/can_hw.cpp @@ -15,14 +15,12 @@ #include "can.h" #include "engine_configuration.h" -#include "periodic_thread_controller.h" #include "pin_repository.h" #include "can_hw.h" #include "can_msg_tx.h" #include "string.h" #include "mpu_util.h" -#include "allsensors.h" -#include "vehicle_speed.h" +#include "engine.h" EXTERN_ENGINE ; @@ -74,11 +72,6 @@ CAN_BTR_1k0 }; CANTxFrame txmsg; -static void setShortValue(CANTxFrame *txmsg, int value, int offset) { - txmsg->data8[offset] = value; - txmsg->data8[offset + 1] = value >> 8; -} - void setTxBit(int offset, int index) { txmsg.data8[offset] = txmsg.data8[offset] | (1 << index); } @@ -112,122 +105,6 @@ void sendCanMessage(int size) { } } -static void canDashboardBMW(void) { - //BMW Dashboard - commonTxInit(CAN_BMW_E46_SPEED); - setShortValue(&txmsg, 10 * 8, 1); - sendCanMessage(); - - commonTxInit(CAN_BMW_E46_RPM); - setShortValue(&txmsg, (int) (GET_RPM() * 6.4), 2); - sendCanMessage(); - - commonTxInit(CAN_BMW_E46_DME2); - setShortValue(&txmsg, (int) ((getCoolantTemperature() + 48.373) / 0.75), 1); - sendCanMessage(); -} - -static void canMazdaRX8(void) { - commonTxInit(CAN_MAZDA_RX_STEERING_WARNING); - // todo: something needs to be set here? see http://rusefi.com/wiki/index.php?title=Vehicle:Mazda_Rx8_2004 - sendCanMessage(); - - commonTxInit(CAN_MAZDA_RX_RPM_SPEED); - - float kph = getVehicleSpeed(); - - setShortValue(&txmsg, SWAP_UINT16(GET_RPM() * 4), 0); - setShortValue(&txmsg, 0xFFFF, 2); - setShortValue(&txmsg, SWAP_UINT16((int )(100 * kph + 10000)), 4); - setShortValue(&txmsg, 0, 6); - sendCanMessage(); - - commonTxInit(CAN_MAZDA_RX_STATUS_1); - txmsg.data8[0] = 0xFE; //Unknown - txmsg.data8[1] = 0xFE; //Unknown - txmsg.data8[2] = 0xFE; //Unknown - txmsg.data8[3] = 0x34; //DSC OFF in combo with byte 5 Live data only seen 0x34 - txmsg.data8[4] = 0x00; // B01000000; // Brake warning B00001000; //ABS warning - txmsg.data8[5] = 0x40; // TCS in combo with byte 3 - txmsg.data8[6] = 0x00; // Unknown - txmsg.data8[7] = 0x00; // Unused - sendCanMessage(); - - commonTxInit(CAN_MAZDA_RX_STATUS_2); - txmsg.data8[0] = (uint8_t)(getCoolantTemperature() + 69); //temp gauge //~170 is red, ~165 last bar, 152 centre, 90 first bar, 92 second bar - txmsg.data8[1] = ((int16_t)(engine->engineState.vssEventCounter*(engineConfiguration->vehicleSpeedCoef*0.277*2.58))) & 0xff; - txmsg.data8[2] = 0x00; // unknown - txmsg.data8[3] = 0x00; //unknown - txmsg.data8[4] = 0x01; //Oil Pressure (not really a gauge) - txmsg.data8[5] = 0x00; //check engine light - txmsg.data8[6] = 0x00; //Coolant, oil and battery - if ((GET_RPM()>0) && (engine->sensors.vBatt<13)) { - setTxBit(6, 6); // battery light - } - if (getCoolantTemperature() > 105) { - setTxBit(6, 1); // coolant light, 101 - red zone, light means its get too hot - } - //oil pressure warning lamp bit is 7 - txmsg.data8[7] = 0x00; //unused - sendCanMessage(); -} - -static void canDashboardFiat(void) { - //Fiat Dashboard - commonTxInit(CAN_FIAT_MOTOR_INFO); - setShortValue(&txmsg, (int) (getCoolantTemperature() - 40), 3); //Coolant Temp - setShortValue(&txmsg, GET_RPM() / 32, 6); //RPM - sendCanMessage(); -} - -static void canDashboardVAG(void) { - //VAG Dashboard - commonTxInit(CAN_VAG_RPM); - setShortValue(&txmsg, GET_RPM() * 4, 2); //RPM - sendCanMessage(); - - commonTxInit(CAN_VAG_CLT); - setShortValue(&txmsg, (int) ((getCoolantTemperature() + 48.373) / 0.75), 1); //Coolant Temp - sendCanMessage(); - - commonTxInit(CAN_VAG_CLT_V2); - setShortValue(&txmsg, (int) ((getCoolantTemperature() + 48.373) / 0.75), 4); //Coolant Temp - sendCanMessage(); - - commonTxInit(CAN_VAG_IMMO); - setShortValue(&txmsg, 0x80, 1); - sendCanMessage(); -} - -class CanWrite final : public PeriodicController<256> { -public: - CanWrite() - : PeriodicController("CAN TX", NORMALPRIO, 50) - { - } - - void PeriodicTask(efitime_t nowNt) { - UNUSED(nowNt); - - switch (engineConfiguration->canNbcType) { - case CAN_BUS_NBC_BMW: - canDashboardBMW(); - break; - case CAN_BUS_NBC_FIAT: - canDashboardFiat(); - break; - case CAN_BUS_NBC_VAG: - canDashboardVAG(); - break; - case CAN_BUS_MAZDA_RX8: - canMazdaRX8(); - break; - default: - break; - } - } -}; - class CanRead final : public ThreadController<256> { public: CanRead() diff --git a/firmware/hw_layer/drivers/can/can_hw.h b/firmware/hw_layer/drivers/can/can_hw.h index ce4ec27bbc..e524327695 100644 --- a/firmware/hw_layer/drivers/can/can_hw.h +++ b/firmware/hw_layer/drivers/can/can_hw.h @@ -12,31 +12,6 @@ #include "tunerstudio_configuration.h" #endif /* EFI_TUNER_STUDIO */ -// CAN Bus ID for broadcast -/** - * e46 data is from http://forums.bimmerforums.com/forum/showthread.php?1887229 - * - * Same for Mini Cooper? http://vehicle-reverse-engineering.wikia.com/wiki/MINI - * - * All the below packets are using 500kb/s - * - */ -#define CAN_BMW_E46_SPEED 0x153 -#define CAN_BMW_E46_RPM 0x316 -#define CAN_BMW_E46_DME2 0x329 -#define CAN_BMW_E46_CLUSTER_STATUS 0x613 -#define CAN_BMW_E46_CLUSTER_STATUS_2 0x615 -#define CAN_FIAT_MOTOR_INFO 0x561 -#define CAN_MAZDA_RX_RPM_SPEED 0x201 -#define CAN_MAZDA_RX_STEERING_WARNING 0x300 -#define CAN_MAZDA_RX_STATUS_1 0x212 -#define CAN_MAZDA_RX_STATUS_2 0x420 -// https://wiki.openstreetmap.org/wiki/VW-CAN -#define CAN_VAG_RPM 0x280 -#define CAN_VAG_CLT 0x288 -#define CAN_VAG_CLT_V2 0x420 -#define CAN_VAG_IMMO 0x3D0 - void initCan(void); void commonTxInit(int eid); void sendCanMessage(int size = 8);