0

I'm having some trouble when putting a very simple c++ program to listen to a given port. Mainly, I have problems when creating a basic_resolver_query. If I do it like this:

boost::asio::ip::tcp::resolver::query query( "0.0.0.0", "5938" );

i works flawlessly. But obviously I don't want to hardcode the port, so I've been trying to read it from a file an passing it there: it isn't working.

If I try to pass it directly as std::string, it doesn't work, with I guess was to be expected. But I've tried passing m_listenPort.c_string() and it doesn't do it.

I've been trying to look in the documentation, and in examples, but I can find nothing. How do I have to do it?

Jk041
  • 934
  • 1
  • 15
  • 33

3 Answers3

4

As best as I can tell, boost::asio::ip::basic_resolver_query has been constructable with two std::string arguments since Boost.Asio was introduced. Here is the overloaded constructor documentation in 1.35 and 1.53.

#include <string>
#include <boost/asio.hpp>

int main()
{
  std::string host = "127.0.0.1";
  std::string port = "1234";
  using boost::asio::ip::tcp;
  tcp::resolver::query query1("127.0.0.1", "1234");
  tcp::resolver::query query2(host, port);
  tcp::resolver::query query3(host.c_str(), port.c_str());
}

Is it possible that you are not using std::string or a type that provides a user-defined conversion to a type from which std::string can be constructed? For instance, std::string provides c_str(), not c_string(). Additionally, it is constructable via const char*, not const unsigned char* or const signed char*, as the three types are distinct.

Tanner Sansbury
  • 51,153
  • 9
  • 112
  • 169
  • Interesting, there indeed are 3 char types (signed, unsigned and plain): http://stackoverflow.com/questions/436513/char-signed-char-char-unsigned-char – Paul Jul 21 '16 at 13:34
2

The following works for me:

std::string host = "192.168.1.1", port = "1234";
tcp::resolver::query query(tcp::v4(), host, port);
Igor R.
  • 14,716
  • 2
  • 49
  • 83
1

I also had some problems when trying to use an IP address instead of a URL. Discovered the technique of creating an endpoint and using it in the connect method on the next_layer object off of the socket object works for me:

const boost::asio::ip::address IP(boost::asio::ip::address::from_string(serverPath));
int iport = atoi(port.c_str());
const boost::asio::ip::tcp::endpoint EP(IP, iport);
// Set up an SSL context.
boost::asio::ssl::context ctx(*IOService, boost::asio::ssl::context::tlsv1_client);
// Specify to not verify the server certificiate right now.
ctx.set_verify_mode(boost::asio::ssl::context::verify_none);
// Init the socket object used to initially communicate with the server.
pSocket = new boost::asio::ssl::stream<boost::asio::ip::tcp::socket>(*IOService, ctx);
//
// Try to connect to the server.  Note - add timeout logic at some point.
boost::system::error_code EC;
pSocket->next_layer().connect(EP, EC);
if (EC)
{
   // Log an error.  This worker thread should exit gracefully after this.
   stringstream ss;
   ss << "SSLSocket::Connect: connect failed to " << sClientIp << " : " << uiClientPort << ".  Error: " << EC.message() + ".\n";
   Log.LogString(ss.str(), LogError);
}
Bob Bryan
  • 3,687
  • 1
  • 32
  • 45