I’m writing a server with Boost, something pretty simple – accept an XML message, process, reply. But I’m running into trouble at telling it when to stop reading.
This is what I have right now: (_index is the buffer into which the data is read)
std::size_t tcp_connection::completion_condition(const boost::system::error_code& error,
std::size_t bytes_transferred)
{
int ret = -1;
std::istream is(&_index);
std::string s;
is >> s;
if (s.find("</end_tag>") != std::string.npos) ret = 0;
return ret;
}
void tcp_connection::start()
{
// Get index from server
boost::asio::async_read(_socket, _index, &(tcp_connection::completion_condition),
boost::bind(&tcp_connection::handle_read, shared_from_this(), boost::asio::placeholders::error,
boost::asio::placeholders::bytes_transferred));
}
This doesn’t compile, since I have to define completion_condition as static to pass it to async_read; and I can’t define _index as static since (obviously) I need it to be specific to the class.
Is there some other way to give parameters to completion_condition? How do I get it to recognize the ending tag and call the reading handler?
You can pass pointers to member functions. The syntax for doing it with C++ is tricky, but
boost::bindhides it and makes it fairly easy to do.An example would be making
completion_conditionnon-static and passing it toasync_readas such:boost::bind(&tcp_connection::completion_condition, this, _1, _2)&tcp_connection::completion_conditionis a pointer to the function.thisis the object of typetcp_connectionto call the function on._1and_2are placeholders; they will be replaced with the two parameters the function is called with.