rewrite MccGenericMovementControls class (single thread version)

This commit is contained in:
2026-02-27 18:02:02 +03:00
parent ba03832ce6
commit d42fa37a04

View File

@@ -14,6 +14,7 @@
#include <atomic>
#include <fstream>
#include <future>
#include <thread>
#include <type_traits>
#include "mcc_coordinate.h"
@@ -236,6 +237,8 @@ template <std::movable PARAMS_T,
MccGenericMovementControlsPolicy EXEC_POLICY = MccGenericMovementControlsPolicy::POLICY_ASYNC>
class MccGenericMovementControls
{
enum { STATE_SLEW, STATE_TRACK, STATE_IDLE } _currentState;
public:
static constexpr MccGenericMovementControlsPolicy executePolicy = EXEC_POLICY;
@@ -251,6 +254,40 @@ public:
_trackFunc(std::forward<TRACK_FUNC_T>(track_func)),
_stopFunc(std::forward<STOP_FUNC_T>(stop_func))
{
if constexpr (executePolicy == MccGenericMovementControlsPolicy::POLICY_ASYNC) {
*_doSlew = false;
*_doTrack = false;
*_stopMovementRequest = false;
_currentState = STATE_IDLE;
_fstFuture = std::async(
[&, this](std::stop_token stoken) {
while (!stoken.stop_requested()) {
if (_stopMovementRequest->load()) {
_currentState = STATE_IDLE;
_stopFunc();
}
if (_doSlew->load()) {
_currentState = STATE_SLEW;
_slewFunc(_slewAndStop->load());
_currentState = STATE_IDLE;
}
if (_doTrack->load()) {
_currentState = STATE_TRACK;
_trackFunc();
_currentState = STATE_IDLE;
}
// wait here ...
_wakeupRequest->wait(false, std::memory_order_relaxed);
_wakeupRequest->clear();
}
},
_fstStopSource.get_token());
}
}
MccGenericMovementControls(const MccGenericMovementControls&) = delete;
@@ -261,27 +298,32 @@ public:
virtual ~MccGenericMovementControls()
{
// if constexpr (executePolicy == MccGenericMovementControlsPolicy::POLICY_ASYNC) {
// // if future is valid then stop is already called
// if (!_stopFuncFuture.valid()) {
// // stopMount();
// _stopFunc();
// }
// } else {
// stopMount();
// }
if constexpr (executePolicy == MccGenericMovementControlsPolicy::POLICY_ASYNC) {
if (_slewFuncFuture.valid()) {
auto status = _slewFuncFuture.wait_for(_waitTimeout->load());
}
// if (_slewFuncFuture.valid()) {
// auto status = _slewFuncFuture.wait_for(_waitTimeout->load());
// }
if (_trackFuncFuture.valid()) {
auto status = _trackFuncFuture.wait_for(_waitTimeout->load());
}
// if (_trackFuncFuture.valid()) {
// auto status = _trackFuncFuture.wait_for(_waitTimeout->load());
// }
if (_stopFuncFuture.valid()) {
auto status = _stopFuncFuture.wait_for(_waitTimeout->load());
// if (_stopFuncFuture.valid()) {
// auto status = _stopFuncFuture.wait_for(_waitTimeout->load());
// }
*_doSlew = false;
*_doTrack = false;
// *_stopMovementRequest = false;
_fstStopSource.request_stop();
_wakeupRequest->test_and_set();
_wakeupRequest->notify_one();
std::this_thread::sleep_for(std::chrono::milliseconds(200));
if (_fstFuture.valid()) {
auto status = _fstFuture.wait_for(_waitTimeout->load());
}
}
}
@@ -291,21 +333,33 @@ public:
*_stopMovementRequest = false;
if constexpr (executePolicy == MccGenericMovementControlsPolicy::POLICY_ASYNC) {
if (_slewFuncFuture.valid()) { // already slewing
_slewFuncFuture = std::async(
std::launch::async,
[this](bool st) {
auto err = _stopFunc(); // first, stop mount
if (!err) {
return _slewFunc(st);
} else {
return err;
}
},
slew_and_stop);
} else {
_slewFuncFuture = std::async(std::launch::async, _slewFunc, slew_and_stop);
// if (_slewFuncFuture.valid()) { // already slewing
// _slewFuncFuture = std::async(
// std::launch::async,
// [this](bool st) {
// auto err = _stopFunc(); // first, stop mount
// if (!err) {
// *_stopMovementRequest = false;
// return _slewFunc(st);
// } else {
// return err;
// }
// },
// slew_and_stop);
// } else {
// _slewFuncFuture = std::async(std::launch::async, _slewFunc, slew_and_stop);
// }
if (_currentState == STATE_SLEW || _currentState == STATE_TRACK) { // first, stop mount
*_stopMovementRequest = true;
}
*_doTrack = false;
*_doSlew = true;
*_slewAndStop = slew_and_stop;
_wakeupRequest->test_and_set();
_wakeupRequest->notify_one();
return MccGenericMovementControlsErrorCode::ERROR_OK;
} else if constexpr (executePolicy == MccGenericMovementControlsPolicy::POLICY_BLOCKING) {
@@ -320,9 +374,19 @@ public:
*_stopMovementRequest = false;
if constexpr (executePolicy == MccGenericMovementControlsPolicy::POLICY_ASYNC) {
if (!_trackFuncFuture.valid()) {
_trackFuncFuture = std::async(std::launch::async, _trackFunc);
} // already tracking
// if (!_trackFuncFuture.valid()) {
// _trackFuncFuture = std::async(std::launch::async, _trackFunc);
// } // already tracking, just ignore
if (_currentState != STATE_TRACK) {
if (_currentState == STATE_SLEW) { // first, stop mount
*_stopMovementRequest = true;
}
*_doSlew = false;
*_doTrack = true;
_wakeupRequest->test_and_set();
_wakeupRequest->notify_one();
} // already tracking, just ignore
return MccGenericMovementControlsErrorCode::ERROR_OK;
} else if constexpr (executePolicy == MccGenericMovementControlsPolicy::POLICY_BLOCKING) {
@@ -338,9 +402,14 @@ public:
if constexpr (executePolicy == MccGenericMovementControlsPolicy::POLICY_ASYNC) {
// if future is valid then stop is already called
if (!_stopFuncFuture.valid()) {
_stopFuncFuture = std::async(std::launch::async, _stopFunc);
}
// if (!_stopFuncFuture.valid()) {
// _stopFuncFuture = std::async(std::launch::async, _stopFunc);
// }
*_doSlew = false;
*_doTrack = false;
_wakeupRequest->test_and_set();
_wakeupRequest->notify_one();
return MccGenericMovementControlsErrorCode::ERROR_OK;
} else if constexpr (executePolicy == MccGenericMovementControlsPolicy::POLICY_BLOCKING) {
@@ -396,6 +465,20 @@ protected:
new std::atomic<std::chrono::nanoseconds>{defaultWaitTimeout}};
std::conditional_t<executePolicy == MccGenericMovementControlsPolicy::POLICY_ASYNC,
std::future<void>,
std::nullptr_t>
_fstFuture{};
std::stop_source _fstStopSource{};
std::unique_ptr<std::atomic_flag> _wakeupRequest{new std::atomic_flag};
std::unique_ptr<std::atomic_bool> _doSlew{new std::atomic_bool{false}};
std::unique_ptr<std::atomic_bool> _doTrack{new std::atomic_bool{false}};
std::unique_ptr<std::atomic_bool> _slewAndStop{new std::atomic_bool{false}};
// utility methods
// the method calculates the change in coordinates of a point over a given time given the current speed and braking