Reputation: 1737
I am attempting to read from/write to an RS-232 capable device. This works without issue on Linux. The device is connected via a Digitus USB/Serial Adapter.
The device shows up in Device Manager as COM4.
void PayLife::run() {
this->sendingData = 0;
this->running = true;
qDebug() << "Starting PayLife Thread";
this->port = new AbstractSerial();
this->port->setDeviceName(this->addy);
QByteArray ba;
if (port->open(AbstractSerial::ReadWrite| AbstractSerial::Unbuffered)) {
if (!port->setBaudRate(AbstractSerial::BaudRate19200)) {
qDebug() << "Set baud rate " << AbstractSerial::BaudRate19200 << " error.";
goto end_thread;
};
if (!port->setDataBits(AbstractSerial::DataBits7)) {
qDebug() << "Set data bits " << AbstractSerial::DataBits7 << " error.";
goto end_thread;
}
if (!port->setParity(AbstractSerial::ParityEven)) {
qDebug() << "Set parity " << AbstractSerial::ParityEven << " error.";
goto end_thread;
}
if (!port->setStopBits(AbstractSerial::StopBits1)) {
qDebug() << "Set stop bits " << AbstractSerial::StopBits1 << " error.";
goto end_thread;
}
if (!port->setFlowControl(AbstractSerial::FlowControlOff)) {
qDebug() << "Set flow " << AbstractSerial::FlowControlOff << " error.";
goto end_thread;
}
while(this->running) {
if ((port->bytesAvailable() > 0) || port->waitForReadyRead(900)) {
ba.clear();
ba = port->read(1024);
qDebug() << "Readed is : " << ba.size() << " bytes";
}
else {
qDebug() << "Timeout read data in time : " << QTime::currentTime();
}
}
}
end_thread:
this->running = false;
}
On Linux, I don't use QSerialDevice, just regular serial reading/writing.
No matter what, I always get:
Starting PayLife Thread
Readed is : 0 bytes
Timeout read data in time : QTime("16:27:43")
Timeout read data in time : QTime("16:27:44")
Timeout read data in time : QTime("16:27:45")
Timeout read data in time : QTime("16:27:46")
I am not exactly sure why.
Note, I tried first to use regular Windows API reading and writing with the same results, i.e. it just doesn't ready any data from the device.
I am 100% sure that there is always something to read from the device, as it spams ENQ across the connection.
Upvotes: 1
Views: 2904
Reputation: 29886
You should generate the doxygen documentation of QSerialDevice
if you haven't already done so. The problem seems to be explained there.
On Windows in unbuffered mode:
Necessary to avoid the values of
CharIntervalTimeout
andTotalReadConstantTimeout
equal to 0. In theory, it was planned that at zero values of timeouts methodAbstractSerial::read()
will read the data which are in the buffer device driver (not to be confused with the bufferAbstractSerial
!) and return them immediately. But for unknown reasons, this reading always returns 0, not depending on whether or not a ready-made data in the buffer.
Because read
waits for the data in unbuffered mode, I guess waitForReadyReady
doesn't do anything useful in that mode.
Upvotes: 1