Uploaded image for project: 'Qt'
  1. Qt
  2. QTBUG-75189

Unable to Setup Asynchronous QTcpSocket Connection with QApplications

    XMLWordPrintable

Details

    • Bug
    • Resolution: Unresolved
    • P4: Low
    • None
    • 5.12.2
    • Network
    • None
    • MacOSX High Sierra (10.13.6)
    • macOS

    Description

      Running the following code on MacOSX:

      #include <QApplication>
      #include <QDebug>
      #include <QTcpSocket>
      #include <QTimer>
      
      #include <cstdint>
      
      static const char * const kHostName = "127.0.0.1";
      static const std::uint16_t kPort = 2344;
      
      int main(int argc, char* argv[])
      {
         QApplication app(argc, argv);   // change type to QCoreApplication for it to work
      
         QTcpSocket socket;
      
         QObject::connect(&socket, &QTcpSocket::stateChanged, [](QAbstractSocket::SocketState state)
         {
            qDebug() << "state changed:" << state;
         });
      
         QObject::connect(&socket, static_cast<void(QTcpSocket::*)(QAbstractSocket::SocketError)>(&QTcpSocket::error), [](QAbstractSocket::SocketError error)
         {
            qDebug() << "error:" << error;
         });
      
         socket.connectToHost(kHostName, kPort);
      
         return app.exec();
      }
      

      Produces: 

      state changed: QAbstractSocket::HostLookupState
      state changed: QAbstractSocket::ConnectingState
      

      Then after some time has passed it appends the following to the stdout:

      state changed: QAbstractSocket::UnconnectedState
      error: QAbstractSocket::SocketTimeoutError

      However if we change the QApplication to QCoreAppliction the results immediately output the following:

      state changed: QAbstractSocket::HostLookupState
      state changed: QAbstractSocket::ConnectingState
      state changed: QAbstractSocket::UnconnectedState
      error: QAbstractSocket::ConnectionRefusedError
      

      The expectation is that there should be no difference in results. Going off the documentation for QTcpSocket.

      void QAbstractSocket::connectToHost(const QString &hostName, quint16 port, QIODevice::OpenMode openMode = ReadWrite, QAbstractSocket::NetworkLayerProtocol protocol = AnyIPProtocol)
      
      Attempts to make a connection to hostName on the given port. The protocol parameter can be used to specify which network protocol to use (eg. IPv4 or IPv6).
      
      The socket is opened in the given openMode and first enters HostLookupState, then performs a host name lookup of hostName. If the lookup succeeds, hostFound() is emitted and QAbstractSocket enters ConnectingState. It then attempts to connect to the address or addresses returned by the lookup. Finally, if a connection is established, QAbstractSocket enters ConnectedState and emits connected().
      
      At any point, the socket can emit error() to signal that an error occurred.
      
      hostName may be an IP address in string form (e.g., "43.195.83.32"), or it may be a host name (e.g., "example.com"). QAbstractSocket will do a lookup only if required. port is in native byte order.

       You could get around this issue by using QTcpSocket::waitForConnected() but that would break the asynchornous nature of the code.

      Attachments

        No reviews matched the request. Check your Options in the drop-down menu of this sections header.

        Activity

          People

            cnn Qt Core & Network
            rodrigor Rodrigo Reichert
            Votes:
            1 Vote for this issue
            Watchers:
            3 Start watching this issue

            Dates

              Created:
              Updated:

              Gerrit Reviews

                There are no open Gerrit changes