56 #ifndef __SICK_SCANSEGMENT_XD_UDP_SOCKETS_H
57 #define __SICK_SCANSEGMENT_XD_UDP_SOCKETS_H
60 #if defined WIN32 || defined _MSC_VER
61 #ifndef _WINSOCK_DEPRECATED_NO_WARNINGS
62 #define _WINSOCK_DEPRECATED_NO_WARNINGS
65 #define UNLINK _unlink
68 int error_num = WSAGetLastError();
69 char error_message[1024] = { 0 };
70 FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
NULL, error_num, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), error_message,
sizeof(error_message),
NULL);
71 return std::to_string(error_num) +
" (" + std::string(error_message) +
")";
76 #include <arpa/inet.h>
77 #include <netinet/ip.h>
78 #include <netinet/udp.h>
79 #include <sys/types.h>
80 #include <sys/socket.h>
83 #define INVALID_SOCKET (-1)
85 #define closesocket close
86 static std::string
getErrorMessage(
void) {
return std::to_string(errno) +
" (" + std::string(strerror(errno)) +
")"; }
100 return (p_data[0]) | (p_data[1] << 8) | (p_data[2] << 16) | (p_data[3] << 24);
127 catch (std::exception & e)
129 ROS_ERROR_STREAM(
"## ERROR ~UdpReceiverSocketImpl: can't close socket, " << e.what());
139 bool Init(
const std::string& udp_sender,
int udp_port,
bool blocking =
false)
147 m_udp_socket = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
161 struct sockaddr_in sim_servaddr = { 0 };
163 sim_servaddr.sin_addr.s_addr = htonl(INADDR_ANY);
165 sim_servaddr.sin_addr.s_addr = inet_addr(
m_udp_sender.c_str());
166 sim_servaddr.sin_family = AF_INET;
168 ROS_INFO_STREAM(
"UdpReceiverSocketImpl: udp socket created, binding to port " << ntohs(sim_servaddr.sin_port) <<
" ... ");
188 catch (std::exception & e)
197 size_t Receive(std::vector<uint8_t>& msg_payload)
199 int64_t bytes_received = 0;
208 return (
size_t)bytes_received;
212 size_t Receive(std::vector<uint8_t>& msg_payload,
double timeout,
const std::vector<uint8_t>& udp_msg_start_seq)
215 size_t headerlength = udp_msg_start_seq.size() +
sizeof(uint32_t);
216 size_t bytes_received = 0;
217 size_t bytes_to_receive = msg_payload.size();
221 int64_t chunk_bytes_received = recv(
m_udp_socket, (
char*)msg_payload.data() + bytes_received, (
int)msg_payload.size() - bytes_received,
m_recv_flags);
222 if (chunk_bytes_received <= 0)
224 std::this_thread::sleep_for(std::chrono::milliseconds(1));
231 if (bytes_received == 0 && chunk_bytes_received > (int64_t)headerlength && std::equal(msg_payload.begin(), msg_payload.begin() + udp_msg_start_seq.size(), udp_msg_start_seq.begin()))
236 size_t Payloadlength=
Convert4Byte(msg_payload.data() + udp_msg_start_seq.size());
237 bytes_to_receive = Payloadlength + headerlength +
sizeof(uint32_t);
238 if(bytes_to_receive > msg_payload.size())
240 ROS_ERROR_STREAM(
"## ERROR UdpReceiverSocketImpl::Receive(): unexpected payloadlength " << Payloadlength <<
" byte incl CRC received");
243 bytes_received += chunk_bytes_received;
245 else if (bytes_received > 0)
247 bytes_received += chunk_bytes_received;
294 #if defined WIN32 || defined _MSC_VER
295 char broadcast_opt = 1;
297 int broadcast_opt = 1;
299 if (setsockopt(
m_udp_socket, SOL_SOCKET, SO_BROADCAST, &broadcast_opt,
sizeof(broadcast_opt)) < 0)
306 catch (
const std::exception& e)
309 ROS_ERROR_STREAM(
"## ERROR UdpSenderSocketImpl(): socket initialization failed, exception: " << e.what());
327 catch (
const std::exception& e)
329 ROS_ERROR_STREAM(
"## ERROR ~UdpSenderSocketImpl(): socket shutdown and close failed, exception: " << e.what());
341 bool Send(std::vector<uint8_t>& message)
343 size_t bytes_sent = 0;
348 struct sockaddr_in sim_servaddr = { 0 };
351 sim_servaddr.sin_addr.s_addr = htonl(INADDR_BROADCAST);
355 #if defined WIN32 || defined _MSC_VER
358 struct in_addr sim_in_addr;
361 sim_servaddr.sin_addr.s_addr = sim_in_addr.s_addr;
370 sim_servaddr.sin_family = AF_INET;
373 if (bytes_sent !=
message.size())
375 ROS_ERROR_STREAM(
"## ERROR UdpSenderSocketImpl()::Send() failed, " << bytes_sent <<
" of " <<
message.size() <<
" bytes sent.");
378 catch (
const std::exception& e)
380 ROS_ERROR_STREAM(
"## ERROR UdpSenderSocketImpl()::Send() failed, exception: " << e.what());
385 ROS_ERROR_STREAM(
"## ERROR UdpSenderSocketImpl()::Send(): udp socket not initialized");
387 return (bytes_sent ==
message.size());
398 #endif // __SICK_SCANSEGMENT_XD_UDP_SOCKETS_H