在QT4下绑定TCP客户端的IP和端口 [bind QTcpSocket HOWTO]

it2024-12-19  5

Author F32 (feng32@163.com)

The code is released under the terms of GNU Lesser General Public License version 2.1

Here's the code.

1 #ifndef Q_BOUND_TCP_SOCKET_H 2 #define Q_BOUND_TCP_SOCKET_H 3 4 #include <QTcpSocket> 5 6 /** 7 * \brief The QBoundTcpSocket class adds binding support 8 * to tcp client sockets. 9 *10 * In Qt 4, it's impossible to bind a tcp client socket to11 * a specific port or ip address.12 *13 * This feature has been added to Qt 5, however with version 4, 14 * it's still possible to do binding while getting convenience from15 * the Qt framework.16 * 17 * Note:18 * 19 * Due to usage of native api, the class currently not supports20 * platforms other than Linux. If you are familiar with 21 * native programming interfaces like winsock, porting the code22 * to other operations systems may be just a piece of cake.23 * 24 * A QBoundTcpSocket object will bind and connect to the server25 * at the same time, because the only way to work around is to26 * create a socket, bind, connect to server with native API from the27 * OS, and then pass the socket to QTcpSocket::setSocketDescriptor28 * with a connected state.29 */30 31 class QBoundTcpSocket : public QTcpSocket32 {33 public:34 /**35 * \brief Bind the socket and then connect to server36 *37 * Note:38 * 39 * Before calling, the socket must be in the unconnected state, 40 * otherwise a value of false is returned.41 * 42 * Typical usage:43 * \code44 * QBoundTcpSocket socket;45 * if (socket.bindAndConnect("192.168.1.10", 0, "10.0.0.1", 80))46 * {47 * // Now bound and connected48 * }49 * else50 * {51 * qDebug() << "An error occurred in QBoundTcpSocket::bindAndConnect";52 * }53 * \endcode54 *55 * \param localAddr Local IP address (e.g., "10.0.0.10").56 * A value of "0.0.0.0" indicates that 57 * the default ip address will be used.58 * \param localPort Local port (e.g., 12345). 59 * A value of 0 indicates that any port is acceptable.60 * \param serverAddr IP address of the server (e.g., "10.0.0.1")61 * \param serverPort Port of the server (e.g., 80)62 *63 * \return The return value is true when both binding and connecting 64 * are successful, and false otherwise.65 */66 bool bindAndConnect(const QString &localAddr, quint16 localPort, 67 const QString &serverAddr, quint16 serverPort);68 };69 70 #endif /* Q_BOUND_TCP_SOCKET_H */

 

1 #include "QBoundTcpSocket.h" 2 3 #ifdef Q_OS_LINUX 4 #include <arpa/inet.h> 5 #endif 6 7 bool QBoundTcpSocket::bindAndConnect(const QString &localAddr, quint16 localPort, 8 const QString &serverAddr, quint16 serverPort) 9 {10 #ifdef Q_OS_LINUX11 int sockfd;12 int result;13 struct sockaddr_in localSockAddr;14 struct sockaddr_in serverSockAddr;15 bzero(&localSockAddr, sizeof(localSockAddr));16 bzero(&serverSockAddr, sizeof(serverSockAddr));17 18 // create socket19 sockfd = socket(AF_INET, SOCK_STREAM, 0);20 if( sockfd == -1 ) 21 {22 qDebug() << "QBoundTcpSocket: Cannot create socket";23 return false;24 }25 26 // bind27 localSockAddr.sin_family = AF_INET;28 localSockAddr.sin_port = htons(localPort);29 localSockAddr.sin_addr.s_addr = inet_addr(localAddr.toLocal8Bit().data());30 31 result = bind(sockfd, (struct sockaddr *)&localSockAddr, sizeof(localSockAddr));32 if( result == -1 ) 33 {34 qDebug() << "QBoundTcpSocket: Cannot bind socket";35 return false;36 }37 38 // connect39 serverSockAddr.sin_family = AF_INET;40 serverSockAddr.sin_port = htons(serverPort);41 serverSockAddr.sin_addr.s_addr = inet_addr(serverAddr.toLocal8Bit().data());42 43 result = ::connect(sockfd, (struct sockaddr *)&serverSockAddr, sizeof(serverSockAddr));44 if( result == -1 ) 45 {46 qDebug() << "QBoundTcpSocket: Cannot connect to server";47 return false;48 }49 50 // set socket descriptor51 if( !setSocketDescriptor(sockfd, QAbstractSocket::ConnectedState))52 {53 qDebug() << "QBoundTcpSocket: Cannot set socket descriptor";54 return false;55 }56 57 return true;58 #else59 qDebug() << "QBoundTcpSocket for Windows/Mac OS is not implemented yet";60 return false;61 #endif62 }

转载于:https://www.cnblogs.com/F-32/archive/2012/03/23/2414204.html

相关资源:通过c++11的std::bind及std::function实现类方法回调,模拟Qt实现信号槽
最新回复(0)