While() infinite loop after migrating from Qt 4.8 to Qt 5.4
-
wrote on 11 Mar 2015, 11:43 last edited by
Hello,
I have with my app after porting it from Qt 4.8 to Qt 5.4
My app connects to a led journal over TCP and retrieves / modifies text contents in memory banks. i.e. i send a command like APL01 and the device returns content of memory 1 like so :
APL01 Memory 1 text content here... @CV
I am testing the @ character to find the end of response and parse it.
With my application compiled under Qt 4.8 everything is fine. With Qt 5.4 the app loops forever.
here is the github project page : https://github.com/martialgallorini/ledManager
the code that causes the app to loop is in tcpClient.cpp :
QString TCPClient::sendQuery(QString query) { if (socket->state() != QAbstractSocket::ConnectedState) { qWarning() << "Can't send command : not connected !"; } else { while (socket->bytesAvailable() > 0) // purge socket buffer { socket->readLine(); } socket->write(query.toLatin1()); QString resp; if(socket->waitForBytesWritten(2000) && socket->waitForReadyRead(2000)) // read response { // ISSUE HERE !!! INFINITE LOOP while(socket->bytesAvailable() > 0 || (!resp.contains("@"))) { resp.append(QString::fromLatin1(socket->readLine())); } return resp; } else { qWarning() << "Waiting for data to read timed out. Nothing to read !"; } } return QString(); }
Do you have any idea ?
Seems like the app never gets the @ character. Are you aware of any QString and/or QByteArray character encoding modifications in Qt 5.4 ?
thanks a lot
-
Hello,
I have with my app after porting it from Qt 4.8 to Qt 5.4
My app connects to a led journal over TCP and retrieves / modifies text contents in memory banks. i.e. i send a command like APL01 and the device returns content of memory 1 like so :
APL01 Memory 1 text content here... @CV
I am testing the @ character to find the end of response and parse it.
With my application compiled under Qt 4.8 everything is fine. With Qt 5.4 the app loops forever.
here is the github project page : https://github.com/martialgallorini/ledManager
the code that causes the app to loop is in tcpClient.cpp :
QString TCPClient::sendQuery(QString query) { if (socket->state() != QAbstractSocket::ConnectedState) { qWarning() << "Can't send command : not connected !"; } else { while (socket->bytesAvailable() > 0) // purge socket buffer { socket->readLine(); } socket->write(query.toLatin1()); QString resp; if(socket->waitForBytesWritten(2000) && socket->waitForReadyRead(2000)) // read response { // ISSUE HERE !!! INFINITE LOOP while(socket->bytesAvailable() > 0 || (!resp.contains("@"))) { resp.append(QString::fromLatin1(socket->readLine())); } return resp; } else { qWarning() << "Waiting for data to read timed out. Nothing to read !"; } } return QString(); }
Do you have any idea ?
Seems like the app never gets the @ character. Are you aware of any QString and/or QByteArray character encoding modifications in Qt 5.4 ?
thanks a lot
wrote on 11 Mar 2015, 12:18 last edited by@Marty said:
while(socket->bytesAvailable() > 0 || (!resp.contains("@")))
{
resp.append(QString::fromLatin1(socket->readLine()));
}The Issue is there.
if resp does not contain '@' and bytesAvailable returns <= 0 you never exit from the loop -
wrote on 11 Mar 2015, 13:20 last edited by Marty 3 Nov 2015, 13:22
Hi,
Yes i know.
Maybe i should add a condition to exit the loop if there is some bug or transmission errors.But the thing is : '@' is expected
I should read it in every response i get from the device. '@' marks the end of every device answer to any command. -
Hi,
Yes i know.
Maybe i should add a condition to exit the loop if there is some bug or transmission errors.But the thing is : '@' is expected
I should read it in every response i get from the device. '@' marks the end of every device answer to any command. -
wrote on 11 Mar 2015, 14:23 last edited by
thanks for the advice.
I will try your suggestions.
Do you think it could be a character encoding issue ?
Like if i read the memory content with the '@' but the app doesn't recognize it as a '@' ? -
wrote on 11 Mar 2015, 14:35 last edited by
I don't think so
-
wrote on 11 Mar 2015, 14:44 last edited by
PS : the device uses CP 1252 character encoding.
How can i be sure to use the same encoding in Qt ? -
wrote on 11 Mar 2015, 15:15 last edited by
Qt internally uses Unicode for QString and QChar.
When you read a text you can useQTextCodec
to handle the right encoding -
wrote on 11 Mar 2015, 16:14 last edited by Marty 3 Nov 2015, 16:14
Seems to work now
While() loop exit condition doesn’t work because socket buffer doesn’t update automatically. It updates when next waitForReadyRead signal fires. So we need to keep checking if data is still available to read with calling waitForReadyRead.
Changing while() loop to :
QString resp; if(socket->waitForBytesWritten(2000)) { while(socket->bytesAvailable() > 0 || socket->waitForReadyRead(2000)) { resp.append(QString::fromLatin1(socket->readLine())); if (resp.contains("@")) return true; } } qWarning() << "Waiting for data to read timed out. Nothing to read !";
-
wrote on 11 Mar 2015, 16:42 last edited by
I think the key is the waitForReadyRead(). I have run into problems with using the function bytesAvailable() for various unknown reasons.
Maybe something like this might work as well (?):
while(socket->bytesAvailable() > 0 || (!resp.contains("@")))
{
resp.append(QString::fromLatin1(socket->readLine()));
socket->waitForReadyRead(1);
}
6/10