获取TCP连接的随机端口

时间:2013-12-26 18:00:15

标签: c++ linux sockets tcp port

我有一个客户端和一个服务器应用程序。当客户端想要发送文件我正在使用TCP连接。当我使用常量端口号进行连接时(服务器接收文件)。

我想使用随机端口,所以我尝试将端口设置为0。

我的代码是:

bzero((char *) &serv_addr, sizeof(serv_addr));
serv_addr.sin_family = AF_INET;
serv_addr.sin_addr.s_addr = INADDR_ANY;
serv_addr.sin_port = 0;

if (bind(sockfd, (struct sockaddr *) &serv_addr, sizeof(serv_addr)) < 0){
    cout << "failed to bind with errno: "<< errno << endl;
    exit(1);
}

绑定有效,但是端口0而不是预期的随机端口。

我做错了什么?

4 个答案:

答案 0 :(得分:5)

嗯,问题解决了。我添加了对getsocketname

的调用
if (getsockname(sockfd, (struct sockaddr *)&serv_addr, &len_inet) < 0){
    cout << "failed to get hostname with errno: "<< errno << endl;
    exit(1);
}

答案 1 :(得分:3)

bind()不会更新您传递给它的地址结构。这是const参数。如果您想知道在指定零时选择了哪个端口,则必须使用getsockname().

答案 2 :(得分:0)

这个小型C工具可以帮助您:https://github.com/yegor256/random-tcp-port

只需使用make进行编译,然后运行./reserve

答案 3 :(得分:-1)

当您可以使用增强功能时,这看起来更加明显并且可以移植:

#include <boost/asio/io_service.hpp>
#include <boost/asio/ip/tcp.hpp>

int getFreeTCPPort(std::string ipv4)
{
  using namespace boost::asio;

  io_service service;
  ip::tcp::socket socket(service);
  socket.open(ip::tcp::v4());
  socket.bind(ip::tcp::endpoint(ip::address::from_string(ipv4), 0));
  return socket.local_endpoint().port();
}

可以肯定的是,它并不能直接回答您的问题,但是当代码不言自明时,也许问题就不会出现了。