2323#include " portable_archive/portable_oarchive.hpp"
2424
2525using namespace lslboost ::asio;
26+ using err_t = const lslboost::system::error_code &;
2627
2728namespace lsl {
2829/* *
@@ -77,16 +78,9 @@ class client_session : public std::enable_shared_from_this<client_session> {
7778 // / Handler that gets called after finishing reading of the query line.
7879 void handle_read_query_outcome (error_code err);
7980
80- // / Handler that gets called after finishing the sending of a reply (nothing to do here).
81- void handle_send_outcome (error_code) {}
82-
8381 // / Helper function to send a status message to the connected party.
8482 void send_status_message (const std::string &msg);
8583
86- // / Handler that gets called after finishing the sending of a message, holding a reference
87- // / to the message.
88- void handle_status_outcome (string_p, error_code) {}
89-
9084 // / Handler that gets called after finishing the reading of feedparameters.
9185 void handle_read_feedparams (
9286 int request_protocol_version, std::string request_uid, error_code err);
@@ -188,7 +182,8 @@ void tcp_server::end_serving() {
188182 shutdown_ = true ;
189183 // issue closure of the server socket; this will result in a cancellation of the associated IO
190184 // operations
191- post (*io_, lslboost::bind (&tcp::acceptor::close, acceptor_));
185+ auto keepalive (acceptor_);
186+ post (*io_, [keepalive]() { keepalive->close (); });
192187 // issue closure of all active client session sockets; cancels the related outstanding IO jobs
193188 close_inflight_sockets ();
194189 // also notify any transfer threads that are blocked waiting for a sample by sending them one (=
@@ -204,9 +199,9 @@ void tcp_server::accept_next_connection() {
204199 std::shared_ptr<client_session> newsession{
205200 std::make_shared<client_session>(shared_from_this ())};
206201 // accept a connection on the session's socket
207- acceptor_-> async_accept (
208- *newsession->socket (), lslboost::bind (&tcp_server::handle_accept_outcome ,
209- shared_from_this (), newsession, placeholders::error) );
202+ auto keepalive ( shared_from_this ());
203+ acceptor_-> async_accept ( *newsession->socket (),
204+ [keepalive, newsession, this ]( err_t err) { handle_accept_outcome ( newsession, err); } );
210205 } catch (std::exception &e) {
211206 LOG_F (ERROR, " Error during tcp_server::accept_next_connection: %s" , e.what ());
212207 }
@@ -234,22 +229,22 @@ void tcp_server::unregister_inflight_socket(const tcp_socket_p &sock) {
234229 inflight_.erase (sock);
235230}
236231
237- template <class SocketPtr , class Protocol > void shutdown_and_close (SocketPtr sock) {
238- try {
239- if (sock->is_open ()) {
240- try {
241- // (in some cases shutdown may fail)
242- sock->shutdown (Protocol::socket::shutdown_both);
243- } catch (...) {}
244- sock->close ();
245- }
246- } catch (std::exception &e) { LOG_F (WARNING, " Error during shutdown_and_close: %s" , e.what ()); }
247- }
248-
249232void tcp_server::close_inflight_sockets () {
250233 lslboost::lock_guard<lslboost::recursive_mutex> lock (inflight_mut_);
251- for (const auto &i : inflight_)
252- post (*io_, lslboost::bind (&shutdown_and_close<tcp_socket_p, tcp>, i));
234+ for (auto sock : inflight_)
235+ post (*io_, [sock]() {
236+ try {
237+ if (sock->is_open ()) {
238+ try {
239+ // (in some cases shutdown may fail)
240+ sock->shutdown (sock->shutdown_both );
241+ } catch (...) {}
242+ sock->close ();
243+ }
244+ } catch (std::exception &e) {
245+ LOG_F (WARNING, " Error during shutdown_and_close: %s" , e.what ());
246+ }
247+ });
253248}
254249
255250
@@ -272,9 +267,9 @@ void client_session::begin_processing() {
272267 serv_->register_inflight_socket (sock_);
273268 registered_ = true ;
274269 // read the request line
270+ auto keepalive (shared_from_this ());
275271 async_read_until (*sock_, requestbuf_, " \r\n " ,
276- lslboost::bind (&client_session::handle_read_command_outcome, shared_from_this (),
277- placeholders::error));
272+ [keepalive, this ](err_t err, size_t ) { handle_read_command_outcome (err); });
278273 } catch (std::exception &e) {
279274 LOG_F (ERROR, " Error during client_session::begin_processing: %s" , e.what ());
280275 }
@@ -287,29 +282,29 @@ void client_session::handle_read_command_outcome(error_code err) {
287282 std::string method;
288283 getline (requeststream_, method);
289284 method = trim (method);
285+ auto keepalive (shared_from_this ());
290286 if (method == " LSL:shortinfo" )
291287 // shortinfo request: read the content query string
292288 async_read_until (*sock_, requestbuf_, " \r\n " ,
293- lslboost::bind (&client_session::handle_read_query_outcome, shared_from_this (),
294- placeholders::error));
289+ [keepalive, this ](err_t err, std::size_t ) { handle_read_query_outcome (err); });
295290 if (method == " LSL:fullinfo" )
296291 // fullinfo request: reply right away
297292 async_write (*sock_, lslboost::asio::buffer (serv_->fullinfo_msg_ ),
298- lslboost::bind (&client_session::handle_send_outcome, shared_from_this (),
299- placeholders::error));
293+ [keepalive, this ](err_t , std::size_t ) { });
300294 if (method == " LSL:streamfeed" )
301295 // streamfeed request (1.00): read feed parameters
302- async_read_until (*sock_, requestbuf_, " \r\n " ,
303- lslboost::bind (&client_session::handle_read_feedparams, shared_from_this (), 100 ,
304- " " , placeholders::error));
296+ async_read_until (
297+ *sock_, requestbuf_, " \r\n " , [keepalive, this ](err_t err, std::size_t ) {
298+ handle_read_feedparams (100 , " " , err);
299+ });
305300 if (method.compare (0 , 15 , " LSL:streamfeed/" ) == 0 ) {
306301 // streamfeed request with version: read feed parameters
307302 std::vector<std::string> parts = splitandtrim (method, ' ' , true );
308303 int request_protocol_version = std::stoi (parts[0 ].substr (15 ));
309304 std::string request_uid = (parts.size () > 1 ) ? parts[1 ] : " " ;
310- async_read_until (*sock_, requestbuf_, " \r\n\r\n " ,
311- lslboost::bind (&client_session:: handle_read_feedparams, shared_from_this (),
312- request_protocol_version, request_uid, placeholders::error) );
305+ async_read_until (*sock_, requestbuf_, " \r\n\r\n " , [=]( err_t err, std:: size_t ) {
306+ keepalive-> handle_read_feedparams (request_protocol_version, request_uid, err);
307+ } );
313308 }
314309 }
315310 } catch (std::exception &e) {
@@ -324,12 +319,14 @@ void client_session::handle_read_query_outcome(error_code err) {
324319 std::string query;
325320 getline (requeststream_, query);
326321 query = trim (query);
327- if (serv_->info_ ->matches_query (query))
322+ if (serv_->info_ ->matches_query (query)) {
328323 // matches: reply (otherwise just close the stream)
324+ auto keepalive (shared_from_this ());
329325 async_write (*sock_, lslboost::asio::buffer (serv_->shortinfo_msg_ ),
330- lslboost::bind (&client_session::handle_send_outcome, shared_from_this (),
331- placeholders::error));
332- else
326+ [keepalive](err_t , std::size_t ) {
327+ /* keep the client_session alive until the shortinfo is sent completely*/
328+ });
329+ } else
333330 LOG_F (INFO, " %p got a shortinfo query response for the wrong query" , this );
334331 }
335332 } catch (std::exception &e) {
@@ -338,10 +335,11 @@ void client_session::handle_read_query_outcome(error_code err) {
338335}
339336
340337void client_session::send_status_message (const std::string &str) {
341- string_p msg (std::make_shared<std::string>(str));
338+ auto msg (std::make_shared<std::string>(str));
339+ auto keepalive (shared_from_this ());
342340 async_write (*sock_, lslboost::asio::buffer (*msg),
343- lslboost::bind (
344- &client_session::handle_status_outcome, shared_from_this (), msg, placeholders::error) );
341+ [msg, keepalive] (
342+ err_t , std:: size_t ) { /* keep objects alive until the message is sent */ } );
345343}
346344
347345void client_session::handle_read_feedparams (
@@ -489,9 +487,10 @@ void client_session::handle_read_feedparams(
489487 else
490488 *outarch_ << *temp;
491489 // send off the newly created feedheader
492- async_write (*sock_, feedbuf_.data (),
493- lslboost::bind (&client_session::handle_send_feedheader_outcome, shared_from_this (),
494- placeholders::error, placeholders::bytes_transferred));
490+ auto keepalive (shared_from_this ());
491+ async_write (*sock_, feedbuf_.data (), [keepalive, this ](err_t err, size_t len) {
492+ handle_send_feedheader_outcome (err, len);
493+ });
495494 DLOG_F (4 , " %p sent test pattern samples" , this );
496495 }
497496 } catch (std::exception &e) {
@@ -545,10 +544,10 @@ void client_session::transfer_samples_thread(std::shared_ptr<client_session>) {
545544 // send off the chunk that we aggregated so far
546545 lslboost::unique_lock<lslboost::mutex> lock (completion_mut_);
547546 transfer_completed_ = false ;
548- async_write (*sock_, feedbuf_. data (),
549- lslboost::bind (&client_session::handle_chunk_transfer_outcome,
550- shared_from_this (), placeholders::error,
551- placeholders::bytes_transferred) );
547+ auto keepalive ( shared_from_this ());
548+ async_write (*sock_, feedbuf_. data (), [keepalive, this ]( err_t err, size_t len) {
549+ handle_chunk_transfer_outcome (err, len);
550+ } );
552551 // wait for the completion condition
553552 completion_cond_.wait (lock, [this ]() { return transfer_completed_; });
554553 // handle transfer outcome
0 commit comments