Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Connection timed out when using QTcpSocket

Connection timed out when using QTcpSocket

Scheduled Pinned Locked Moved Unsolved General and Desktop
7 Posts 2 Posters 456 Views
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • N Offline
    N Offline
    n34rt
    wrote on 1 May 2023, 21:43 last edited by
    #1

    I'm trying to create a TCP socket connection using QTcpSocket, it's working correctly when I use a local ip, but when I try with my public ip it doesn't.

    After some time it throws an error: "Connection timed out".

    I'm not sure if this has something with the Windows Firewall, I have added both server and client to the "Allowed apps" of the firewall and also tried temporarily turning the firewall off, but the error persists.

    I'm able to ping my public IP from different networks.
    I also tested the sample below on a different machine/network and got the same error.

    How could i troubleshoot this?

    server

    #include <QNetworkInterface>
    #include <QTcpSocket>
    #include <QTcpServer>
    
    class Server : public QDialog
    {
        Q_OBJECT
    public:
        explicit Server(QWidget* parent = nullptr) : QDialog(parent), statusLabel(new QLabel)
        {
            statusLabel->setTextInteractionFlags(Qt::TextBrowserInteraction);
            initServer();
    
            fortunes << tr("You've been leading a dog's life. Stay off the furniture.")
                << tr("You've got to think about tomorrow.")
                << tr("You will be surprised by a loud noise.");
    
            auto quitButton = new QPushButton(tr("Quit"));
            quitButton->setAutoDefault(false);
            connect(quitButton, &QAbstractButton::clicked, this, &QWidget::close);
            connect(tcpServer, &QTcpServer::newConnection, this, &Server::sendFortune);
    
            auto buttonLayout = new QHBoxLayout;
            buttonLayout->addStretch(1);
            buttonLayout->addWidget(quitButton);
            buttonLayout->addStretch(1);
    
            QVBoxLayout* mainLayout = new QVBoxLayout(this);
            mainLayout->addWidget(statusLabel);
            mainLayout->addLayout(buttonLayout);
    
            setWindowTitle(QGuiApplication::applicationDisplayName());
        }
    
    private slots:
        void sendFortune()
        {
            QByteArray block;
            QDataStream out(&block, QIODevice::WriteOnly);
            out.setVersion(QDataStream::Qt_6_5);
    
            out << fortunes[QRandomGenerator::global()->bounded(fortunes.size())];
    
            QTcpSocket* clientConnection = tcpServer->nextPendingConnection();
            connect(clientConnection, &QAbstractSocket::disconnected,
                clientConnection, &QObject::deleteLater);
    
            clientConnection->write(block);
            clientConnection->disconnectFromHost();
        }
    
    private:
        void initServer()
        {
            tcpServer = new QTcpServer(this);
            if (!tcpServer->listen(QHostAddress("tcp://000.000.000.000"))) {
                QMessageBox::critical(this, tr("Fortune Server"), tr("Unable to start the server: %1.").arg(tcpServer->errorString()));
                close();
                return;
            }
            QString ipAddress = "000.000.000.000";
            statusLabel->setText(tr("The server is running on\n\nIP: %1\nport: %2\n\n"
                "Run the Fortune Client example now.").arg(ipAddress).arg(tcpServer->serverPort()));
        }
    
        QLabel *statusLabel = nullptr;
        QTcpServer *tcpServer = nullptr;
        QList<QString> fortunes;
    };
    
    
    
    int main(int argc, char *argv[])
    {
        QApplication::setApplicationDisplayName(Server::tr("Fortune Server"));
        Server server;
        server.show();
        return a.exec();
    }
    

    client

    #pragma once
    #include <QtNetwork>
    #include <QNetworkInterface>
    #include <QTcpSocket>
    #include <QTcpServer>
    
    class Client : public QDialog
    {
        Q_OBJECT
    public:
        explicit Client(QWidget* parent = nullptr) : QDialog(parent), hostCombo(new QComboBox), portLineEdit(new QLineEdit), getFortuneButton(new QPushButton(tr("Get Fortune"))), tcpSocket(new QTcpSocket(this))
        {
            hostCombo->setEditable(true);
            hostCombo->addItem(QString("000.000.000.000"));
    
            portLineEdit->setValidator(new QIntValidator(1, 65535, this));
    
            auto hostLabel = new QLabel(tr("&Server name:"));
            hostLabel->setBuddy(hostCombo);
            auto portLabel = new QLabel(tr("S&erver port:"));
            portLabel->setBuddy(portLineEdit);
    
            statusLabel = new QLabel(tr("This examples requires that you run the "
                "Fortune Server example as well."));
    
            getFortuneButton->setDefault(true);
            getFortuneButton->setEnabled(false);
    
            auto quitButton = new QPushButton(tr("Quit"));
    
            auto buttonBox = new QDialogButtonBox;
            buttonBox->addButton(getFortuneButton, QDialogButtonBox::ActionRole);
            buttonBox->addButton(quitButton, QDialogButtonBox::RejectRole);
            in.setDevice(tcpSocket);
            in.setVersion(QDataStream::Qt_6_5);
    
            connect(hostCombo, &QComboBox::editTextChanged, this, &Client::enableGetFortuneButton);
            connect(portLineEdit, &QLineEdit::textChanged, this, &Client::enableGetFortuneButton);
            connect(getFortuneButton, &QAbstractButton::clicked, this, &Client::requestNewFortune);
            connect(quitButton, &QAbstractButton::clicked, this, &QWidget::close);
            connect(tcpSocket, &QIODevice::readyRead, this, &Client::readFortune);
            connect(tcpSocket, &QAbstractSocket::errorOccurred, this, &Client::displayError);
    
            QGridLayout* mainLayout = mainLayout = new QGridLayout(this);
            mainLayout->addWidget(hostLabel, 0, 0);
            mainLayout->addWidget(hostCombo, 0, 1);
            mainLayout->addWidget(portLabel, 1, 0);
            mainLayout->addWidget(portLineEdit, 1, 1);
            mainLayout->addWidget(statusLabel, 2, 0, 1, 2);
            mainLayout->addWidget(buttonBox, 3, 0, 1, 2);
    
            setWindowTitle(QGuiApplication::applicationDisplayName());
            portLineEdit->setFocus();
        }
    
    private slots:
        void requestNewFortune()
        {
            getFortuneButton->setEnabled(false);
            tcpSocket->abort();
            tcpSocket->connectToHost(hostCombo->currentText(), portLineEdit->text().toInt());
        }
    
        void readFortune()
        {
            in.startTransaction();
            QString nextFortune;
            in >> nextFortune;
    
            if (!in.commitTransaction())
                return;
    
            if (nextFortune == currentFortune) {
                QTimer::singleShot(0, this, &Client::requestNewFortune);
                return;
            }
    
            currentFortune = nextFortune;
            statusLabel->setText(currentFortune);
            getFortuneButton->setEnabled(true);
        }
    
        void displayError(QAbstractSocket::SocketError socketError)
        {
            switch (socketError) {
            case QAbstractSocket::RemoteHostClosedError:
            break;
            case QAbstractSocket::HostNotFoundError:
            QMessageBox::information(this, tr("Fortune Client"),
                tr("The host was not found. Please check the "
                    "host name and port settings."));
            break;
            case QAbstractSocket::ConnectionRefusedError:
            QMessageBox::information(this, tr("Fortune Client"),
                tr("The connection was refused by the peer. "
                    "Make sure the fortune server is running, "
                    "and check that the host name and port "
                    "settings are correct."));
            break;
            default:
            QMessageBox::information(this, tr("Fortune Client"),
                tr("The following error occurred: %1.")
                .arg(tcpSocket->errorString()));
            }
    
            getFortuneButton->setEnabled(true);
        }
    
        void enableGetFortuneButton() 
        {
            getFortuneButton->setEnabled(!hostCombo->currentText().isEmpty() && !portLineEdit->text().isEmpty());
        }
    
    private:
        QComboBox *hostCombo = nullptr;
        QLineEdit *portLineEdit = nullptr;
        QLabel *statusLabel = nullptr;
        QPushButton *getFortuneButton = nullptr;
    
        QTcpSocket *tcpSocket = nullptr;
        QDataStream in;
        QString currentFortune;
    };
    
    
    int main(int argc, char *argv[])
    {
        QApplication::setApplicationDisplayName(Client::tr("Fortune Client"));
        Client client;
        client.show();
        return a.exec();
    }
    

    Qt 6.5, Windows 10.

    K 1 Reply Last reply 1 May 2023, 21:52
    0
    • N n34rt
      1 May 2023, 21:43

      I'm trying to create a TCP socket connection using QTcpSocket, it's working correctly when I use a local ip, but when I try with my public ip it doesn't.

      After some time it throws an error: "Connection timed out".

      I'm not sure if this has something with the Windows Firewall, I have added both server and client to the "Allowed apps" of the firewall and also tried temporarily turning the firewall off, but the error persists.

      I'm able to ping my public IP from different networks.
      I also tested the sample below on a different machine/network and got the same error.

      How could i troubleshoot this?

      server

      #include <QNetworkInterface>
      #include <QTcpSocket>
      #include <QTcpServer>
      
      class Server : public QDialog
      {
          Q_OBJECT
      public:
          explicit Server(QWidget* parent = nullptr) : QDialog(parent), statusLabel(new QLabel)
          {
              statusLabel->setTextInteractionFlags(Qt::TextBrowserInteraction);
              initServer();
      
              fortunes << tr("You've been leading a dog's life. Stay off the furniture.")
                  << tr("You've got to think about tomorrow.")
                  << tr("You will be surprised by a loud noise.");
      
              auto quitButton = new QPushButton(tr("Quit"));
              quitButton->setAutoDefault(false);
              connect(quitButton, &QAbstractButton::clicked, this, &QWidget::close);
              connect(tcpServer, &QTcpServer::newConnection, this, &Server::sendFortune);
      
              auto buttonLayout = new QHBoxLayout;
              buttonLayout->addStretch(1);
              buttonLayout->addWidget(quitButton);
              buttonLayout->addStretch(1);
      
              QVBoxLayout* mainLayout = new QVBoxLayout(this);
              mainLayout->addWidget(statusLabel);
              mainLayout->addLayout(buttonLayout);
      
              setWindowTitle(QGuiApplication::applicationDisplayName());
          }
      
      private slots:
          void sendFortune()
          {
              QByteArray block;
              QDataStream out(&block, QIODevice::WriteOnly);
              out.setVersion(QDataStream::Qt_6_5);
      
              out << fortunes[QRandomGenerator::global()->bounded(fortunes.size())];
      
              QTcpSocket* clientConnection = tcpServer->nextPendingConnection();
              connect(clientConnection, &QAbstractSocket::disconnected,
                  clientConnection, &QObject::deleteLater);
      
              clientConnection->write(block);
              clientConnection->disconnectFromHost();
          }
      
      private:
          void initServer()
          {
              tcpServer = new QTcpServer(this);
              if (!tcpServer->listen(QHostAddress("tcp://000.000.000.000"))) {
                  QMessageBox::critical(this, tr("Fortune Server"), tr("Unable to start the server: %1.").arg(tcpServer->errorString()));
                  close();
                  return;
              }
              QString ipAddress = "000.000.000.000";
              statusLabel->setText(tr("The server is running on\n\nIP: %1\nport: %2\n\n"
                  "Run the Fortune Client example now.").arg(ipAddress).arg(tcpServer->serverPort()));
          }
      
          QLabel *statusLabel = nullptr;
          QTcpServer *tcpServer = nullptr;
          QList<QString> fortunes;
      };
      
      
      
      int main(int argc, char *argv[])
      {
          QApplication::setApplicationDisplayName(Server::tr("Fortune Server"));
          Server server;
          server.show();
          return a.exec();
      }
      

      client

      #pragma once
      #include <QtNetwork>
      #include <QNetworkInterface>
      #include <QTcpSocket>
      #include <QTcpServer>
      
      class Client : public QDialog
      {
          Q_OBJECT
      public:
          explicit Client(QWidget* parent = nullptr) : QDialog(parent), hostCombo(new QComboBox), portLineEdit(new QLineEdit), getFortuneButton(new QPushButton(tr("Get Fortune"))), tcpSocket(new QTcpSocket(this))
          {
              hostCombo->setEditable(true);
              hostCombo->addItem(QString("000.000.000.000"));
      
              portLineEdit->setValidator(new QIntValidator(1, 65535, this));
      
              auto hostLabel = new QLabel(tr("&Server name:"));
              hostLabel->setBuddy(hostCombo);
              auto portLabel = new QLabel(tr("S&erver port:"));
              portLabel->setBuddy(portLineEdit);
      
              statusLabel = new QLabel(tr("This examples requires that you run the "
                  "Fortune Server example as well."));
      
              getFortuneButton->setDefault(true);
              getFortuneButton->setEnabled(false);
      
              auto quitButton = new QPushButton(tr("Quit"));
      
              auto buttonBox = new QDialogButtonBox;
              buttonBox->addButton(getFortuneButton, QDialogButtonBox::ActionRole);
              buttonBox->addButton(quitButton, QDialogButtonBox::RejectRole);
              in.setDevice(tcpSocket);
              in.setVersion(QDataStream::Qt_6_5);
      
              connect(hostCombo, &QComboBox::editTextChanged, this, &Client::enableGetFortuneButton);
              connect(portLineEdit, &QLineEdit::textChanged, this, &Client::enableGetFortuneButton);
              connect(getFortuneButton, &QAbstractButton::clicked, this, &Client::requestNewFortune);
              connect(quitButton, &QAbstractButton::clicked, this, &QWidget::close);
              connect(tcpSocket, &QIODevice::readyRead, this, &Client::readFortune);
              connect(tcpSocket, &QAbstractSocket::errorOccurred, this, &Client::displayError);
      
              QGridLayout* mainLayout = mainLayout = new QGridLayout(this);
              mainLayout->addWidget(hostLabel, 0, 0);
              mainLayout->addWidget(hostCombo, 0, 1);
              mainLayout->addWidget(portLabel, 1, 0);
              mainLayout->addWidget(portLineEdit, 1, 1);
              mainLayout->addWidget(statusLabel, 2, 0, 1, 2);
              mainLayout->addWidget(buttonBox, 3, 0, 1, 2);
      
              setWindowTitle(QGuiApplication::applicationDisplayName());
              portLineEdit->setFocus();
          }
      
      private slots:
          void requestNewFortune()
          {
              getFortuneButton->setEnabled(false);
              tcpSocket->abort();
              tcpSocket->connectToHost(hostCombo->currentText(), portLineEdit->text().toInt());
          }
      
          void readFortune()
          {
              in.startTransaction();
              QString nextFortune;
              in >> nextFortune;
      
              if (!in.commitTransaction())
                  return;
      
              if (nextFortune == currentFortune) {
                  QTimer::singleShot(0, this, &Client::requestNewFortune);
                  return;
              }
      
              currentFortune = nextFortune;
              statusLabel->setText(currentFortune);
              getFortuneButton->setEnabled(true);
          }
      
          void displayError(QAbstractSocket::SocketError socketError)
          {
              switch (socketError) {
              case QAbstractSocket::RemoteHostClosedError:
              break;
              case QAbstractSocket::HostNotFoundError:
              QMessageBox::information(this, tr("Fortune Client"),
                  tr("The host was not found. Please check the "
                      "host name and port settings."));
              break;
              case QAbstractSocket::ConnectionRefusedError:
              QMessageBox::information(this, tr("Fortune Client"),
                  tr("The connection was refused by the peer. "
                      "Make sure the fortune server is running, "
                      "and check that the host name and port "
                      "settings are correct."));
              break;
              default:
              QMessageBox::information(this, tr("Fortune Client"),
                  tr("The following error occurred: %1.")
                  .arg(tcpSocket->errorString()));
              }
      
              getFortuneButton->setEnabled(true);
          }
      
          void enableGetFortuneButton() 
          {
              getFortuneButton->setEnabled(!hostCombo->currentText().isEmpty() && !portLineEdit->text().isEmpty());
          }
      
      private:
          QComboBox *hostCombo = nullptr;
          QLineEdit *portLineEdit = nullptr;
          QLabel *statusLabel = nullptr;
          QPushButton *getFortuneButton = nullptr;
      
          QTcpSocket *tcpSocket = nullptr;
          QDataStream in;
          QString currentFortune;
      };
      
      
      int main(int argc, char *argv[])
      {
          QApplication::setApplicationDisplayName(Client::tr("Fortune Client"));
          Client client;
          client.show();
          return a.exec();
      }
      

      Qt 6.5, Windows 10.

      K Offline
      K Offline
      Kent-Dorfman
      wrote on 1 May 2023, 21:52 last edited by
      #2

      @n34rt

      "how can I troubleshoot this?" is an extremely broad question. There is no such thing as a "local IP". There are public and private IPs. Private IPs are behind a NAT firewall, usually.

      You don't give enough information about your network environment to say for sure, but I'll wager your problems have nothing to do with Qt, but are due to a lack of understanding of the network config side of things.

      N 1 Reply Last reply 1 May 2023, 23:03
      0
      • K Kent-Dorfman
        1 May 2023, 21:52

        @n34rt

        "how can I troubleshoot this?" is an extremely broad question. There is no such thing as a "local IP". There are public and private IPs. Private IPs are behind a NAT firewall, usually.

        You don't give enough information about your network environment to say for sure, but I'll wager your problems have nothing to do with Qt, but are due to a lack of understanding of the network config side of things.

        N Offline
        N Offline
        n34rt
        wrote on 1 May 2023, 23:03 last edited by
        #3

        @Kent-Dorfman said in Connection timed out when using QTcpSocket:

        You don't give enough information about your network environment

        Sure, what information about my network environment could help troubleshoot this issue?
        Im testing the code into two completely different machines/network, and getting the same error.

        K 1 Reply Last reply 2 May 2023, 00:16
        0
        • N n34rt
          1 May 2023, 23:03

          @Kent-Dorfman said in Connection timed out when using QTcpSocket:

          You don't give enough information about your network environment

          Sure, what information about my network environment could help troubleshoot this issue?
          Im testing the code into two completely different machines/network, and getting the same error.

          K Offline
          K Offline
          Kent-Dorfman
          wrote on 2 May 2023, 00:16 last edited by
          #4

          @n34rt
          what host/ip is the server running on?
          what host/ip is the client running on?
          what network exists between them? same network subnet? NAT translation?

          You do understand that you cannot talk to a NAT machine behind a firewall using the public IP address without doing something called port forwarding in the router?

          N 1 Reply Last reply 2 May 2023, 01:07
          0
          • K Kent-Dorfman
            2 May 2023, 00:16

            @n34rt
            what host/ip is the server running on?
            what host/ip is the client running on?
            what network exists between them? same network subnet? NAT translation?

            You do understand that you cannot talk to a NAT machine behind a firewall using the public IP address without doing something called port forwarding in the router?

            N Offline
            N Offline
            n34rt
            wrote on 2 May 2023, 01:07 last edited by n34rt 5 Feb 2023, 01:07
            #5

            @Kent-Dorfman said in Connection timed out when using QTcpSocket:

            You do understand that you cannot talk to a NAT machine behind a firewall using the public IP address without doing something called port forwarding in the router?

            I didn't, thank you for pointing this, I'm completely new in networking, sockets, etc.

            I was searching more about, would it work if I host a local server with something like apache?

            K 1 Reply Last reply 2 May 2023, 01:47
            0
            • N n34rt
              2 May 2023, 01:07

              @Kent-Dorfman said in Connection timed out when using QTcpSocket:

              You do understand that you cannot talk to a NAT machine behind a firewall using the public IP address without doing something called port forwarding in the router?

              I didn't, thank you for pointing this, I'm completely new in networking, sockets, etc.

              I was searching more about, would it work if I host a local server with something like apache?

              K Offline
              K Offline
              Kent-Dorfman
              wrote on 2 May 2023, 01:47 last edited by
              #6

              @n34rt said in Connection timed out when using QTcpSocket:

              I was searching more about, would it work if I host a local server with something like apache?

              no. that's the whole purpose of consumer grade internet connectivity via NAT routers: to keep customers from running services without paying for commercial grade service.

              N 1 Reply Last reply 2 May 2023, 01:55
              0
              • K Kent-Dorfman
                2 May 2023, 01:47

                @n34rt said in Connection timed out when using QTcpSocket:

                I was searching more about, would it work if I host a local server with something like apache?

                no. that's the whole purpose of consumer grade internet connectivity via NAT routers: to keep customers from running services without paying for commercial grade service.

                N Offline
                N Offline
                n34rt
                wrote on 2 May 2023, 01:55 last edited by
                #7

                @Kent-Dorfman even if I open the required ports to the apache server in my router?

                1 Reply Last reply
                0

                3/7

                1 May 2023, 23:03

                • Login

                • Login or register to search.
                3 out of 7
                • First post
                  3/7
                  Last post
                0
                • Categories
                • Recent
                • Tags
                • Popular
                • Users
                • Groups
                • Search
                • Get Qt Extensions
                • Unsolved