其他分享
首页 > 其他分享> > QTcpServer之(The bound address is already in use)问题

QTcpServer之(The bound address is already in use)问题

作者:互联网

问题

每次kill掉该服务器进程并重新启动的时候,都会出现bind错误:error:98,Address already in use

问题产生原因

1、一般来说,一个端口释放后会等待两分钟之后才能再被使用,SO_REUSEADDR是让端口释放后立即就可以被再次使用。
SO_REUSEADDR用于对TCP套接字处于TIME_WAIT状态下的socket,才可以重复绑定使用。server程序总是应该在调用bind()之前设置SO_REUSEADDR套接字选项。TCP,先调用close()的一方会进入TIME_WAIT状态

具体代码

#ifdef Q_OS_UNIX
#include <QtNetwork/private/qnativesocketengine_p.h>
#include <QtNetwork/private/qnet_unix_p.h>
#endif
bool listen(const QHostAddress &address, ushort port)
{
#ifdef Q_OS_UNIX
//    int listenfd = qt_safe_socket(AF_INET,SOCK_STREAM,0);
//    struct sockaddr_in servaddr;
//    //先把地址清空,检测任意IP
//    memset(&servaddr,0,sizeof(servaddr));
//    servaddr.sin_family = AF_INET;
//    servaddr.sin_addr.s_addr = htonl(INADDR_ANY);
//    servaddr.sin_port = htons(21846);

//    int reuse = 1;
//    if(0 != setsockopt(listenfd, SOL_SOCKET, SO_REUSEADDR, &reuse, sizeof(reuse)))
//    {
//        printf("can not setsockopt");
//        return 0;
//    }
//    //地址绑定到listenfd
//    if ( bind(listenfd, (struct sockaddr*)&servaddr, sizeof(servaddr)) == -1) {
//        qDebug() << " bind socket error: %s (errno :" << errno;
//        return 0;
//    }
//    //监听listenfd
//    if( qt_safe_listen(listenfd,10) == -1) {
//        qDebug() << " listen socket error: %s (errno :)\n" << errno;
//        return 0;
//    }

//    qDebug() << "====waiting for client's request=======";
//    m_server->setSocketDescriptor(listenfd);
//    qDebug() << "listen state" << m_server->isListening();
    QTcpSocket *p = new QTcpSocket(this);
     if(p->bind(address, port, QAbstractSocket::ReuseAddressHint))
{
         int listenfd = (int)p->socketDescriptor();
        //监听listenfd
        if( qt_safe_listen(listenfd,10) == -1) {
            qDebug() << " listen socket error: %s (errno :)\n" << errno;
            return 0;
        }
            m_server->setSocketDescriptor(listenfd);
            qDebug() << "listen state" << m_server->isListening();
}
     else{
         qDebug() << "create listen socket error";
     }
  return true;
}
#endif

补充说明TIME_WAIT有什么意义

(1)可靠地实现TCP全双工连接的终止;

(2)允许老的重复分节在网络中消逝。

参考

Socket中SO_REUSEADDR详解
time_wait状态产生的原因,危害,如何避免

标签:QTcpServer,use,already,REUSEADDR,listenfd,int,SO,qDebug,servaddr
来源: https://blog.csdn.net/Black_Silencer/article/details/115068820