diff --git a/README.md b/README.md
index b5b708f..0df5071 100644
--- a/README.md
+++ b/README.md
@@ -1,6 +1,6 @@
## grblHAL ##
-Latest build date is 20250206, see the [changelog](changelog.md) for details.
+Latest build date is 20250216, see the [changelog](changelog.md) for details.
> [!NOTE]
> A settings reset will be performed on an update of builds prior to 20241208. Backup and restore of settings is recommended.
@@ -89,4 +89,4 @@ G/M-codes not supported by [legacy Grbl](https://github.com/gnea/grbl/wiki) are
Some [plugins](https://github.com/grblHAL/plugins) implements additional M-codes.
---
-20250208
+20250216
diff --git a/changelog.md b/changelog.md
index a49e50c..97e46f2 100644
--- a/changelog.md
+++ b/changelog.md
@@ -1,5 +1,21 @@
## grblHAL changelog
+20250216
+
+Core:
+
+* Fixed issue with restoring spindle status for spindles making use optional spindle status flags. Ref. PR [#673](https://github.com/grblHAL/core/pull/673);
+
+Drivers:
+
+* ESP32: added OpenPNP plugin.
+
+Plugins:
+
+* Networking: added/updated mutexes to Websocket and Telnet daemons for FreeRTOS enabled drivers. Ref. PR [#13](https://github.com/grblHAL/Plugin_networking/pull/13).
+
+---
+
20250213
Drivers:
diff --git a/grbl.h b/grbl.h
index 2de9f10..90fca64 100644
--- a/grbl.h
+++ b/grbl.h
@@ -42,7 +42,7 @@
#else
#define GRBL_VERSION "1.1f"
#endif
-#define GRBL_BUILD 20250206
+#define GRBL_BUILD 20250213
#define GRBL_URL "https://github.com/grblHAL"
diff --git a/spindle_control.c b/spindle_control.c
index e99ad9e..cebab0e 100644
--- a/spindle_control.c
+++ b/spindle_control.c
@@ -553,6 +553,21 @@ void spindle_set_override (spindle_ptrs_t *spindle, override_t speed_override)
}
}
+/*! \brief Checks actual spindle state against given state.
+\param spindle pointer to a \ref spindle_ptrs_t structure.
+\param state a \ref spindle_state_t structure.
+\returns \a true if on and ccw fields are equal, \a false otherwise.
+*/
+bool spindle_check_state (spindle_ptrs_t *spindle, spindle_state_t state)
+{
+ static const spindle_state_t mask = {
+ .on = On,
+ .ccw = On
+ };
+
+ return (state.value & mask.value) == (spindle->get_state(spindle).value & mask.value);
+}
+
/*! \internal \brief Immediately sets spindle running state with direction and spindle rpm, if enabled.
Called by g-code parser spindle_set_state_synced(), parking retract and restore, g-code program end,
sleep, and spindle stop override.
@@ -595,7 +610,7 @@ for it to reach the speed and raise an alarm if the speed is not reached within
\param rpm the spindle RPM to set.
\returns \a true if successful, \a false if the current controller state is \ref ABORTED.
*/
-static bool spindle_set_state_wait (spindle_ptrs_t *spindle, spindle_state_t state, float rpm, uint16_t on_delay_ms, delaymode_t delay_mode)
+static bool spindle_set_state_wait (spindle_ptrs_t *spindle, spindle_state_t state, float rpm, uint16_t delay_ms, delaymode_t delay_mode)
{
bool ok;
@@ -606,16 +621,16 @@ static bool spindle_set_state_wait (spindle_ptrs_t *spindle, spindle_state_t sta
bool at_speed = !state.on || spindle->cap.torch || !spindle->cap.at_speed || spindle->at_speed_tolerance <= 0.0f;
if(at_speed)
- ok = on_delay_ms == 0 || spindle->cap.torch || delay_sec((float)on_delay_ms / 1000.0f, delay_mode);
+ ok = delay_ms == 0 || spindle->cap.torch || delay_sec((float)delay_ms / 1000.0f, delay_mode);
else {
uint16_t delay = 0;
- if(on_delay_ms == 0)
- on_delay_ms = 60000; // one minute...
+ if(delay_ms == 0)
+ delay_ms = 60000; // one minute...
while(!(at_speed = spindle->get_state(spindle).at_speed)) {
if(!delay_sec(0.2f, delay_mode))
break;
delay += 200;
- if(delay > on_delay_ms) {
+ if(delay > delay_ms) {
gc_spindle_off();
system_raise_alarm(Alarm_Spindle);
break;
@@ -649,14 +664,14 @@ bool spindle_set_state_synced (spindle_ptrs_t *spindle, spindle_state_t state, f
\param rpm the spindle RPM to set.
\returns \a true if successful, \a false if the current controller state is \ref ABORTED.
*/
-bool spindle_restore (spindle_ptrs_t *spindle, spindle_state_t state, float rpm, uint16_t on_delay_ms)
+bool spindle_restore (spindle_ptrs_t *spindle, spindle_state_t state, float rpm, uint16_t delay_ms)
{
bool ok;
if((ok = spindle->cap.laser)) // When in laser mode, ignore spindle spin-up delay. Set to turn on laser when cycle starts.
sys.step_control.update_spindle_rpm = On;
- else if(!(ok = state.value == spindle->get_state(spindle).value))
- ok = spindle_set_state_wait(spindle, state, rpm, on_delay_ms, DelayMode_SysSuspend);
+ else if(!(ok = spindle_check_state(spindle, state)))
+ ok = spindle_set_state_wait(spindle, state, rpm, delay_ms, DelayMode_SysSuspend);
return ok;
}
diff --git a/spindle_control.h b/spindle_control.h
index 393ecc7..2ba6880 100644
--- a/spindle_control.h
+++ b/spindle_control.h
@@ -348,6 +348,8 @@ bool spindle_set_state (spindle_ptrs_t *spindle, spindle_state_t state, float rp
// Called by g-code parser when setting spindle state and requires a buffer sync.
bool spindle_set_state_synced (spindle_ptrs_t *spindle, spindle_state_t state, float rpm);
+bool spindle_check_state (spindle_ptrs_t *spindle, spindle_state_t state);
+
// Spindle speed calculation and limit handling
float spindle_set_rpm (spindle_ptrs_t *spindle, float rpm, override_t speed_override);