Merge pull request #1456 from greenoem/tesla-feature-socreset

Tesla: Add SOC reset feature
This commit is contained in:
Daniel Öster 2025-08-29 19:44:19 +03:00 committed by GitHub
commit 681b915faa
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
5 changed files with 69 additions and 1 deletions

View file

@ -74,6 +74,7 @@ class Battery {
virtual bool supports_clear_isolation() { return false; }
virtual bool supports_reset_BMS() { return false; }
virtual bool supports_reset_SOC() { return false; }
virtual bool supports_reset_crash() { return false; }
virtual bool supports_reset_NVROL() { return false; }
virtual bool supports_reset_DTC() { return false; }
@ -92,6 +93,7 @@ class Battery {
virtual void clear_isolation() {}
virtual void reset_BMS() {}
virtual void reset_SOC() {}
virtual void reset_crash() {}
virtual void reset_contactor() {}
virtual void reset_NVROL() {}

View file

@ -727,10 +727,26 @@ void TeslaBattery::
#ifdef DEBUG_LOG
logging.println("ERROR: BMS reset failed due to contactors not being open, or BMS ECU not allowing it");
#endif //DEBUG_LOG
stateMachineBMSReset = 0;
stateMachineBMSReset = 0xFF;
datalayer.battery.settings.user_requests_tesla_bms_reset = false;
}
}
if (datalayer.battery.settings.user_requests_tesla_soc_reset) {
if (datalayer.battery.status.real_soc < 1500 || datalayer.battery.status.real_soc > 9000) {
//Start the SOC reset statemachine, only if SOC < 15% or > 90%
stateMachineSOCReset = 0;
datalayer.battery.settings.user_requests_tesla_soc_reset = false;
#ifdef DEBUG_LOG
logging.println("SOC reset requested");
#endif //DEBUG_LOG
} else {
#ifdef DEBUG_LOG
logging.println("ERROR: SOC reset failed due to SOC not being less than 15 or greater than 90");
#endif //DEBUG_LOG
stateMachineSOCReset = 0xFF;
datalayer.battery.settings.user_requests_tesla_soc_reset = false;
}
}
//Update 0x333 UI_chargeTerminationPct (bit 16, width 10) value to SOC max value - expose via UI?
//One firmware version this was seen at bit 17 width 11
@ -2312,6 +2328,47 @@ void TeslaBattery::transmit_can(unsigned long currentMillis) {
break;
}
}
if (stateMachineSOCReset != 0xFF) {
//This implementation should be rewritten to actually reply to the UDS responses sent by the BMS
//While this may work, it is not the correct way to implement this
switch (stateMachineSOCReset) {
case 0:
TESLA_602.data = {0x02, 0x27, 0x05, 0x00, 0x00, 0x00, 0x00, 0x00};
transmit_can_frame(&TESLA_602);
stateMachineSOCReset = 1;
break;
case 1:
TESLA_602.data = {0x30, 0x00, 0x0A, 0x00, 0x00, 0x00, 0x00, 0x00};
transmit_can_frame(&TESLA_602);
stateMachineSOCReset = 2;
break;
case 2:
TESLA_602.data = {0x10, 0x12, 0x27, 0x06, 0x35, 0x34, 0x37, 0x36};
transmit_can_frame(&TESLA_602);
stateMachineSOCReset = 3;
break;
case 3:
TESLA_602.data = {0x21, 0x31, 0x30, 0x33, 0x32, 0x3D, 0x3C, 0x3F};
transmit_can_frame(&TESLA_602);
stateMachineSOCReset = 4;
break;
case 4:
TESLA_602.data = {0x22, 0x3E, 0x39, 0x38, 0x3B, 0x3A, 0x00, 0x00};
transmit_can_frame(&TESLA_602);
//Should generate a CAN UDS log message indicating ECU unlocked
stateMachineSOCReset = 5;
break;
case 5:
TESLA_602.data = {0x04, 0x31, 0x01, 0x04, 0x07, 0x00, 0x00, 0x00};
transmit_can_frame(&TESLA_602);
stateMachineSOCReset = 0xFF;
break;
default:
//Something went wrong. Reset all and cancel
stateMachineSOCReset = 0xFF;
break;
}
}
if (stateMachineBMSQuery != 0xFF) {
//This implementation should be rewritten to actually reply to the UDS responses sent by the BMS
//While this may work, it is not the correct way to implement this query logic

View file

@ -33,6 +33,9 @@ class TeslaBattery : public CanBattery {
bool supports_reset_BMS() { return true; }
void reset_BMS() { datalayer.battery.settings.user_requests_tesla_bms_reset = true; }
bool supports_reset_SOC() { return true; }
void reset_SOC() { datalayer.battery.settings.user_requests_tesla_soc_reset = true; }
bool supports_charged_energy() { return true; }
BatteryHtmlRenderer& get_status_renderer() { return renderer; }
@ -486,6 +489,7 @@ class TeslaBattery : public CanBattery {
uint8_t stateMachineClearIsolationFault = 0xFF;
uint8_t stateMachineBMSReset = 0xFF;
uint8_t stateMachineSOCReset = 0xFF;
uint8_t stateMachineBMSQuery = 0xFF;
uint16_t sendContactorClosingMessagesStill = 300;
uint16_t battery_cell_max_v = 3300;

View file

@ -152,6 +152,7 @@ struct DATALAYER_BATTERY_SETTINGS_TYPE {
bool user_requests_balancing = false;
bool user_requests_tesla_isolation_clear = false;
bool user_requests_tesla_bms_reset = false;
bool user_requests_tesla_soc_reset = false;
/* Forced balancing max time & start timestamp */
uint32_t balancing_time_ms = 3600000; //1h default, (60min*60sec*1000ms)
uint32_t balancing_start_time_ms = 0; //For keeping track when balancing started

View file

@ -25,6 +25,10 @@ std::vector<BatteryCommand> battery_commands = {
[](Battery* b) {
b->reset_BMS();
}},
{"resetSOC", "SOC reset", "reset SOC?", [](Battery* b) { return b && b->supports_reset_SOC(); },
[](Battery* b) {
b->reset_SOC();
}},
{"resetCrash", "Unlock crashed BMS",
"reset crash data? Note this will unlock your BMS and enable contactor closing and SOC calculation.",
[](Battery* b) { return b && b->supports_reset_crash(); },