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. [SOLVED] reading data in QTCPsocket is incomplete
Forum Updated to NodeBB v4.3 + New Features

[SOLVED] reading data in QTCPsocket is incomplete

Scheduled Pinned Locked Moved General and Desktop
14 Posts 3 Posters 9.7k Views 1 Watching
  • 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.
  • M Offline
    M Offline
    Marty
    wrote on last edited by
    #4

    Hi and thank you for your suggestions !

    the thing is :

    • the server is a device and i don't have much information about the TCP message format for the answer. The only thing i know is the response message is composed of :

    • the command the device received + EOL (CR/LF)

    • the answer to the query, here this is the message stored in memory + EOL (CR/LF)

    • state of execution (valid or not) + EOL (CR/LF)

    it would be great if the device sends the message size in the TCP frame but i don't have this information.

    So i don't know how to be sure i read all data !

    I will try to get the number of bytes written to the device as suggested.

    Could the EOL (CR/LF) be a problem when reveiving TCP packets ?
    How can i handle this ?

    thanks a lot

    1 Reply Last reply
    0
    • Q Offline
      Q Offline
      qxoz
      wrote on last edited by
      #5

      [quote author="Marty" date="1392894981"]

      • the command the device received + EOL (CR/LF)
      • the answer to the query, here this is the message stored in memory + EOL (CR/LF)
      • state of execution (valid or not) + EOL (CR/LF)
        [/quote]
        You already have enough information. Just wait until you receive all three parts of message which are ends with EOL.
      1 Reply Last reply
      0
      • M Offline
        M Offline
        Marty
        wrote on last edited by
        #6

        how would you write this part ?

        because in the documentation it says the response always ends with "@ + first letter of the command sent + state (like V for valid or E for error) + EOL".
        I tried to detect the character "@" yesterday just for a test purpose but my app froze like in infinite loop while waiting for that character that never arrives.

        Also, why when i send the command with telnet in a terminal i get the entire answer. How does telnet know when it gets the entire response ?

        thanks again

        1 Reply Last reply
        0
        • IamSumitI Offline
          IamSumitI Offline
          IamSumit
          wrote on last edited by
          #7

          @OK your server is a device ,the information you only know the composition of message as response from the server .
          Your problem is you are not getting full data from the server(Which is unknown to you) .
          You can use QQueue data structure -

          QQueue <QByteArray>Queue; (in .h file)

          QBytearray data=pSocket->readAll();
          qDebug() << "Data From Client : " << "\n\n" <<data;
          Queue.enqueue(data);

          while(!Queue.isEmpty())
          {
          QString str=Queue.dequeue();
          QString str=data;

              qdebug() << str ;
                 str.clear();
          

          }
          try it

          Be Cute

          1 Reply Last reply
          0
          • Q Offline
            Q Offline
            qxoz
            wrote on last edited by
            #8

            Use Wireshark, so you can see what exactly happening(what data sends by device) in network.
            And as IamSumit wrote using QQueue is good solution.

            1 Reply Last reply
            0
            • Q Offline
              Q Offline
              qxoz
              wrote on last edited by
              #9

              By the way
              can you show code how do you doing it?

              1 Reply Last reply
              0
              • M Offline
                M Offline
                Marty
                wrote on last edited by
                #10

                yep. will have a look to QQueue.

                here is some code.

                When i clic a button :

                @void ledBar::getStoredMessage(int bank)
                {
                QString message;
                if (bank < 10)
                {
                message = sendQuery("COP0" + QString::number(bank) + "\r\n");
                }
                else
                {
                message = sendQuery("COP" + QString::number(bank) + "\r\n");
                }
                qDebug() << message;
                }@

                The sendQuery() Method :

                @void TCPClient::sendQuery(QByteArray query)
                {
                if (socket->state() != QAbstractSocket::ConnectedState)
                {
                qWarning() << "Can't send command : not connected !";
                }
                else
                {
                socket->write(query)
                }
                }
                @

                then my readYread() slot :

                @void TCPClient::readyRead()
                {
                if(socket->waitForBytesWritten(2000) && socket->waitForReadyRead((2000)))
                {
                timer->start(timeout);
                return socket->readAll();
                }
                }@

                1 Reply Last reply
                0
                • Q Offline
                  Q Offline
                  qxoz
                  wrote on last edited by
                  #11

                  Is your code compiled ok?
                  Anyway, let's change your code in following way:
                  Add some buffer variables in your class
                  @private:
                  //....
                  QString responseTempalte;
                  QByteArray incommingData;
                  bool isDataComplete;
                  //....@
                  change getStoredMessage(int bank)
                  @void ledBar::getStoredMessage(int bank)
                  {
                  QString message = QStringLiteral("COP%1\r\n").arg(bank, 2, 10, QChar('0'));
                  responseTempalte = QStringLiteral("@%1%2\r\n").arg(message.at(0));
                  incommingData.clear();
                  isDataComplete = false;
                  sendQuery(message.toLatin1());
                  qDebug() << message;
                  }@
                  and most important part, readyRead slot
                  @void TCPClient::readyRead()
                  {
                  incommingData.append(socket->readAll());
                  if(incommingData.contains(responseTempalte.arg("V")) ||
                  incommingData.contains(responseTempalte.arg("E")) )
                  {
                  isDataComplete = true;//or emit some signal
                  }
                  }@
                  something like that, i hope didn't forget something important.

                  1 Reply Last reply
                  0
                  • M Offline
                    M Offline
                    Marty
                    wrote on last edited by
                    #12

                    Great i will give it a try !

                    maybe the best is, if you have time, to have a look at the whole project :

                    https://github.com/martialgallorini/ledManager

                    thanks a lot

                    1 Reply Last reply
                    0
                    • M Offline
                      M Offline
                      Marty
                      wrote on last edited by
                      #13

                      humm... can't make it to work

                      program without change compile and run well (except truncated TCP response)

                      i have applied the changes you suggested. It compiles ok, but when clic on send command button it freezes then close then crashes the app

                      1 Reply Last reply
                      0
                      • M Offline
                        M Offline
                        Marty
                        wrote on last edited by
                        #14

                        Well i figured it out but i don't understand why !

                        With

                        [CODE]socket->readLine();[/CODE]

                        it reads each complete line.

                        I tried everything (read(), readAll()...) and NOTHING but readLine() works !
                        If anybody has a clue why readAll() does'nt make it here...

                        [CODE]
                        void TCPClient::readyRead()
                        {
                        if(socket->waitForReadyRead(2000))
                        {
                        QString resp;
                        while(socket->bytesAvailable() > 0)
                        {
                        resp.append(socket->readLine());
                        }
                        emit sigTcpDataReceived(resp.toUtf8());
                        }
                        else
                        {
                        qWarning() << "Waiting for data to read timed out. No data received !";
                        }
                        }
                        [/CODE]

                        Thank you very much to everybody and for your help !

                        1 Reply Last reply
                        0

                        • Login

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