Motion Master
Loading...
Searching...
No Matches
spoe.h
Go to the documentation of this file.
1#pragma once
2
3#include <atomic>
4#include <chrono>
5#include <string>
6#include <unordered_map>
7#include <vector>
8
9#include <boost/asio.hpp>
10#include <nlohmann/json.hpp>
11
12#include "base.h"
14#include "core/util.h"
15
16namespace mm::comm::spoe {
17
26enum class SpoeMessageType : uint8_t {
27 SDO_READ = 0x01,
28 SDO_WRITE = 0x02,
30 0x03,
31 PDO_CONTROL = 0x04,
34 FILE_READ = 0x0C,
35 FILE_WRITE = 0x0D,
37 0x0E,
38 STATE_READ = 0x0F,
39 // PARAM_INDEXES_LIST = 0x10, ///< Request a list of parameter indexes.
40 PARAM_LIST = 0x13,
42};
43
50enum class SpoeMessageRequestStatus : uint8_t {
51 OK = 0x00,
52 FIRST = 0x80,
53 MIDDLE = 0xC0,
54 LAST = 0x40,
55};
56
61enum class SpoeMessageParamListErrorStatus : uint8_t {
62 SUCCESS_ACK = 0x58,
63
64 ERR = 0x63,
66};
67
74enum class SpoeMessageSdoStatus : uint16_t {
75 NO_ERR = 0x0000,
76 GENERIC = 0x0001,
77 NOT_FOUND = 0x0002,
78 READ_ONLY = 0x0003,
79 WRITE_ONLY = 0x0004,
80 WRONG_TYPE = 0x0005,
81 INVALID_LIST = 0x0006,
87 SI0_NOT_ZERO = 0x000C,
88 SUB_NOT_FOUND = 0x000D,
89};
90
91// enum class SpoeMessageSdoStatus : uint16_t {
92// NO_ERROR = 0x0000,
93// };
94
120
127enum class SpoeMessagePacketStatus : uint8_t {
128 OK = 0x00,
129 FIRST = 0x80,
130 MIDDLE = 0xC0,
131 LAST = 0x40,
132};
133
145enum class PdoMode : uint8_t {
146 NONE = 0,
148 1,
150};
151
159struct Message {
161 static constexpr size_t kHeaderSize = 7;
162
164 static constexpr size_t kBufferSize = 1500 - kHeaderSize;
165
171
177 uint16_t id;
178
184 uint16_t status;
185
191 uint16_t size;
192
198 std::vector<uint8_t> data;
199};
200
202
219Message parseMessage(const std::vector<uint8_t>& buffer);
220
234std::vector<uint8_t> serializeSpoeMessage(const Message& message);
235
246
251};
252
266 public:
267 // Forward constructor to base class constructor
269 std::chrono::milliseconds interval);
270
271 protected:
289 void refresh(const std::vector<mm::comm::base::Parameter::Address>& addresses)
290 override;
291};
292
303 public:
317 Device(const std::string& ip, uint16_t port, uint16_t position = 0,
318 std::chrono::milliseconds refresherInterval =
319 std::chrono::milliseconds(3000));
320
326 ~Device();
327
336 std::string getSocketAddress() const;
337
350 uint16_t incrementSeqId();
351
362 bool connect(std::chrono::seconds expiryTime = std::chrono::seconds(3));
363
372 bool isConnected();
373
387 bool disconnect();
388
407 const Message& requestMessage,
408 const std::chrono::steady_clock::duration expiryTime);
409
410 uint16_t getPosition() const override;
411
439 uint8_t getState(bool refresh = false,
440 const std::chrono::steady_clock::duration expiryTime =
441 std::chrono::milliseconds(5000)) override;
442
460 bool setState(uint8_t state,
461 const std::chrono::steady_clock::duration expiryTime =
462 std::chrono::milliseconds(5000)) override;
463
495 std::vector<uint8_t> readFile(
496 const std::string& filename,
497 const std::chrono::steady_clock::duration expiryTime =
498 std::chrono::milliseconds(5000)) override;
499
500 std::vector<std::string> readFileList(
501 const bool stripSizeSuffix = true,
502 const std::chrono::steady_clock::duration expiryTime =
503 std::chrono::milliseconds(5000)) override;
504
522 void removeFile(const std::string& filename,
523 const std::chrono::steady_clock::duration expiryTime =
524 std::chrono::milliseconds(5000)) override;
525
548 const std::vector<std::uint8_t>& data,
549 const std::vector<std::string>& skipFiles = {"SOMANET_CiA_402.xml.zip",
550 "stack_image.svg.zip"},
551 std::function<void(uint8_t, std::string)> progressCallback = nullptr,
552 const std::chrono::steady_clock::duration expiryTime =
553 std::chrono::milliseconds(60000)) override;
554
576 void writeFile(const std::string& filename, const std::vector<uint8_t>& data,
577 const std::chrono::steady_clock::duration expiryTime =
578 std::chrono::milliseconds(5000)) override;
579
596 bool triggerFirmwareUpdate(const std::chrono::steady_clock::duration
597 expiryTime = std::chrono::milliseconds(2000));
598
625 std::vector<mm::comm::base::Parameter> getParametersFromDevice(
626 bool readValues = false,
627 const std::chrono::steady_clock::duration expiryTime =
628 std::chrono::milliseconds(1000));
629
649 std::vector<uint8_t> readSdo(
650 uint16_t index, uint8_t subindex,
651 const std::chrono::steady_clock::duration expiryTime =
652 std::chrono::milliseconds(1000));
653
682 std::vector<std::vector<uint8_t>> readSdoBatch(
683 const std::vector<mm::comm::base::Parameter::Address>& addresses,
684 const std::chrono::steady_clock::duration expiryTime =
685 std::chrono::milliseconds(1000));
686
699 std::vector<std::vector<uint8_t>> readSdoBatch(
700 const std::vector<mm::comm::base::Parameter>& parameters,
701 const std::chrono::steady_clock::duration expiryTime =
702 std::chrono::milliseconds(1000));
703
716 std::vector<mm::comm::base::Parameter>& parameters,
717 std::size_t batchSize = 50,
718 std::chrono::steady_clock::duration expiryTime =
719 std::chrono::milliseconds(1000));
720
740 bool writeSdo(uint16_t index, uint8_t subindex,
741 const std::vector<uint8_t>& data,
742 const std::chrono::steady_clock::duration expiryTime =
743 std::chrono::milliseconds(1000));
744
758 size_t loadParameters(bool readValues = false,
759 const std::chrono::steady_clock::duration expiryTime =
760 std::chrono::milliseconds(9000)) override;
761
762 void clearParameters() override;
763
775 std::vector<std::reference_wrapper<mm::comm::base::Parameter>> parameters()
776 override;
777
779 uint8_t subindex) override;
780
782 const uint16_t index, const uint8_t subindex,
783 const std::chrono::steady_clock::duration expiryTime =
784 std::chrono::milliseconds(3000)) override;
785
806 template <typename T>
807 T upload(uint16_t index, uint8_t subindex,
808 const std::chrono::steady_clock::duration expiryTime =
809 std::chrono::milliseconds(5000)) {
810 mm::comm::base::Parameter& parameter = upload(index, subindex, expiryTime);
811 return parameter.getValue<T>();
812 }
813
814 void download(uint16_t index, uint8_t subindex,
815 const std::chrono::steady_clock::duration expiryTime =
816 std::chrono::milliseconds(5000)) override;
817
818 void download(uint16_t index, uint8_t subindex,
820 const std::chrono::steady_clock::duration expiryTime =
821 std::chrono::milliseconds(5000)) override;
822
841 template <typename T>
842 void download(uint16_t index, uint8_t subindex, const T& value,
843 const std::chrono::steady_clock::duration expiryTime =
844 std::chrono::milliseconds(5000)) {
846 }
847
863 ServerInfo getServerInfo(const std::chrono::steady_clock::duration
864 expiryTime = std::chrono::milliseconds(3000));
865
878 bool setPdoMode(PdoMode mode,
879 const std::chrono::steady_clock::duration expiryTime =
880 std::chrono::milliseconds(3000));
881
888
905
906 std::vector<uint8_t> exchangeProcessData(
907 const std::vector<uint8_t>& data,
908 const std::chrono::steady_clock::duration expiryTime =
909 std::chrono::milliseconds(1000));
910
931
948 uint64_t missedCycles = 0) override;
949
951 uint16_t index, uint8_t subindex) const override;
952
967
978 bool isOnline() override;
979
984 DeviceParameterRefresher& refresher() { return refresher_; }
985
986 private:
987 boost::asio::io_context ioContext_;
989 boost::asio::ip::tcp::endpoint
990 endpoint_;
992 boost::asio::ip::tcp::socket
993 socket_;
994
1001 std::recursive_mutex
1002 mutex_;
1003
1004 std::mutex disconnectMutex_;
1005
1013 std::atomic<uint16_t> seqId_{0};
1014
1015 uint16_t position_;
1017
1018 uint8_t state_;
1021
1022 PdoMode pdoMode_;
1024
1025 std::unordered_map<mm::comm::base::Parameter::Address,
1027 parametersMap_;
1030 pdoMappings_;
1031
1032 std::atomic_flag isSendingAndReceivingProcessData_ =
1033 ATOMIC_FLAG_INIT;
1035
1037 txPdoQueue_;
1038
1039 std::mutex
1040 sendAndReceiveProcessDataExceptionPtrMutex_;
1043
1044 std::exception_ptr sendAndReceiveProcessDataExceptionPtr_ =
1045 nullptr;
1047
1048 DeviceParameterRefresher refresher_;
1050};
1051
1052} // namespace mm::comm::spoe
Base class for periodically refreshing a set of device parameters in a background thread.
Definition base.h:1608
Abstract interface representing a generic device.
Definition base.h:1035
Represents a device parameter identified by index and subindex.
Definition base.h:466
ParameterValue getValue() const
Retrieves the value of the parameter based on its data type.
Definition base.cc:41
std::pair< uint16_t, uint8_t > Address
Alias for a pair of uint16_t and uint8_t representing a parameter address.
Definition base.h:476
Concrete refresher that uploads parameters from a device.
Definition spoe.h:265
DeviceParameterRefresher(mm::comm::base::Device &device, std::chrono::milliseconds interval)
Definition spoe.cc:64
void refresh(const std::vector< mm::comm::base::Parameter::Address > &addresses) override
Rereads the specified device parameters in a single message exchange.
Definition spoe.cc:68
mm::comm::base::Parameter & findParameter(uint16_t index, uint8_t subindex) override
Finds and returns a reference to a parameter by its index and subindex.
Definition spoe.cc:1021
size_t loadParameters(bool readValues=false, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(9000)) override
Loads parameters from the device and stores them locally.
Definition spoe.cc:997
void clearParameters() override
Clears all loaded object dictionary parameters.
Definition spoe.cc:1007
void removeFile(const std::string &filename, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(5000)) override
Remove a file from the SPoE device.
Definition spoe.cc:486
DeviceParameterRefresher & refresher()
Get a reference to the device parameter refresher.
Definition spoe.h:984
bool setState(uint8_t state, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(5000)) override
Sends a state control command to the SPoE device and checks the response.
Definition spoe.cc:334
Message exchangeWithTimeout(const Message &requestMessage, const std::chrono::steady_clock::duration expiryTime)
Exchanges a message with a remote server and waits for a response with a timeout.
Definition spoe.cc:238
void readSdoBatchAndUpdateParameters(std::vector< mm::comm::base::Parameter > &parameters, std::size_t batchSize=50, std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(1000))
Reads the specified parameters in batches and updates their values.
Definition spoe.cc:925
uint16_t getPosition() const override
Gets the device's position in the network chain.
Definition spoe.cc:307
bool isConnected()
Checks if the SPoE socket is currently open.
Definition spoe.cc:200
std::vector< std::reference_wrapper< mm::comm::base::Parameter > > parameters() override
Get a vector of references to parameters.
Definition spoe.cc:1010
bool writeSdo(uint16_t index, uint8_t subindex, const std::vector< uint8_t > &data, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(1000))
Writes a Service Data Object (SDO) to the device.
Definition spoe.cc:950
std::vector< uint8_t > readFile(const std::string &filename, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(5000)) override
Reads the contents of a file over SPoE from the device.
Definition spoe.cc:367
void writeFile(const std::string &filename, const std::vector< uint8_t > &data, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(5000)) override
Write a file to the SPoE device in segments.
Definition spoe.cc:553
void performProcessDataExchangeAsync()
Perform asynchronous process data exchange with the SPoE device.
Definition spoe.cc:1174
std::vector< uint8_t > exchangeProcessData(const std::vector< uint8_t > &data, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(1000))
Exchanges process data (PDO) with the device.
Definition spoe.cc:1144
std::string getSocketAddress() const
Returns the socket address as a string in the format "IP:port".
Definition spoe.cc:152
PdoMode getPdoMode()
Retrieves the current PDO mode of the device.
Definition spoe.cc:1142
bool connect(std::chrono::seconds expiryTime=std::chrono::seconds(3))
Attempts to connect the SPoE device to the specified endpoint.
Definition spoe.cc:162
void download(uint16_t index, uint8_t subindex, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(5000)) override
Downloads a parameter to the device using SDO communication.
Definition spoe.cc:1054
std::vector< uint8_t > readSdo(uint16_t index, uint8_t subindex, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(1000))
Reads an SDO (Service Data Object) from the device.
Definition spoe.cc:796
Device(const std::string &ip, uint16_t port, uint16_t position=0, std::chrono::milliseconds refresherInterval=std::chrono::milliseconds(3000))
Constructs a SpoeDevice object with the specified IP address, port, and optionally position.
Definition spoe.cc:104
void download(uint16_t index, uint8_t subindex, const T &value, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(5000))
Sets and downloads a parameter value to the device using the specified type.
Definition spoe.h:842
T upload(uint16_t index, uint8_t subindex, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(5000))
Uploads a parameter from the device and returns its value as the specified type.
Definition spoe.h:807
~Device()
Destructor for the Device class.
Definition spoe.cc:147
bool triggerFirmwareUpdate(const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(2000))
Sends a firmware update request to the connected Integro device.
Definition spoe.cc:615
uint8_t getState(bool refresh=false, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(5000)) override
Sends a request to read the state of the device and returns the state value.
Definition spoe.cc:309
mm::comm::base::MappedParameterValues getMappedParameterValues()
Retrieves the mapped parameter values for the SPoE device.
Definition spoe.cc:1323
std::vector< std::vector< uint8_t > > readSdoBatch(const std::vector< mm::comm::base::Parameter::Address > &addresses, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(1000))
Reads a batch of SDOs from the device in a single request.
Definition spoe.cc:832
bool isOnline() override
Checks if the SPoE device is online.
Definition spoe.cc:1341
mm::comm::base::PdoMappingStatus getPdoMappingStatus(uint16_t index, uint8_t subindex) const override
Determines the PDO mapping status of a parameter by its index and subindex.
Definition spoe.cc:1295
uint16_t incrementSeqId()
Increments the sequence ID atomically and wraps it around at the maximum value.
Definition spoe.cc:157
mm::comm::base::Parameter & upload(const uint16_t index, const uint8_t subindex, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(3000)) override
Uploads a parameter from the device via SDO and updates the local parameter store.
Definition spoe.cc:1034
bool disconnect()
Gracefully disconnects the SPoE device.
Definition spoe.cc:202
void updateFirmware(const std::vector< std::uint8_t > &data, const std::vector< std::string > &skipFiles={"SOMANET_CiA_402.xml.zip", "stack_image.svg.zip"}, std::function< void(uint8_t, std::string)> progressCallback=nullptr, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(60000)) override
Updates the firmware on this SPoE device.
bool setPdoMode(PdoMode mode, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(3000))
Sets the PDO mode of the device.
Definition spoe.cc:1116
void exchangeProcessDataAndUpdateParameters(uint64_t missedCycles=0) override
Exchanges process data and updates device parameters.
Definition spoe.cc:1234
std::vector< std::string > readFileList(const bool stripSizeSuffix=true, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(5000)) override
Reads a list of file names from the device.
Definition spoe.cc:448
ServerInfo getServerInfo(const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(3000))
Retrieves the server information from the connected SPoE device.
Definition spoe.cc:1080
std::vector< mm::comm::base::Parameter > getParametersFromDevice(bool readValues=false, const std::chrono::steady_clock::duration expiryTime=std::chrono::milliseconds(1000))
Retrieves the parameter list from the device.
Definition spoe.cc:634
Thread-safe FIFO queue with optional capacity limit.
Definition thread_safe_queue.h:23
uint8_t type
Definition co_dictionary.h:1
uint8_t * value
Definition co_dictionary.h:9
uint16_t index
Definition co_dictionary.h:0
PdoMappingStatus
Represents the PDO mapping status of a parameter.
Definition base.h:439
std::variant< bool, std::int8_t, std::int16_t, std::int32_t, std::int64_t, std::uint8_t, std::uint16_t, std::uint32_t, std::uint64_t, float, double, std::string, std::vector< std::uint8_t > > ParameterValue
Alias for a variant that can hold multiple types of values.
Definition base.h:403
Definition spoe.cc:13
SpoeMessagePacketStatus
Packet status codes for SPoE messages.
Definition spoe.h:127
SpoeMessageFileErrorStatus
Error status codes returned when reading or writing a file via SPoE message.
Definition spoe.h:99
@ COMMUNICATION_BRIDGE_ERROR
Definition spoe.h:118
SpoeMessageParamListErrorStatus
Error status codes returned when reading the parameter list via SPoE.
Definition spoe.h:61
@ SUCCESS_ACK
Success Acknowledgement.
Definition spoe.h:62
PdoMode
Defines the modes for Process Data Object (PDO) communication over SPoE.
Definition spoe.h:145
@ NONE
No process or cyclic data exchange available.
Definition spoe.h:146
@ CONTROL
Both RxPDO and TxPDO data exchange enabled.
Definition spoe.h:149
@ MONITOR
Device sends RxPDO values only; incoming requests are ignored.
Definition spoe.h:147
std::vector< uint8_t > serializeSpoeMessage(const Message &message)
Serializes an SpoeMessage object into a byte buffer.
Definition spoe.cc:42
SpoeMessageType
Enumeration of SPoE message types used in the protocol.
Definition spoe.h:26
@ SDO_BATCH_READ
Read multiple SDOs in a single request.
Definition spoe.h:32
@ SERVER_INFO
Request information about the server or device.
Definition spoe.h:41
@ STATE_CONTROL
Control the state of the device (e.g., INIT, PREOP).
Definition spoe.h:36
@ FILE_READ
Read a file from the device.
Definition spoe.h:34
@ STATE_READ
Read the current state of the device.
Definition spoe.h:38
@ SDO_WRITE
Write a value to a Service Data Object (SDO).
Definition spoe.h:28
@ SDO_READ
Read a Service Data Object (SDO) value.
Definition spoe.h:27
@ FIRMWARE_UPDATE
Perform firmware update operation.
Definition spoe.h:33
@ FILE_WRITE
Write a file to the device.
Definition spoe.h:35
@ PDO_CONTROL
Control or configure PDO behavior.
Definition spoe.h:31
@ PARAM_LIST
Request a full list of parameters.
Definition spoe.h:40
@ PDO_RXTX_FRAME
Transmit or receive a Process Data Object (PDO) frame.
Definition spoe.h:29
SpoeMessageRequestStatus
Status codes representing the state of an SPoE request message.
Definition spoe.h:50
@ FIRST
First segment of a multi-part message.
Definition spoe.h:52
@ MIDDLE
Middle segment of a multi-part message.
Definition spoe.h:53
@ OK
Message is complete and valid.
Definition spoe.h:51
@ LAST
Last segment of a multi-part message.
Definition spoe.h:54
SpoeMessageSdoStatus
Status codes returned during SDO (Service Data Object) read and write operations.
Definition spoe.h:74
@ INSUFFICIENT_BUFFER
Definition spoe.h:82
@ SUB_NOT_FOUND
Definition spoe.h:88
@ UNKNOWN_OR_UNSUPPORTED
Definition spoe.h:84
@ SI0_NOT_ZERO
Definition spoe.h:87
@ UNSUPPORTED_ACCESS
Definition spoe.h:86
@ NO_ERR
Success Acknowledgement.
Definition spoe.h:75
@ WRONG_TYPE
Definition spoe.h:80
@ VALUEINFO_UNAVAILABLE
Definition spoe.h:83
@ INVALID_LIST
Definition spoe.h:81
@ LOCAL_TRANSFER
Definition spoe.h:85
@ WRITE_ONLY
Definition spoe.h:79
Message parseMessage(const std::vector< uint8_t > &buffer)
Parses a raw SPoE message buffer into a structured SpoeMessage.
Definition spoe.cc:15
NLOHMANN_DEFINE_TYPE_NON_INTRUSIVE(Message, type, id, status, size, data)
Holds collections of mapped parameter values for RX and TX directions.
Definition base.h:428
Represents the mapped PDO entries for a slave device.
Definition base.h:148
Definition spoe.h:159
uint16_t status
The status of the response message.
Definition spoe.h:184
uint16_t size
The size of the buffer in the response message.
Definition spoe.h:191
static constexpr size_t kBufferSize
Definition spoe.h:164
SpoeMessageType type
The type of the response message.
Definition spoe.h:170
std::vector< uint8_t > data
The payload data of the response message.
Definition spoe.h:198
static constexpr size_t kHeaderSize
Definition spoe.h:161
uint16_t id
The sequence ID of the response message.
Definition spoe.h:177
Contains information about the server's protocol version and monitoring mode.
Definition spoe.h:241
uint16_t protocolVersion
Version of the communication protocol used by the server.
Definition spoe.h:245
uint8_t monitoringMode
Indicates the monitoring mode configuration.
Definition spoe.h:250