...
This commit is contained in:
parent
78e4bb182c
commit
bc300bb3de
@ -6,10 +6,47 @@ namespace asibfm700
|
|||||||
|
|
||||||
template <mcc::traits::mcc_range_of_input_char_range R>
|
template <mcc::traits::mcc_range_of_input_char_range R>
|
||||||
Asibfm700MountNetServer::Asibfm700MountNetServer(asio::io_context& ctx,
|
Asibfm700MountNetServer::Asibfm700MountNetServer(asio::io_context& ctx,
|
||||||
|
Asibfm700Mount& mount,
|
||||||
std::shared_ptr<spdlog::logger> logger,
|
std::shared_ptr<spdlog::logger> logger,
|
||||||
const R& pattern_range)
|
const R& pattern_range)
|
||||||
: _base_t(ctx, [this](std::string_view msg) { return handleMessage(msg); }, std::move(logger), pattern_range)
|
: base_t(ctx, mount, std::move(logger), pattern_range)
|
||||||
{
|
{
|
||||||
|
// to avoid possible compiler optimization (one needs to catch 'mount' strictly by reference)
|
||||||
|
auto* mount_ptr = &mount;
|
||||||
|
|
||||||
|
base_t::_handleMessageFunc = [base_hndl_func = std::move(base_t::_handleMessageFunc), mount_ptr,
|
||||||
|
this](std::string_view command) {
|
||||||
|
using mount_error_t = typename Asibfm700Mount::error_t;
|
||||||
|
std::error_code err{};
|
||||||
|
|
||||||
|
Asibfm700NetMessage input_msg;
|
||||||
|
Asibfm700NetMessage<handle_message_func_result_t> output_msg;
|
||||||
|
|
||||||
|
auto ec = parseMessage(command, input_msg);
|
||||||
|
|
||||||
|
if (ec) {
|
||||||
|
output_msg.construct(mcc::network::MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR, ec);
|
||||||
|
} else {
|
||||||
|
if (input_msg.withKey(ASIBFM700_COMMPROTO_KEYWORD_METEO_STR)) {
|
||||||
|
// what is operation type (set or get)?
|
||||||
|
if (input_msg.paramSize()) { // set operation
|
||||||
|
auto vp = input_msg.paramValue<Asibfm700CCTE::meteo_t>(0);
|
||||||
|
if (vp) {
|
||||||
|
mount_ptr->updateMeteoERFA(vp.value());
|
||||||
|
} else {
|
||||||
|
output_msg.construct(mcc::network::MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR, vp.error());
|
||||||
|
}
|
||||||
|
} else { // get operation
|
||||||
|
output_msg.construct(mcc::network::MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR,
|
||||||
|
ASIBFM700_COMMPROTO_KEYWORD_METEO_STR, mount_ptr->getStateERFA().meteo);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
output_msg = base_t::handleMessage<decltype(output_msg)>(input_msg, mount_ptr);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return output_msg.byteRepr();
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace asibfm700
|
} // namespace asibfm700
|
||||||
|
|||||||
@ -4,6 +4,7 @@
|
|||||||
#include <mcc_netserver_proto.h>
|
#include <mcc_netserver_proto.h>
|
||||||
|
|
||||||
#include "asibfm700_common.h"
|
#include "asibfm700_common.h"
|
||||||
|
#include "asibfm700_mount.h"
|
||||||
|
|
||||||
namespace asibfm700
|
namespace asibfm700
|
||||||
{
|
{
|
||||||
@ -57,11 +58,59 @@ struct Asibfm700NetMessageValidKeywords {
|
|||||||
};
|
};
|
||||||
|
|
||||||
template <mcc::traits::mcc_char_range BYTEREPR_T = std::string_view>
|
template <mcc::traits::mcc_char_range BYTEREPR_T = std::string_view>
|
||||||
class Asibfm700MountNetMessage : public mcc::network::MccNetMessage<BYTEREPR_T, Asibfm700NetMessageValidKeywords>
|
class Asibfm700NetMessage : public mcc::network::MccNetMessage<BYTEREPR_T, Asibfm700NetMessageValidKeywords>
|
||||||
{
|
{
|
||||||
protected:
|
protected:
|
||||||
using base_t = mcc::network::MccNetMessage<BYTEREPR_T, Asibfm700NetMessageValidKeywords>;
|
using base_t = mcc::network::MccNetMessage<BYTEREPR_T, Asibfm700NetMessageValidKeywords>;
|
||||||
|
|
||||||
|
class serializer_t : public base_t::DefaultSerializer
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
template <typename T, mcc::traits::mcc_output_char_range OR>
|
||||||
|
void operator()(const T& value, OR& bytes)
|
||||||
|
{
|
||||||
|
if constexpr (std::same_as<T, Asibfm700CCTE::meteo_t>) {
|
||||||
|
// serialize just like a vector
|
||||||
|
std::vector<double> meteo{value.temperature, value.humidity, value.pressure};
|
||||||
|
base_t::operator()(meteo, bytes);
|
||||||
|
} else {
|
||||||
|
base_t::operator()(value, bytes);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} _serializer;
|
||||||
|
|
||||||
|
|
||||||
|
class deserializer_t : public base_t::DefaultDeserializer
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
template <mcc::traits::mcc_input_char_range IR, typename VT>
|
||||||
|
std::error_code operator()(IR&& bytes, VT& value)
|
||||||
|
{
|
||||||
|
if constexpr (std::same_as<VT, Asibfm700CCTE::meteo_t>) {
|
||||||
|
// deserialize just like a vector
|
||||||
|
|
||||||
|
std::vector<double> v;
|
||||||
|
auto ec = base_t::operator()(std::forward<IR>(bytes), v);
|
||||||
|
if (ec) {
|
||||||
|
return ec;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (v.size() < 3) {
|
||||||
|
return std::make_error_code(std::errc::invalid_argument);
|
||||||
|
}
|
||||||
|
|
||||||
|
value.temperature = v[0];
|
||||||
|
value.humidity = v[1];
|
||||||
|
value.pressure = v[2];
|
||||||
|
|
||||||
|
return {};
|
||||||
|
} else {
|
||||||
|
return base_t::operator()(std::forward<IR>(bytes), value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} _deserializer;
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
using base_t::base_t;
|
using base_t::base_t;
|
||||||
@ -69,7 +118,7 @@ public:
|
|||||||
template <typename T>
|
template <typename T>
|
||||||
std::expected<T, std::error_code> paramValue(size_t idx)
|
std::expected<T, std::error_code> paramValue(size_t idx)
|
||||||
{
|
{
|
||||||
return paramValue<T>(idx, _defaultDeserilizer);
|
return paramValue<T>(idx, _deserializer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -78,19 +127,20 @@ public:
|
|||||||
std::error_code construct(KT&& key, PTs&&... params)
|
std::error_code construct(KT&& key, PTs&&... params)
|
||||||
requires mcc::traits::mcc_output_char_range<BYTEREPR_T>
|
requires mcc::traits::mcc_output_char_range<BYTEREPR_T>
|
||||||
{
|
{
|
||||||
return construct(_defaultSerializer, std::forward<KT>(key), std::forward<PTs>(params)...);
|
return construct(_serializer, std::forward<KT>(key), std::forward<PTs>(params)...);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
class Asibfm700MountNetServer : public mcc::network::MccGenericNetworkServer<Asibfm700Logger>
|
class Asibfm700MountNetServer : public mcc::network::MccGenericMountNetworkServer<Asibfm700Logger>
|
||||||
{
|
{
|
||||||
using _base_t = mcc::network::MccGenericNetworkServer<Asibfm700Logger>;
|
using base_t = mcc::network::MccGenericMountNetworkServer<Asibfm700Logger>;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
template <mcc::traits::mcc_range_of_input_char_range R = decltype(Asibfm700Logger::LOGGER_DEFAULT_FORMAT)>
|
template <mcc::traits::mcc_range_of_input_char_range R = decltype(Asibfm700Logger::LOGGER_DEFAULT_FORMAT)>
|
||||||
Asibfm700MountNetServer(asio::io_context& ctx,
|
Asibfm700MountNetServer(asio::io_context& ctx,
|
||||||
|
Asibfm700Mount& mount,
|
||||||
std::shared_ptr<spdlog::logger> logger,
|
std::shared_ptr<spdlog::logger> logger,
|
||||||
const R& pattern_range = Asibfm700Logger::LOGGER_DEFAULT_FORMAT);
|
const R& pattern_range = Asibfm700Logger::LOGGER_DEFAULT_FORMAT);
|
||||||
|
|
||||||
|
|||||||
@ -19,7 +19,8 @@ enum class MccGenericMountErrorCode : int {
|
|||||||
ERROR_HW_STOP,
|
ERROR_HW_STOP,
|
||||||
ERROR_HW_GETSTATE,
|
ERROR_HW_GETSTATE,
|
||||||
ERROR_SET_TARGET,
|
ERROR_SET_TARGET,
|
||||||
ERROR_MOUNT_SLEW
|
ERROR_MOUNT_SLEW,
|
||||||
|
ERROR_MOUNT_TRACK
|
||||||
};
|
};
|
||||||
|
|
||||||
enum class MccGenericFsmMountErrorCode : int { ERROR_OK, ERROR_INVALID_OPERATION, ERROR_UNKNOWN_EVENT };
|
enum class MccGenericFsmMountErrorCode : int { ERROR_OK, ERROR_INVALID_OPERATION, ERROR_UNKNOWN_EVENT };
|
||||||
@ -152,6 +153,9 @@ public:
|
|||||||
using typename SlewModelT::slewing_params_t;
|
using typename SlewModelT::slewing_params_t;
|
||||||
using typename TrackModelT::tracking_params_t;
|
using typename TrackModelT::tracking_params_t;
|
||||||
|
|
||||||
|
|
||||||
|
enum class mount_status_t : int { IDLE, INITIALIZATION, STOPPED, SLEWING, ADJUSTING, TRACKING, ERROR };
|
||||||
|
|
||||||
MccGenericMount(HardwareT hardware,
|
MccGenericMount(HardwareT hardware,
|
||||||
TelemetryT telemetry,
|
TelemetryT telemetry,
|
||||||
PZoneContT pzone_cont,
|
PZoneContT pzone_cont,
|
||||||
@ -163,8 +167,10 @@ public:
|
|||||||
PZoneContT(std::move(pzone_cont)),
|
PZoneContT(std::move(pzone_cont)),
|
||||||
SlewModelT(std::move(slew_model)),
|
SlewModelT(std::move(slew_model)),
|
||||||
TrackModelT(std::move(track_model)),
|
TrackModelT(std::move(track_model)),
|
||||||
LoggerT(std::move(logger))
|
LoggerT(std::move(logger)),
|
||||||
|
_mountStatus(new mount_status_t)
|
||||||
{
|
{
|
||||||
|
*_mountStatus = mount_status_t::IDLE;
|
||||||
}
|
}
|
||||||
|
|
||||||
MccGenericMount(MccGenericMount&&) = default;
|
MccGenericMount(MccGenericMount&&) = default;
|
||||||
@ -173,7 +179,10 @@ public:
|
|||||||
MccGenericMount& operator=(MccGenericMount&&) = default;
|
MccGenericMount& operator=(MccGenericMount&&) = default;
|
||||||
MccGenericMount& operator=(const MccGenericMount&) = delete;
|
MccGenericMount& operator=(const MccGenericMount&) = delete;
|
||||||
|
|
||||||
virtual ~MccGenericMount() = default;
|
virtual ~MccGenericMount()
|
||||||
|
{
|
||||||
|
stopMount();
|
||||||
|
};
|
||||||
|
|
||||||
error_t stopMount()
|
error_t stopMount()
|
||||||
{
|
{
|
||||||
@ -184,11 +193,15 @@ public:
|
|||||||
|
|
||||||
auto hw_err = this->hardwareStop();
|
auto hw_err = this->hardwareStop();
|
||||||
if (hw_err) {
|
if (hw_err) {
|
||||||
|
*_mountStatus = mount_status_t::ERROR;
|
||||||
|
|
||||||
return mcc_deduce_error_code(hw_err, MccGenericMountErrorCode::ERROR_HW_STOP);
|
return mcc_deduce_error_code(hw_err, MccGenericMountErrorCode::ERROR_HW_STOP);
|
||||||
}
|
}
|
||||||
|
|
||||||
logInfo("Stop command was sent");
|
logInfo("Stop command was sent");
|
||||||
|
|
||||||
|
*_mountStatus = mount_status_t::STOPPED;
|
||||||
|
|
||||||
return MccGenericMountErrorCode::ERROR_OK;
|
return MccGenericMountErrorCode::ERROR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -196,13 +209,19 @@ public:
|
|||||||
{
|
{
|
||||||
logInfo("Start generic mount initialization ...");
|
logInfo("Start generic mount initialization ...");
|
||||||
|
|
||||||
|
*_mountStatus = mount_status_t::INITIALIZATION;
|
||||||
|
|
||||||
auto hw_err = this->hardwareInit();
|
auto hw_err = this->hardwareInit();
|
||||||
if (hw_err) {
|
if (hw_err) {
|
||||||
|
*_mountStatus = mount_status_t::ERROR;
|
||||||
|
|
||||||
return mcc_deduce_error_code(hw_err, MccGenericMountErrorCode::ERROR_HW_STOP);
|
return mcc_deduce_error_code(hw_err, MccGenericMountErrorCode::ERROR_HW_STOP);
|
||||||
}
|
}
|
||||||
|
|
||||||
logInfo("Generic mount initialization was performed");
|
logInfo("Generic mount initialization was performed");
|
||||||
|
|
||||||
|
*_mountStatus = mount_status_t::IDLE;
|
||||||
|
|
||||||
return MccGenericMountErrorCode::ERROR_OK;
|
return MccGenericMountErrorCode::ERROR_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -231,17 +250,66 @@ public:
|
|||||||
// re-implements SlewModelT::slewToTarget to fetch input target coordinates from intermediate buffer
|
// re-implements SlewModelT::slewToTarget to fetch input target coordinates from intermediate buffer
|
||||||
error_t slewToTarget(bool slew_and_stop = false)
|
error_t slewToTarget(bool slew_and_stop = false)
|
||||||
{
|
{
|
||||||
|
*_mountStatus = mount_status_t::SLEWING;
|
||||||
|
|
||||||
auto err = TelemetryT::setPointingTarget(_enteredTargetCoordiniates);
|
auto err = TelemetryT::setPointingTarget(_enteredTargetCoordiniates);
|
||||||
if (err) {
|
if (err) {
|
||||||
|
*_mountStatus = mount_status_t::ERROR;
|
||||||
|
|
||||||
return mcc_deduce_error_code(err, MccGenericMountErrorCode::ERROR_SET_TARGET);
|
return mcc_deduce_error_code(err, MccGenericMountErrorCode::ERROR_SET_TARGET);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (slew_and_stop) {
|
||||||
|
*_mountStatus = mount_status_t::IDLE;
|
||||||
|
}
|
||||||
|
|
||||||
return mcc_deduce_error_code(SlewModelT::slewToTarget(slew_and_stop),
|
return mcc_deduce_error_code(SlewModelT::slewToTarget(slew_and_stop),
|
||||||
MccGenericMountErrorCode::ERROR_MOUNT_SLEW);
|
MccGenericMountErrorCode::ERROR_MOUNT_SLEW);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
error_t trackTarget()
|
||||||
|
{
|
||||||
|
auto err = TrackModelT::traclTarget();
|
||||||
|
if (err) {
|
||||||
|
*_mountStatus = mount_status_t::ERROR;
|
||||||
|
|
||||||
|
return mcc_deduce_error_code(err, MccGenericMountErrorCode::ERROR_MOUNT_TRACK);
|
||||||
|
}
|
||||||
|
|
||||||
|
*_mountStatus = mount_status_t::TRACKING;
|
||||||
|
|
||||||
|
return MccGenericMountErrorCode::ERROR_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
error_t stopSlewing()
|
||||||
|
{
|
||||||
|
*_mountStatus = mount_status_t::IDLE;
|
||||||
|
|
||||||
|
SlewModelT::stopSlewing();
|
||||||
|
|
||||||
|
return MccGenericMountErrorCode::ERROR_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
error_t stopTracking()
|
||||||
|
{
|
||||||
|
*_mountStatus = mount_status_t::IDLE;
|
||||||
|
|
||||||
|
TrackModelT::stopTracking();
|
||||||
|
|
||||||
|
return MccGenericMountErrorCode::ERROR_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
MccGenericMount::mount_status_t mountStatus() const
|
||||||
|
{
|
||||||
|
return _mountStatus.get();
|
||||||
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
MccCelestialPoint _enteredTargetCoordiniates;
|
MccCelestialPoint _enteredTargetCoordiniates{};
|
||||||
|
|
||||||
|
std::unique_ptr<std::atomic<MccGenericMount::mount_status_t>> _mountStatus;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -975,7 +975,7 @@ concept mcc_all_controls_c = mcc_position_controls_c<T> && mcc_telemetry_c<T> &&
|
|||||||
// 2) prohibited zones related methods
|
// 2) prohibited zones related methods
|
||||||
// 3) slewing and tracking, stop and init mount methods
|
// 3) slewing and tracking, stop and init mount methods
|
||||||
template <typename T>
|
template <typename T>
|
||||||
concept mcc_generic_mount_c = mcc_telemetry_c<T> && mcc_pzone_container_c<T> && requires(T t) {
|
concept mcc_generic_mount_c = mcc_telemetry_c<T> && mcc_pzone_container_c<T> && requires(T t, const T t_const) {
|
||||||
// requires mcc_error_c<typename T::error_t>;
|
// requires mcc_error_c<typename T::error_t>;
|
||||||
|
|
||||||
// slew mount to target (it is assumed that the target coordinates are determined in the telemetry data)
|
// slew mount to target (it is assumed that the target coordinates are determined in the telemetry data)
|
||||||
@ -996,6 +996,42 @@ concept mcc_generic_mount_c = mcc_telemetry_c<T> && mcc_pzone_container_c<T> &&
|
|||||||
|
|
||||||
// init mount
|
// init mount
|
||||||
{ t.initMount() };
|
{ t.initMount() };
|
||||||
|
|
||||||
|
//
|
||||||
|
// minimal set of mount status mnemonic constants
|
||||||
|
//
|
||||||
|
requires requires(typename T::mount_status_t type) {
|
||||||
|
requires std::formattable<
|
||||||
|
std::conditional_t<std::is_enum_v<typename T::mount_status_t>,
|
||||||
|
std::underlying_type_t<typename T::mount_status_t>, typename T::mount_status_t>,
|
||||||
|
char>;
|
||||||
|
|
||||||
|
[]() {
|
||||||
|
// mount initialization
|
||||||
|
static constexpr auto v1 = T::mount_status_t::INITIALIZATION;
|
||||||
|
|
||||||
|
// IDLE
|
||||||
|
static constexpr auto v2 = T::mount_status_t::IDLE;
|
||||||
|
|
||||||
|
// mount is in state after the stopMount() method invoking
|
||||||
|
static constexpr auto v3 = T::mount_status_t::STOPPED;
|
||||||
|
|
||||||
|
// mount is slewing (move to given celestial point)
|
||||||
|
static constexpr auto v4 = T::mount_status_t::SLEWING;
|
||||||
|
|
||||||
|
// mount is adjusting its position in the end of slewing
|
||||||
|
// (adjusting actual mount position to align with target celestial point at the end of slewing process)
|
||||||
|
static constexpr auto v5 = T::mount_status_t::ADJUSTING;
|
||||||
|
|
||||||
|
// mount is tracking
|
||||||
|
static constexpr auto v6 = T::mount_status_t::TRACKING;
|
||||||
|
|
||||||
|
// an error occured while mount operation
|
||||||
|
static constexpr auto v7 = T::mount_status_t::ERROR;
|
||||||
|
}();
|
||||||
|
};
|
||||||
|
|
||||||
|
{ t_const.mountStatus() } -> std::same_as<typename T::mount_status_t>;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
@ -1011,6 +1047,4 @@ concept mcc_generic_fsm_mount_c = mcc_generic_mount_c<T> && std::derived_from<T,
|
|||||||
template <typename T>
|
template <typename T>
|
||||||
concept mcc_generic_fsm_log_mount_c =
|
concept mcc_generic_fsm_log_mount_c =
|
||||||
mcc_generic_mount_c<T> && mcc_logger_c<T> && std::derived_from<T, fsm::MccFiniteStateMachine>;
|
mcc_generic_mount_c<T> && mcc_logger_c<T> && std::derived_from<T, fsm::MccFiniteStateMachine>;
|
||||||
|
|
||||||
|
|
||||||
} // namespace mcc
|
} // namespace mcc
|
||||||
|
|||||||
@ -899,154 +899,317 @@ public:
|
|||||||
MccGenericMountNetworkServer(asio::io_context& ctx, MountT& mount, LoggerCtorArgsTs&&... log_args)
|
MccGenericMountNetworkServer(asio::io_context& ctx, MountT& mount, LoggerCtorArgsTs&&... log_args)
|
||||||
: base_t(ctx, {}, std::forward<LoggerCtorArgsTs>(log_args)...)
|
: base_t(ctx, {}, std::forward<LoggerCtorArgsTs>(log_args)...)
|
||||||
{
|
{
|
||||||
base_t::_handleMessageFunc = [mount = std::move(mount), this](std::string_view command) {
|
// to avoid possible compiler optimization (one needs to catch 'mount' strictly by reference)
|
||||||
using mount_error_t = decltype(mount)::error_t;
|
auto* mount_ptr = &mount;
|
||||||
|
|
||||||
|
base_t::_handleMessageFunc = [mount_ptr, this](std::string_view command) {
|
||||||
|
using mount_error_t = typename MountT::error_t;
|
||||||
mount_error_t m_err;
|
mount_error_t m_err;
|
||||||
|
|
||||||
MccNetMessage input_msg;
|
MccNetMessage input_msg;
|
||||||
MccNetMessage<handle_message_func_result_t> output_msg;
|
MccNetMessage<handle_message_func_result_t> output_msg;
|
||||||
|
|
||||||
std::error_code err{};
|
auto ec = parseMessage(command, input_msg);
|
||||||
|
if (ec) {
|
||||||
if (auto ec = parseMessage(command, input_msg)) {
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR, ec);
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR, ec);
|
||||||
} else {
|
} else {
|
||||||
if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR)) { // strange!
|
output_msg = handleMessage<decltype(output_msg)>(input_msg, mount_ptr);
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR)) { // ??!!!
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_RESTART_SERVER_STR)) {
|
|
||||||
this->restart();
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_INIT_STR)) {
|
|
||||||
m_err = mount.initMount();
|
|
||||||
if (m_err) {
|
|
||||||
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_INIT);
|
|
||||||
}
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_STOP_STR)) {
|
|
||||||
m_err = mount.stopMount();
|
|
||||||
if (m_err) {
|
|
||||||
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_STOP);
|
|
||||||
}
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_SLEW_STR)) {
|
|
||||||
m_err = mount.slewToTarget(false);
|
|
||||||
if (m_err) {
|
|
||||||
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SLEW);
|
|
||||||
}
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_MOVE_STR)) {
|
|
||||||
m_err = mount.slewToTarget(true);
|
|
||||||
if (m_err) {
|
|
||||||
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_MOVE);
|
|
||||||
}
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TRACK_STR)) {
|
|
||||||
m_err = mount.trackTarget();
|
|
||||||
if (m_err) {
|
|
||||||
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_TRACK);
|
|
||||||
}
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDFMT_STR)) {
|
|
||||||
auto v = input_msg.paramValue<MccCoordinateSerializer::SerializedCoordFormat>(0);
|
|
||||||
if (v) {
|
|
||||||
_coordFormat = v.value();
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
|
||||||
} else {
|
|
||||||
err = v.error();
|
|
||||||
}
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDPREC_STR)) {
|
|
||||||
auto v = input_msg.paramValue<MccCoordinateSerializer::SexagesimalCoordPrec>(0);
|
|
||||||
if (v) {
|
|
||||||
_coordPrec = v.value();
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
|
||||||
} else {
|
|
||||||
err = v.error();
|
|
||||||
}
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TARGET_STR)) {
|
|
||||||
// by default return ICRS coordinates
|
|
||||||
MccCelestialPoint cp{.pair_kind = MccCoordPairKind::COORDS_KIND_RADEC_ICRS};
|
|
||||||
|
|
||||||
auto sz = input_msg.paramSize();
|
|
||||||
if (sz) { // set or get operation
|
|
||||||
auto vc = input_msg.paramValue<MccCelestialPoint>(0); // is it set operation?
|
|
||||||
if (vc) { // coordinates are given - set operation
|
|
||||||
auto m_err = mount.setPointingTarget(vc.value());
|
|
||||||
if (m_err) {
|
|
||||||
if (m_err) {
|
|
||||||
err = mcc_deduce_error_code(
|
|
||||||
m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SET_TARGET);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
auto vp = input_msg.paramValue<MccCoordPairKind>(0);
|
|
||||||
if (vp) { // coordinate pair kind is given
|
|
||||||
cp.pair_kind = vp.value();
|
|
||||||
err = coordsFromTelemetryData(mount, true, cp);
|
|
||||||
if (!err) {
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR,
|
|
||||||
MCC_COMMPROTO_KEYWORD_TARGET_STR, cp);
|
|
||||||
}
|
|
||||||
} else { // invalid command!!!
|
|
||||||
err = vp.error();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else { // get operation
|
|
||||||
err = coordsFromTelemetryData(mount, true, cp);
|
|
||||||
if (!err) {
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TARGET_STR,
|
|
||||||
_coordFormat, _coordPrec, cp);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_MOUNT_STR)) {
|
|
||||||
// by default return ICRS coordinates
|
|
||||||
MccCelestialPoint cp{.pair_kind = MccCoordPairKind::COORDS_KIND_RADEC_ICRS};
|
|
||||||
|
|
||||||
if (input_msg.paramSize()) { // ccordinate pair kind is given
|
|
||||||
auto vp = input_msg.paramValue<MccCoordPairKind>(0);
|
|
||||||
if (vp) { // coordinate pair kind is given
|
|
||||||
cp.pair_kind = vp.value();
|
|
||||||
err = coordsFromTelemetryData(mount, false, cp);
|
|
||||||
if (!err) {
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR,
|
|
||||||
MCC_COMMPROTO_KEYWORD_MOUNT_STR, cp);
|
|
||||||
}
|
|
||||||
} else { // invalid command!!!
|
|
||||||
err = vp.error();
|
|
||||||
}
|
|
||||||
|
|
||||||
} else {
|
|
||||||
err = coordsFromTelemetryData(mount, false, cp);
|
|
||||||
if (!err) {
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_MOUNT_STR,
|
|
||||||
_coordFormat, _coordPrec, cp);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
err = std::make_error_code(std::errc::invalid_argument);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (err) { // send error description
|
|
||||||
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR, err);
|
|
||||||
}
|
|
||||||
// else { // send ACK with copy of the input message
|
|
||||||
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
|
||||||
// }
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return output_msg.byteRepr();
|
return output_msg.byteRepr();
|
||||||
|
|
||||||
|
// std::error_code err{};
|
||||||
|
|
||||||
|
// if (auto ec = parseMessage(command, input_msg)) {
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR, ec);
|
||||||
|
// } else {
|
||||||
|
// if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR)) { // strange!
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR)) { // ??!!!
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_RESTART_SERVER_STR)) {
|
||||||
|
// this->restart();
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_INIT_STR)) {
|
||||||
|
// m_err = mount_ptr->initMount();
|
||||||
|
// if (m_err) {
|
||||||
|
// err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_INIT);
|
||||||
|
// }
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_STOP_STR)) {
|
||||||
|
// m_err = mount_ptr->stopMount();
|
||||||
|
// if (m_err) {
|
||||||
|
// err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_STOP);
|
||||||
|
// }
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_SLEW_STR)) {
|
||||||
|
// m_err = mount_ptr->slewToTarget(false);
|
||||||
|
// if (m_err) {
|
||||||
|
// err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SLEW);
|
||||||
|
// }
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_MOVE_STR)) {
|
||||||
|
// m_err = mount_ptr->slewToTarget(true);
|
||||||
|
// if (m_err) {
|
||||||
|
// err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_MOVE);
|
||||||
|
// }
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TRACK_STR)) {
|
||||||
|
// m_err = mount_ptr->trackTarget();
|
||||||
|
// if (m_err) {
|
||||||
|
// err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_TRACK);
|
||||||
|
// }
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDFMT_STR)) {
|
||||||
|
// auto v = input_msg.paramValue<MccCoordinateSerializer::SerializedCoordFormat>(0);
|
||||||
|
// if (v) {
|
||||||
|
// _coordFormat = v.value();
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
||||||
|
// } else {
|
||||||
|
// err = v.error();
|
||||||
|
// }
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDPREC_STR)) {
|
||||||
|
// auto v = input_msg.paramValue<MccCoordinateSerializer::SexagesimalCoordPrec>(0);
|
||||||
|
// if (v) {
|
||||||
|
// _coordPrec = v.value();
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
||||||
|
// } else {
|
||||||
|
// err = v.error();
|
||||||
|
// }
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TARGET_STR)) {
|
||||||
|
// // by default return ICRS coordinates
|
||||||
|
// MccCelestialPoint cp{.pair_kind = MccCoordPairKind::COORDS_KIND_RADEC_ICRS};
|
||||||
|
|
||||||
|
// auto sz = input_msg.paramSize();
|
||||||
|
// if (sz) { // set or get operation
|
||||||
|
// auto vc = input_msg.paramValue<MccCelestialPoint>(0); // is it set operation?
|
||||||
|
// if (vc) { // coordinates are given - set
|
||||||
|
// operation
|
||||||
|
// auto m_err = mount_ptr->setPointingTarget(vc.value());
|
||||||
|
// if (m_err) {
|
||||||
|
// if (m_err) {
|
||||||
|
// err = mcc_deduce_error_code(
|
||||||
|
// m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SET_TARGET);
|
||||||
|
// }
|
||||||
|
// } else {
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
||||||
|
// }
|
||||||
|
// } else {
|
||||||
|
// auto vp = input_msg.paramValue<MccCoordPairKind>(0);
|
||||||
|
// if (vp) { // coordinate pair kind is given
|
||||||
|
// cp.pair_kind = vp.value();
|
||||||
|
// err = coordsFromTelemetryData(*mount_ptr, true, cp);
|
||||||
|
// if (!err) {
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR,
|
||||||
|
// MCC_COMMPROTO_KEYWORD_TARGET_STR, cp);
|
||||||
|
// }
|
||||||
|
// } else { // invalid command!!!
|
||||||
|
// err = vp.error();
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// } else { // get operation
|
||||||
|
// err = coordsFromTelemetryData(*mount_ptr, true, cp);
|
||||||
|
// if (!err) {
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR,
|
||||||
|
// MCC_COMMPROTO_KEYWORD_TARGET_STR,
|
||||||
|
// _coordFormat, _coordPrec, cp);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// } else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_MOUNT_STR)) {
|
||||||
|
// // by default return ICRS coordinates
|
||||||
|
// MccCelestialPoint cp{.pair_kind = MccCoordPairKind::COORDS_KIND_RADEC_ICRS};
|
||||||
|
|
||||||
|
// if (input_msg.paramSize()) { // ccordinate pair kind is given
|
||||||
|
// auto vp = input_msg.paramValue<MccCoordPairKind>(0);
|
||||||
|
// if (vp) { // coordinate pair kind is given
|
||||||
|
// cp.pair_kind = vp.value();
|
||||||
|
// err = coordsFromTelemetryData(*mount_ptr, false, cp);
|
||||||
|
// if (!err) {
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR,
|
||||||
|
// MCC_COMMPROTO_KEYWORD_MOUNT_STR, cp);
|
||||||
|
// }
|
||||||
|
// } else { // invalid command!!!
|
||||||
|
// err = vp.error();
|
||||||
|
// }
|
||||||
|
|
||||||
|
// } else {
|
||||||
|
// err = coordsFromTelemetryData(*mount_ptr, false, cp);
|
||||||
|
// if (!err) {
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR,
|
||||||
|
// MCC_COMMPROTO_KEYWORD_MOUNT_STR,
|
||||||
|
// _coordFormat, _coordPrec, cp);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// } else {
|
||||||
|
// err = std::make_error_code(std::errc::invalid_argument);
|
||||||
|
// }
|
||||||
|
|
||||||
|
// if (err) { // send error description
|
||||||
|
// output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR, err);
|
||||||
|
// }
|
||||||
|
// // else { // send ACK with copy of the input message
|
||||||
|
// // output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, command);
|
||||||
|
// // }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// return output_msg.byteRepr();
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual ~MccGenericMountNetworkServer() {}
|
virtual ~MccGenericMountNetworkServer() {}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
// MccNetMessageCoordFormat _coordFormat{MccNetMessageCoordFormat::CFMT_SGM}; // ouput coordinates format
|
|
||||||
// MccNetMessageCoordPrec _coordPrec{2, 1};
|
|
||||||
|
|
||||||
MccCoordinateSerializer::SerializedCoordFormat _coordFormat{
|
MccCoordinateSerializer::SerializedCoordFormat _coordFormat{
|
||||||
MccCoordinateSerializer::SerializedCoordFormat::CFMT_SGM};
|
MccCoordinateSerializer::SerializedCoordFormat::CFMT_SGM};
|
||||||
MccCoordinateSerializer::SexagesimalCoordPrec _coordPrec{2, 1};
|
MccCoordinateSerializer::SexagesimalCoordPrec _coordPrec{2, 1};
|
||||||
|
|
||||||
|
|
||||||
|
template <typename RESULT_MSG_T, typename INPUT_MSG_T, mcc_generic_mount_c MountT>
|
||||||
|
RESULT_MSG_T handleMessage(const INPUT_MSG_T& input_msg, MountT* mount_ptr)
|
||||||
|
requires(
|
||||||
|
std::derived_from<RESULT_MSG_T,
|
||||||
|
MccNetMessage<typename RESULT_MSG_T::byte_repr_t, typename RESULT_MSG_T::valid_keys_t>> &&
|
||||||
|
std::derived_from<INPUT_MSG_T,
|
||||||
|
MccNetMessage<typename INPUT_MSG_T::byte_repr_t, typename INPUT_MSG_T::valid_keys_t>>)
|
||||||
|
{
|
||||||
|
using mount_error_t = typename MountT::error_t;
|
||||||
|
mount_error_t m_err;
|
||||||
|
|
||||||
|
RESULT_MSG_T output_msg;
|
||||||
|
|
||||||
|
std::error_code err{};
|
||||||
|
|
||||||
|
if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR)) { // strange!
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR)) { // ??!!!
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_RESTART_SERVER_STR)) {
|
||||||
|
this->restart();
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_STATUS_STR)) {
|
||||||
|
auto st = mount_ptr->status(); // according to mcc_generic_mount_c 'st' is formattable
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_STATUS_STR, st);
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_INIT_STR)) {
|
||||||
|
m_err = mount_ptr->initMount();
|
||||||
|
if (m_err) {
|
||||||
|
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_INIT);
|
||||||
|
} else {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_INIT_STR);
|
||||||
|
}
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_STOP_STR)) {
|
||||||
|
m_err = mount_ptr->stopMount();
|
||||||
|
if (m_err) {
|
||||||
|
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_STOP);
|
||||||
|
} else {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_STOP_STR);
|
||||||
|
}
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_SLEW_STR)) {
|
||||||
|
m_err = mount_ptr->slewToTarget(false);
|
||||||
|
if (m_err) {
|
||||||
|
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SLEW);
|
||||||
|
} else {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_SLEW_STR);
|
||||||
|
}
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_MOVE_STR)) {
|
||||||
|
m_err = mount_ptr->slewToTarget(true);
|
||||||
|
if (m_err) {
|
||||||
|
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_MOVE);
|
||||||
|
} else {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_MOVE_STR);
|
||||||
|
}
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TRACK_STR)) {
|
||||||
|
m_err = mount_ptr->trackTarget();
|
||||||
|
if (m_err) {
|
||||||
|
err = mcc_deduce_error_code(m_err, MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_TRACK);
|
||||||
|
} else {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TRACK_STR);
|
||||||
|
}
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDFMT_STR)) {
|
||||||
|
auto v = input_msg.template paramValue<MccCoordinateSerializer::SerializedCoordFormat>(0);
|
||||||
|
if (v) {
|
||||||
|
_coordFormat = v.value();
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
||||||
|
} else {
|
||||||
|
err = v.error();
|
||||||
|
}
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_COORDPREC_STR)) {
|
||||||
|
auto v = input_msg.template paramValue<MccCoordinateSerializer::SexagesimalCoordPrec>(0);
|
||||||
|
if (v) {
|
||||||
|
_coordPrec = v.value();
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
||||||
|
} else {
|
||||||
|
err = v.error();
|
||||||
|
}
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_TARGET_STR)) {
|
||||||
|
// by default return ICRS coordinates
|
||||||
|
MccCelestialPoint cp{.pair_kind = MccCoordPairKind::COORDS_KIND_RADEC_ICRS};
|
||||||
|
|
||||||
|
auto sz = input_msg.paramSize();
|
||||||
|
if (sz) { // set or get operation
|
||||||
|
auto vc = input_msg.template paramValue<MccCelestialPoint>(0); // is it set operation?
|
||||||
|
if (vc) { // coordinates are given - set operation
|
||||||
|
auto m_err = mount_ptr->setPointingTarget(vc.value());
|
||||||
|
if (m_err) {
|
||||||
|
if (m_err) {
|
||||||
|
err = mcc_deduce_error_code(m_err,
|
||||||
|
MccGenericMountNetworkServerErrorCode::ERROR_MOUNT_SET_TARGET);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, input_msg.byteRepr());
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
auto vp = input_msg.template paramValue<MccCoordPairKind>(0);
|
||||||
|
if (vp) { // coordinate pair kind is given
|
||||||
|
cp.pair_kind = vp.value();
|
||||||
|
err = coordsFromTelemetryData(*mount_ptr, true, cp);
|
||||||
|
if (!err) {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TARGET_STR,
|
||||||
|
cp);
|
||||||
|
}
|
||||||
|
} else { // invalid command!!!
|
||||||
|
err = vp.error();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else { // get operation
|
||||||
|
err = coordsFromTelemetryData(*mount_ptr, true, cp);
|
||||||
|
if (!err) {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_TARGET_STR,
|
||||||
|
_coordFormat, _coordPrec, cp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} else if (input_msg.withKey(MCC_COMMPROTO_KEYWORD_MOUNT_STR)) {
|
||||||
|
// by default return ICRS coordinates
|
||||||
|
MccCelestialPoint cp{.pair_kind = MccCoordPairKind::COORDS_KIND_RADEC_ICRS};
|
||||||
|
|
||||||
|
if (input_msg.paramSize()) { // ccordinate pair kind is given
|
||||||
|
auto vp = input_msg.template paramValue<MccCoordPairKind>(0);
|
||||||
|
if (vp) { // coordinate pair kind is given
|
||||||
|
cp.pair_kind = vp.value();
|
||||||
|
err = coordsFromTelemetryData(*mount_ptr, false, cp);
|
||||||
|
if (!err) {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_MOUNT_STR, cp);
|
||||||
|
}
|
||||||
|
} else { // invalid command!!!
|
||||||
|
err = vp.error();
|
||||||
|
}
|
||||||
|
|
||||||
|
} else {
|
||||||
|
err = coordsFromTelemetryData(*mount_ptr, false, cp);
|
||||||
|
if (!err) {
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ACK_STR, MCC_COMMPROTO_KEYWORD_MOUNT_STR,
|
||||||
|
_coordFormat, _coordPrec, cp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
err = std::make_error_code(std::errc::invalid_argument);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (err) { // send error description
|
||||||
|
output_msg.construct(MCC_COMMPROTO_KEYWORD_SERVER_ERROR_STR, err);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
return output_msg;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
template <typename MSG_T>
|
template <typename MSG_T>
|
||||||
std::error_code parseMessage(std::string_view msg_bytes, MSG_T& msg)
|
std::error_code parseMessage(std::string_view msg_bytes, MSG_T& msg)
|
||||||
{
|
{
|
||||||
|
|||||||
@ -493,18 +493,6 @@ template <typename T>
|
|||||||
concept mcc_netmessage_c = requires(T t) { T(); };
|
concept mcc_netmessage_c = requires(T t) { T(); };
|
||||||
|
|
||||||
|
|
||||||
/* helper types to format serialized celestial coordinates */
|
|
||||||
/* it can be used as inputs in "construct" method or corresponding constructor */
|
|
||||||
|
|
||||||
// format of output (serialized) coordinates
|
|
||||||
enum class MccNetMessageCoordFormat { CFMT_DEGREES, CFMT_SGM };
|
|
||||||
|
|
||||||
// precision of sexagesimal coordinates (number of decimal places in seconds/arcseconds)
|
|
||||||
struct MccNetMessageCoordPrec {
|
|
||||||
uint8_t hour_prec = 2;
|
|
||||||
uint8_t deg_prec = 1;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
template <mcc::traits::mcc_char_range BYTEREPR_T = std::string_view,
|
template <mcc::traits::mcc_char_range BYTEREPR_T = std::string_view,
|
||||||
mcc_netmsg_valid_keys_c BASE_T = MccNetMessageValidKeywords>
|
mcc_netmsg_valid_keys_c BASE_T = MccNetMessageValidKeywords>
|
||||||
@ -537,7 +525,7 @@ protected:
|
|||||||
if (value == MccCoordPairKind::COORDS_KIND_UNKNOWN) {
|
if (value == MccCoordPairKind::COORDS_KIND_UNKNOWN) {
|
||||||
return std::make_error_code(std::errc::invalid_argument);
|
return std::make_error_code(std::errc::invalid_argument);
|
||||||
}
|
}
|
||||||
} else if constexpr (std::same_as<VT, MccNetMessageCoordFormat>) {
|
} else if constexpr (std::same_as<VT, MccCoordinateSerializer::SerializedCoordFormat>) {
|
||||||
std::string v;
|
std::string v;
|
||||||
auto ec = (*this)(std::forward<IR>(bytes), v);
|
auto ec = (*this)(std::forward<IR>(bytes), v);
|
||||||
if (ec) {
|
if (ec) {
|
||||||
@ -545,13 +533,13 @@ protected:
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (v.compare(MCC_COMMPROTO_KEYWORD_COORDFMT_SEXGM_STR) == 0) {
|
if (v.compare(MCC_COMMPROTO_KEYWORD_COORDFMT_SEXGM_STR) == 0) {
|
||||||
value = MccNetMessageCoordFormat::CFMT_SGM;
|
value = MccCoordinateSerializer::SerializedCoordFormat::CFMT_SGM;
|
||||||
} else if (v.compare(MCC_COMMPROTO_KEYWORD_COORDFMT_FIXED_STR) == 0) {
|
} else if (v.compare(MCC_COMMPROTO_KEYWORD_COORDFMT_FIXED_STR) == 0) {
|
||||||
value = MccNetMessageCoordFormat::CFMT_DEGREES;
|
value = MccCoordinateSerializer::SerializedCoordFormat::CFMT_DEGREES;
|
||||||
} else {
|
} else {
|
||||||
return std::make_error_code(std::errc::invalid_argument);
|
return std::make_error_code(std::errc::invalid_argument);
|
||||||
}
|
}
|
||||||
} else if constexpr (std::same_as<VT, MccNetMessageCoordPrec>) {
|
} else if constexpr (std::same_as<VT, MccCoordinateSerializer::SexagesimalCoordPrec>) {
|
||||||
std::vector<int64_t> v;
|
std::vector<int64_t> v;
|
||||||
auto ec = (*this)(std::forward<IR>(bytes), v);
|
auto ec = (*this)(std::forward<IR>(bytes), v);
|
||||||
if (ec) {
|
if (ec) {
|
||||||
@ -683,8 +671,10 @@ public:
|
|||||||
// fromCharRange(msg);
|
// fromCharRange(msg);
|
||||||
// }
|
// }
|
||||||
|
|
||||||
|
virtual ~MccNetMessage() = default;
|
||||||
|
|
||||||
template <traits::mcc_input_char_range KT>
|
template <traits::mcc_input_char_range KT>
|
||||||
constexpr bool withKey(const KT& key)
|
constexpr bool withKey(const KT& key) const
|
||||||
{
|
{
|
||||||
if constexpr (std::is_pointer_v<std::decay_t<KT>>) {
|
if constexpr (std::is_pointer_v<std::decay_t<KT>>) {
|
||||||
return withKey(std::string_view{key});
|
return withKey(std::string_view{key});
|
||||||
@ -719,7 +709,7 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <std::ranges::range R>
|
template <std::ranges::range R>
|
||||||
R params(size_t start_idx = 0, size_t Nelemes = std::numeric_limits<size_t>::max())
|
R params(size_t start_idx = 0, size_t Nelemes = std::numeric_limits<size_t>::max()) const
|
||||||
requires(traits::mcc_view_or_output_char_range<R> || traits::mcc_range_of_char_range<R>)
|
requires(traits::mcc_view_or_output_char_range<R> || traits::mcc_range_of_char_range<R>)
|
||||||
{
|
{
|
||||||
if (start_idx >= _params.size()) {
|
if (start_idx >= _params.size()) {
|
||||||
@ -758,13 +748,13 @@ public:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string_view params(size_t start_idx = 0, size_t Nelemes = std::numeric_limits<size_t>::max())
|
std::string_view params(size_t start_idx = 0, size_t Nelemes = std::numeric_limits<size_t>::max()) const
|
||||||
{
|
{
|
||||||
return params<std::string_view>(start_idx, Nelemes);
|
return params<std::string_view>(start_idx, Nelemes);
|
||||||
}
|
}
|
||||||
|
|
||||||
template <traits::mcc_view_or_output_char_range R>
|
template <traits::mcc_view_or_output_char_range R>
|
||||||
R param(size_t idx)
|
R param(size_t idx) const
|
||||||
{
|
{
|
||||||
if (idx >= _params.size()) {
|
if (idx >= _params.size()) {
|
||||||
return {};
|
return {};
|
||||||
@ -780,7 +770,7 @@ public:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string_view param(size_t idx)
|
std::string_view param(size_t idx) const
|
||||||
{
|
{
|
||||||
if (idx >= _params.size()) {
|
if (idx >= _params.size()) {
|
||||||
return {};
|
return {};
|
||||||
@ -791,7 +781,7 @@ public:
|
|||||||
|
|
||||||
|
|
||||||
template <typename T, typename DeserFuncT>
|
template <typename T, typename DeserFuncT>
|
||||||
std::expected<T, std::error_code> paramValue(size_t idx, DeserFuncT&& deser_func)
|
std::expected<T, std::error_code> paramValue(size_t idx, DeserFuncT&& deser_func) const
|
||||||
{
|
{
|
||||||
if (idx >= _params.size()) {
|
if (idx >= _params.size()) {
|
||||||
return std::unexpected{std::make_error_code(std::errc::argument_out_of_domain)};
|
return std::unexpected{std::make_error_code(std::errc::argument_out_of_domain)};
|
||||||
@ -808,9 +798,9 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
template <typename T>
|
template <typename T>
|
||||||
std::expected<T, std::error_code> paramValue(size_t idx)
|
std::expected<T, std::error_code> paramValue(size_t idx) const
|
||||||
{
|
{
|
||||||
return paramValue<T>(idx, _defaultDeserilizer);
|
return paramValue<T>(idx, _defaultDeserializer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -948,7 +938,7 @@ protected:
|
|||||||
|
|
||||||
BYTEREPR_T _msgBuffer{};
|
BYTEREPR_T _msgBuffer{};
|
||||||
|
|
||||||
inline static DefaultDeserializer _defaultDeserilizer{};
|
inline static DefaultDeserializer _defaultDeserializer{};
|
||||||
|
|
||||||
DefaultSerializer _defaultSerializer{};
|
DefaultSerializer _defaultSerializer{};
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user