Fawkes API  Fawkes Development Version
client.h
1 
2 /***************************************************************************
3  * client.h - Protobuf stream protocol - client
4  *
5  * Created: Thu Jan 31 17:28:09 2013
6  * Copyright 2013 Tim Niemueller [www.niemueller.de]
7  ****************************************************************************/
8 
9 /* Redistribution and use in source and binary forms, with or without
10  * modification, are permitted provided that the following conditions
11  * are met:
12  *
13  * - Redistributions of source code must retain the above copyright
14  * notice, this list of conditions and the following disclaimer.
15  * - Redistributions in binary form must reproduce the above copyright
16  * notice, this list of conditions and the following disclaimer in
17  * the documentation and/or other materials provided with the
18  * distribution.
19  * - Neither the name of the authors nor the names of its contributors
20  * may be used to endorse or promote products derived from this
21  * software without specific prior written permission.
22  *
23  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
24  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
26  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
27  * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT,
28  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
29  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
30  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
31  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
32  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
33  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
34  * OF THE POSSIBILITY OF SUCH DAMAGE.
35  */
36 
37 #ifndef __PROTOBUF_COMM_CLIENT_H_
38 #define __PROTOBUF_COMM_CLIENT_H_
39 
40 #include <protobuf_comm/frame_header.h>
41 #include <protobuf_comm/message_register.h>
42 #include <protobuf_comm/queue_entry.h>
43 
44 #include <boost/asio.hpp>
45 #include <boost/signals2.hpp>
46 #include <google/protobuf/message.h>
47 #include <queue>
48 #include <string>
49 #include <mutex>
50 #include <thread>
51 #include <cstdint>
52 
53 namespace protobuf_comm {
54 #if 0 /* just to make Emacs auto-indent happy */
55 }
56 #endif
57 
58 
60 {
61  public:
63  ProtobufStreamClient(std::vector<std::string> &proto_path);
64  ProtobufStreamClient(MessageRegister *mr, frame_header_version_t header_version = PB_FRAME_V2);
66 
67  /** Get the client's message register.
68  * @return message register
69  */
71  { return *message_register_; }
72 
73  void async_connect(const char *host, unsigned short port);
74  void disconnect();
75 
76  /** Check if client is connected.
77  * @return true if the client is connected, false otherwise
78  */
79  bool connected() const
80  { return connected_; }
81 
82  void send(uint16_t component_id, uint16_t msg_type,
83  google::protobuf::Message &m);
84 
85  void send(std::shared_ptr<google::protobuf::Message> m);
86  void send(google::protobuf::Message &m);
87 
88  /** Signal that is invoked when a message has been received.
89  * @return signal
90  */
91  boost::signals2::signal<void (uint16_t, uint16_t,
92  std::shared_ptr<google::protobuf::Message>)> &
93  signal_received() { return sig_rcvd_; }
94 
95  /** Signal that is invoked when receiving a message failed.
96  * @return signal
97  */
98  boost::signals2::signal<void (uint16_t, uint16_t, std::string)> &
99  signal_receive_failed() { return sig_recv_failed_; }
100 
101  /** Signal that is invoked when the connection has been established.
102  * @return signal
103  */
104  boost::signals2::signal<void ()> &
105  signal_connected() { return sig_connected_; }
106 
107  /** Signal that is invoked when the connection is closed.
108  * @return signal
109  */
110  boost::signals2::signal<void (const boost::system::error_code &)> &
111  signal_disconnected() { return sig_disconnected_; }
112 
113  private: // types
114 
115  private: // methods
116  void disconnect_nosig();
117  void run_asio();
118  void handle_resolve(const boost::system::error_code& err,
119  boost::asio::ip::tcp::resolver::iterator endpoint_iterator);
120  void handle_connect(const boost::system::error_code& err);
121  void handle_write(const boost::system::error_code& error,
122  size_t /*bytes_transferred*/, QueueEntry *entry);
123  void start_recv();
124  void handle_read_header(const boost::system::error_code& error);
125  void handle_read_message(const boost::system::error_code& error);
126 
127  private: // members
128  bool connected_;
129  std::mutex asio_mutex_;
130  boost::asio::io_service io_service_;
131  boost::asio::ip::tcp::resolver resolver_;
132  boost::asio::ip::tcp::socket socket_;
133  boost::asio::io_service::work io_service_work_;
134 
135  boost::signals2::signal<void (uint16_t, uint16_t,
136  std::shared_ptr<google::protobuf::Message>)> sig_rcvd_;
137  boost::signals2::signal<void (uint16_t, uint16_t, std::string)> sig_recv_failed_;
138  boost::signals2::signal<void ()> sig_connected_;
139  boost::signals2::signal<void (const boost::system::error_code &)> sig_disconnected_;
140 
141  std::thread asio_thread_;
142 
143  std::queue<QueueEntry *> outbound_queue_;
144  std::mutex outbound_mutex_;
145  bool outbound_active_;
146 
147  void *in_frame_header_;
148  size_t in_frame_header_size_;
149  size_t in_data_size_;
150  void * in_data_;
151 
152  MessageRegister *message_register_;
153  bool own_message_register_;
154 
155  frame_header_version_t frame_header_version_;
156 };
157 
158 } // end namespace protobuf_comm
159 
160 #endif
Outgoing queue entry.
Definition: queue_entry.h:49
Register to map msg type numbers to Protobuf messages.
ProtobufStreamClient()
Constructor.
Definition: client.cpp:57
void disconnect()
Disconnect from remote host.
Definition: client.cpp:225
boost::signals2::signal< void(uint16_t, uint16_t, std::shared_ptr< google::protobuf::Message >)> & signal_received()
Signal that is invoked when a message has been received.
Definition: client.h:93
boost::signals2::signal< void(uint16_t, uint16_t, std::string)> & signal_receive_failed()
Signal that is invoked when receiving a message failed.
Definition: client.h:99
void send(uint16_t component_id, uint16_t msg_type, google::protobuf::Message &m)
Send a message to the server.
Definition: client.cpp:351
void async_connect(const char *host, unsigned short port)
Asynchronous connect.
Definition: client.cpp:154
boost::signals2::signal< void()> & signal_connected()
Signal that is invoked when the connection has been established.
Definition: client.h:105
bool connected() const
Check if client is connected.
Definition: client.h:79
boost::signals2::signal< void(const boost::system::error_code &)> & signal_disconnected()
Signal that is invoked when the connection is closed.
Definition: client.h:111
Stream client for protobuf message transmission.
Definition: client.h:59
MessageRegister & message_register()
Get the client&#39;s message register.
Definition: client.h:70