00001 // Copyright (c) 2014, Pepperl+Fuchs GmbH, Mannheim 00002 // Copyright (c) 2014, Denis Dillenberger 00003 // All rights reserved. 00004 // 00005 // Use, modification, and distribution is subject to the 00006 // 3-clause BSD license ("Revised BSD License", 00007 // "New BSD License", or "Modified BSD License") 00008 // You should have received a copy of this license 00009 // in a file named COPYING or LICENSE. 00010 00011 #ifndef SCAN_DATA_RECEIVER_H 00012 #define SCAN_DATA_RECEIVER_H 00013 00014 #define BOOST_CB_DISABLE_DEBUG 00015 #include <string> 00016 #include <iostream> 00017 #include <mutex> 00018 #include <condition_variable> 00019 #include <deque> 00020 #include <array> 00021 #include <boost/bind.hpp> 00022 #include <boost/asio.hpp> 00023 #include <boost/thread.hpp> 00024 #include <boost/circular_buffer.hpp> 00025 #include <pepperl_fuchs_r2000/packet_structure.h> 00026 00027 namespace pepperl_fuchs { 00028 00032 class ScanDataReceiver 00033 { 00034 public: 00036 ScanDataReceiver(const std::string hostname, const int tcp_port); 00037 00039 ScanDataReceiver(); 00040 00042 ~ScanDataReceiver(); 00043 00045 int getUDPPort() const { return udp_port_; } 00046 00048 bool isConnected() const { return is_connected_; } 00049 00051 void disconnect(); 00052 00057 ScanData getScan(); 00058 00062 ScanData getFullScan(); 00063 00065 std::size_t getScansAvailable() const { return scan_data_.size(); } 00066 00068 std::size_t getFullScansAvailable() const; 00069 00070 private: 00072 void handleSocketRead(const boost::system::error_code& error); 00073 00075 void handleSocketRead(const boost::system::error_code& error, std::size_t bytes_transferred); 00076 00079 bool handleNextPacket(); 00080 00083 int findPacketStart(); 00084 00087 bool retrievePacket( std::size_t start, PacketTypeC* p ); 00088 00091 bool checkConnection(); 00092 00096 void readBufferFront(char* dst, std::size_t numbytes ); 00097 00101 void writeBufferBack(char* src, std::size_t numbytes ); 00102 00104 int udp_port_; 00105 00107 bool is_connected_; 00108 00110 boost::thread io_service_thread_; 00111 boost::asio::io_service io_service_; 00112 00114 boost::asio::streambuf inbuf_; 00115 00117 std::istream instream_; 00118 00120 boost::asio::ip::tcp::socket* tcp_socket_; 00121 00123 boost::asio::ip::udp::socket* udp_socket_; 00124 00126 boost::asio::ip::udp::endpoint udp_endpoint_; 00127 00129 std::array< char, 65536 > udp_buffer_; 00130 00132 boost::circular_buffer<char> ring_buffer_; 00133 00135 std::mutex data_mutex_; 00136 00138 std::condition_variable data_notifier_; 00139 00141 std::deque<ScanData> scan_data_; 00142 00144 double last_data_time_; 00145 }; 00146 00147 } 00148 #endif // SCAN_DATA_RECEIVER_H