diff --git a/firmware/controllers/actuators/electronic_throttle.cpp b/firmware/controllers/actuators/electronic_throttle.cpp index e5c59b75b8..962f83b7a1 100644 --- a/firmware/controllers/actuators/electronic_throttle.cpp +++ b/firmware/controllers/actuators/electronic_throttle.cpp @@ -495,6 +495,15 @@ void EtbController::update() { return; } + if (CONFIG(disableEtbWhenEngineStopped)) { + if (engine->triggerCentral.getTimeSinceTriggerEvent(getTimeNowNt()) > 1) { + // If engine is stopped and so configured, skip the ETB update entirely + // This is quieter and pulls less power than leaving it on all the time + m_motor->disable(); + return; + } + } + #if EFI_TUNER_STUDIO if (engineConfiguration->debugMode == DBG_ETB_LOGIC) { tsOutputChannels.debugFloatField1 = engine->engineState.targetFromTable; diff --git a/firmware/controllers/actuators/idle_hardware.cpp b/firmware/controllers/actuators/idle_hardware.cpp index 74c0ae171f..3d75cccd66 100644 --- a/firmware/controllers/actuators/idle_hardware.cpp +++ b/firmware/controllers/actuators/idle_hardware.cpp @@ -66,7 +66,7 @@ void applyIACposition(percent_t position DECLARE_ENGINE_PARAMETER_SUFFIX) { #endif /* EFI_UNIT_TEST */ } else { // if not spinning or running a bench test, turn off the idle valve(s) to be quieter and save power - if (engine->triggerCentral.getTimeSinceTriggerEvent(getTimeNowNt()) > 1.0f && timeToStopIdleTest == 0) { + if (!engine->triggerCentral.engineMovedRecently() && timeToStopIdleTest == 0) { idleSolenoidOpen.setSimplePwmDutyCycle(0); idleSolenoidClose.setSimplePwmDutyCycle(0); return; diff --git a/firmware/controllers/trigger/trigger_central.h b/firmware/controllers/trigger/trigger_central.h index f96399e8cc..aed9386015 100644 --- a/firmware/controllers/trigger/trigger_central.h +++ b/firmware/controllers/trigger/trigger_central.h @@ -49,6 +49,11 @@ public: return m_lastEventTimer.getElapsedSeconds(nowNt); } + bool engineMovedRecently() const { + // Trigger event some time in the past second = engine moving + return getTimeSinceTriggerEvent(getTimeNowNt()) < 1.0f; + } + TriggerNoiseFilter noiseFilter; trigger_type_e vvtTriggerType; diff --git a/firmware/integration/rusefi_config.txt b/firmware/integration/rusefi_config.txt index c55bc9e9db..bc38e75f79 100644 --- a/firmware/integration/rusefi_config.txt +++ b/firmware/integration/rusefi_config.txt @@ -831,7 +831,7 @@ bit is_enabled_spi_2 bit useIacTableForCoasting;+This setting allows the ECU to open the IAC during overrun conditions to help reduce engine breaking, this can be helpful for large engines in light weight cars. Used in Auto-PID Idle mode. bit useNoiselessTriggerDecoder bit useIdleTimingPidControl - bit unused744b25 + bit disableEtbWhenEngineStopped;+Allows disabling the ETB when the engine is stopped. You may not like the power draw or PWM noise from the motor, so this lets you turn it off until it's necessary. bit is_enabled_spi_4 bit pauseEtbControl;+Disable the electronic throttle motor and DC idle motor for testing.\nThis mode is for testing ETB/DC idle position sensors, etc without actually driving the throttle. bit alignEngineSnifferAtTDC diff --git a/firmware/tunerstudio/rusefi.input b/firmware/tunerstudio/rusefi.input index de2c448fd8..fe995c8909 100644 --- a/firmware/tunerstudio/rusefi.input +++ b/firmware/tunerstudio/rusefi.input @@ -3254,6 +3254,7 @@ cmd_set_engine_type_default = "@@TS_IO_TEST_COMMAND_char@@\x00\x31\x00\x00" dialog = etbDialogLeft field = "https://rusefi.com/s/etb" field = "Detailed status in console", isVerboseETB + field = "Disable ETB if engine is stopped", disableEtbWhenEngineStopped field = "Disable ETB Motor", pauseEtbControl field = "H-Bridge #1 function", etbFunctions1 field = "H-Bridge #2 function", etbFunctions2