websocketpp  0.5.1
C++/Boost Asio based websocket client/server library
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Pages
connection.hpp
1 /*
2  * Copyright (c) 2014, Peter Thorson. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions are met:
6  * * Redistributions of source code must retain the above copyright
7  * notice, this list of conditions and the following disclaimer.
8  * * Redistributions in binary form must reproduce the above copyright
9  * notice, this list of conditions and the following disclaimer in the
10  * documentation and/or other materials provided with the distribution.
11  * * Neither the name of the WebSocket++ Project nor the
12  * names of its contributors may be used to endorse or promote products
13  * derived from this software without specific prior written permission.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
16  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
17  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18  * ARE DISCLAIMED. IN NO EVENT SHALL PETER THORSON BE LIABLE FOR ANY
19  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
20  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
21  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
22  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
23  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
24  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25  *
26  */
27 
28 #ifndef WEBSOCKETPP_TRANSPORT_DEBUG_CON_HPP
29 #define WEBSOCKETPP_TRANSPORT_DEBUG_CON_HPP
30 
31 #include <websocketpp/transport/debug/base.hpp>
32 
33 #include <websocketpp/transport/base/connection.hpp>
34 
35 #include <websocketpp/logger/levels.hpp>
36 
37 #include <websocketpp/common/connection_hdl.hpp>
38 #include <websocketpp/common/memory.hpp>
39 #include <websocketpp/common/platforms.hpp>
40 
41 #include <string>
42 #include <vector>
43 
44 namespace websocketpp {
45 namespace transport {
46 namespace debug {
47 
50 struct timer {
51  void cancel() {}
52 };
53 
54 template <typename config>
55 class connection : public lib::enable_shared_from_this< connection<config> > {
56 public:
60  typedef lib::shared_ptr<type> ptr;
61 
63  typedef typename config::concurrency_type concurrency_type;
65  typedef typename config::alog_type alog_type;
67  typedef typename config::elog_type elog_type;
68 
69  // Concurrency policy types
70  typedef typename concurrency_type::scoped_lock_type scoped_lock_type;
71  typedef typename concurrency_type::mutex_type mutex_type;
72 
73  typedef lib::shared_ptr<timer> timer_ptr;
74 
75  explicit connection(bool is_server, alog_type & alog, elog_type & elog)
76  : m_reading(false), m_is_server(is_server), m_alog(alog), m_elog(elog)
77  {
78  m_alog.write(log::alevel::devel,"debug con transport constructor");
79  }
80 
82  ptr get_shared() {
83  return type::shared_from_this();
84  }
85 
87 
94  void set_secure(bool) {}
95 
97 
102  bool is_secure() const {
103  return false;
104  }
105 
107 
120  void set_remote_endpoint(std::string) {}
121 
123 
131  std::string get_remote_endpoint() const {
132  return "unknown (debug transport)";
133  }
134 
136 
140  return connection_hdl();
141  }
142 
144 
153  timer_ptr set_timer(long, timer_handler handler) {
154  m_alog.write(log::alevel::devel,"debug connection set timer");
155  m_timer_handler = handler;
156  return timer_ptr();
157  }
158 
160 
175  size_t read_all(char const * buf, size_t len) {
176  size_t total_read = 0;
177  size_t temp_read = 0;
178 
179  do {
180  temp_read = this->read_some_impl(buf+total_read,len-total_read);
181  total_read += temp_read;
182  } while (temp_read != 0 && total_read < len);
183 
184  return total_read;
185  }
186 
187  // debug stuff to invoke the async handlers
188  void expire_timer(lib::error_code const & ec) {
189  m_timer_handler(ec);
190  }
191 
192  void fullfil_write() {
193  m_write_handler(lib::error_code());
194  }
195 protected:
197 
202  void init(init_handler handler) {
203  m_alog.write(log::alevel::devel,"debug connection init");
204  handler(lib::error_code());
205  }
206 
208 
231  void async_read_at_least(size_t num_bytes, char * buf, size_t len,
232  read_handler handler)
233  {
234  std::stringstream s;
235  s << "debug_con async_read_at_least: " << num_bytes;
236  m_alog.write(log::alevel::devel,s.str());
237 
238  if (num_bytes > len) {
239  handler(make_error_code(error::invalid_num_bytes),size_t(0));
240  return;
241  }
242 
243  if (m_reading == true) {
244  handler(make_error_code(error::double_read),size_t(0));
245  return;
246  }
247 
248  if (num_bytes == 0 || len == 0) {
249  handler(lib::error_code(),size_t(0));
250  return;
251  }
252 
253  m_buf = buf;
254  m_len = len;
255  m_bytes_needed = num_bytes;
256  m_read_handler = handler;
257  m_cursor = 0;
258  m_reading = true;
259  }
260 
262 
273  void async_write(char const *, size_t, write_handler handler) {
274  m_alog.write(log::alevel::devel,"debug_con async_write");
275  m_write_handler = handler;
276  }
277 
279 
289  void async_write(std::vector<buffer> const &, write_handler handler) {
290  m_alog.write(log::alevel::devel,"debug_con async_write buffer list");
291  m_write_handler = handler;
292  }
293 
295 
299 
301 
311  lib::error_code dispatch(dispatch_handler handler) {
312  handler();
313  return lib::error_code();
314  }
315 
317 
321  handler(lib::error_code());
322  }
323 
324  size_t read_some_impl(char const * buf, size_t len) {
325  m_alog.write(log::alevel::devel,"debug_con read_some");
326 
327  if (!m_reading) {
328  m_elog.write(log::elevel::devel,"write while not reading");
329  return 0;
330  }
331 
332  size_t bytes_to_copy = (std::min)(len,m_len-m_cursor);
333 
334  std::copy(buf,buf+bytes_to_copy,m_buf+m_cursor);
335 
336  m_cursor += bytes_to_copy;
337 
338  if (m_cursor >= m_bytes_needed) {
339  complete_read(lib::error_code());
340  }
341 
342  return bytes_to_copy;
343  }
344 
346 
361  void complete_read(lib::error_code const & ec) {
362  m_reading = false;
363 
364  read_handler handler = m_read_handler;
365  m_read_handler = read_handler();
366 
367  handler(ec,m_cursor);
368  }
369 private:
370  timer_handler m_timer_handler;
371 
372  // Read space (Protected by m_read_mutex)
373  char * m_buf;
374  size_t m_len;
375  size_t m_bytes_needed;
376  read_handler m_read_handler;
377  size_t m_cursor;
378 
379  // transport resources
380  connection_hdl m_connection_hdl;
381  write_handler m_write_handler;
382  shutdown_handler m_shutdown_handler;
383 
384  bool m_reading;
385  bool const m_is_server;
386  bool m_is_secure;
387  alog_type & m_alog;
388  elog_type & m_elog;
389  std::string m_remote_endpoint;
390 };
391 
392 
393 } // namespace debug
394 } // namespace transport
395 } // namespace websocketpp
396 
397 #endif // WEBSOCKETPP_TRANSPORT_DEBUG_CON_HPP
ptr get_shared()
Get a shared pointer to this component.
Definition: connection.hpp:82
config::concurrency_type concurrency_type
transport concurrency policy
Definition: connection.hpp:63
lib::shared_ptr< type > ptr
Type of a shared pointer to this connection transport component.
Definition: connection.hpp:60
void set_remote_endpoint(std::string)
Set human readable remote endpoint address.
Definition: connection.hpp:120
void set_handle(connection_hdl)
Set Connection Handle.
Definition: connection.hpp:298
std::string get_remote_endpoint() const
Get human readable remote endpoint address.
Definition: connection.hpp:131
void async_read_at_least(size_t num_bytes, char *buf, size_t len, read_handler handler)
Initiate an async_read for at least num_bytes bytes into buf.
Definition: connection.hpp:231
lib::function< void(lib::error_code const &)> write_handler
The type and signature of the callback passed to the write method.
Definition: connection.hpp:123
static level const devel
Low level debugging information (warning: very chatty)
Definition: levels.hpp:63
lib::weak_ptr< void > connection_hdl
A handle to uniquely identify a connection.
lib::function< void(lib::error_code const &, size_t)> read_handler
The type and signature of the callback passed to the read method.
Definition: connection.hpp:120
config::alog_type alog_type
Type of this transport's access logging policy.
Definition: connection.hpp:65
connection_hdl get_handle() const
Get the connection handle.
Definition: connection.hpp:139
void complete_read(lib::error_code const &ec)
Signal that a requested read is complete.
Definition: connection.hpp:361
static level const devel
Development messages (warning: very chatty)
Definition: levels.hpp:141
void async_write(char const *, size_t, write_handler handler)
Asyncronous Transport Write.
Definition: connection.hpp:273
timer_ptr set_timer(long, timer_handler handler)
Call back a function after a period of time.
Definition: connection.hpp:153
connection< config > type
Type of this connection transport component.
Definition: connection.hpp:58
config::elog_type elog_type
Type of this transport's error logging policy.
Definition: connection.hpp:67
void set_secure(bool)
Set whether or not this connection is secure.
Definition: connection.hpp:94
lib::function< void()> dispatch_handler
The type and signature of the callback passed to the dispatch method.
Definition: connection.hpp:135
lib::function< void(lib::error_code const &)> timer_handler
The type and signature of the callback passed to the read method.
Definition: connection.hpp:126
void init(init_handler handler)
Initialize the connection transport.
Definition: connection.hpp:202
lib::function< void(lib::error_code const &)> shutdown_handler
The type and signature of the callback passed to the shutdown method.
Definition: connection.hpp:129
Namespace for the WebSocket++ project.
Definition: base64.hpp:41
lib::function< void(lib::error_code const &)> init_handler
The type and signature of the callback passed to the init hook.
Definition: connection.hpp:117
lib::error_code dispatch(dispatch_handler handler)
Call given handler back within the transport's event system (if present)
Definition: connection.hpp:311
void async_write(std::vector< buffer > const &, write_handler handler)
Asyncronous Transport Write (scatter-gather)
Definition: connection.hpp:289
void async_shutdown(shutdown_handler handler)
Perform cleanup on socket shutdown_handler.
Definition: connection.hpp:320
bool is_secure() const
Tests whether or not the underlying transport is secure.
Definition: connection.hpp:102
size_t read_all(char const *buf, size_t len)
Manual input supply (read all)
Definition: connection.hpp:175