diff --git a/libnymea-modbus/tools/connectiontool/modbustcp.py b/libnymea-modbus/tools/connectiontool/modbustcp.py index 1245ec5..88c24f9 100644 --- a/libnymea-modbus/tools/connectiontool/modbustcp.py +++ b/libnymea-modbus/tools/connectiontool/modbustcp.py @@ -272,49 +272,51 @@ def writePropertyUpdateMethodImplementationsTcp(fileDescriptor, className, regis propertyName = registerDefinition['id'] writeLine(fileDescriptor, 'void %s::update%s()' % (className, propertyName[0].upper() + propertyName[1:])) writeLine(fileDescriptor, '{') - writeLine(fileDescriptor, ' // Update registers from %s' % registerDefinition['description']) - writeLine(fileDescriptor, ' qCDebug(dc%s()) << "--> Read \\"%s\\" register:" << %s << "size:" << %s;' % (className, registerDefinition['description'], registerDefinition['address'], registerDefinition['size'])) if queuedRequests: if 'readSchedule' in registerDefinition and registerDefinition['readSchedule'] == 'init': writeLine(fileDescriptor, ' if (m_currentInitReply)') writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' m_currentInitReply = read%s();' % (propertyName[0].upper() + propertyName[1:])) - writeLine(fileDescriptor, ' if (!m_currentInitReply) {') + writeLine(fileDescriptor, ' // Update registers from %s' % registerDefinition['description']) + writeLine(fileDescriptor, ' qCDebug(dc%s()) << "--> Read \\"%s\\" register:" << %s << "size:" << %s;' % (className, registerDefinition['description'], registerDefinition['address'], registerDefinition['size'])) + writeLine(fileDescriptor, ' QModbusReply *reply = read%s();' % (propertyName[0].upper() + propertyName[1:])) + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' if (!reply) {') writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Error occurred while reading \\"%s\\" init register from" << m_modbusTcpMaster->hostAddress().toString() << m_modbusTcpMaster->errorString();' % (className, registerDefinition['description'])) writeLine(fileDescriptor, ' finishInitialization(false);') writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' if (m_currentInitReply->isFinished()) {') - writeLine(fileDescriptor, ' m_currentInitReply->deleteLater(); // Broadcast reply returns immediatly') - writeLine(fileDescriptor, ' m_currentInitReply = nullptr;') + writeLine(fileDescriptor, ' if (reply->isFinished()) {') + writeLine(fileDescriptor, ' reply->deleteLater(); // Broadcast reply returns immediatly') writeLine(fileDescriptor, ' if (!verifyInitFinished())') writeLine(fileDescriptor, ' QTimer::singleShot(%s, this, &%s::sendNextQueuedInitRequest);' % (queuedRequestsDelay, className)) writeLine(fileDescriptor) writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' connect(m_currentInitReply, &QModbusReply::finished, m_currentInitReply, &QModbusReply::deleteLater);') - writeLine(fileDescriptor, ' connect(m_currentInitReply, &QModbusReply::finished, this, [this](){') - writeLine(fileDescriptor, ' handleModbusError(m_currentInitReply->error());') + writeLine(fileDescriptor, ' m_currentInitReply = reply;') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' if (m_currentInitReply->error() != QModbusDevice::NoError) {') - writeLine(fileDescriptor, ' QModbusResponse response = m_currentInitReply->rawResult();') - writeLine(fileDescriptor, ' if (m_currentInitReply->error() == QModbusDevice::ProtocolError && response.isException()) {') - writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating init \\"%s\\" registers" << m_currentInitReply->error() << m_currentInitReply->errorString() << ModbusDataUtils::exceptionCodeToString(response.exceptionCode());' % (className, blockName)) + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::finished, reply, &QModbusReply::deleteLater);') + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::finished, this, [this, reply](){') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' m_currentInitReply = nullptr;') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' handleModbusError(reply->error());') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' if (reply->error() != QModbusDevice::NoError) {') + writeLine(fileDescriptor, ' QModbusResponse response = reply->rawResult();') + writeLine(fileDescriptor, ' if (reply->error() == QModbusDevice::ProtocolError && response.isException()) {') + writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating init \\"%s\\" registers" << reply->error() << reply->errorString() << ModbusDataUtils::exceptionCodeToString(response.exceptionCode());' % (className, registerDefinition['description'])) writeLine(fileDescriptor, ' } else {') - writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating init \\"%s\\" registers" << m_currentInitReply->error() << m_currentInitReply->errorString();' % (className, blockName)) + writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating init \\"%s\\" registers" << reply->error() << reply->errorString();' % (className, registerDefinition['description'])) writeLine(fileDescriptor, ' }') writeLine(fileDescriptor, ' finishInitialization(false);') - writeLine(fileDescriptor, ' m_currentInitReply = nullptr;') writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' const QModbusDataUnit unit = m_currentInitReply->result();') - writeLine(fileDescriptor, ' m_currentInitReply = nullptr;') - writeLine(fileDescriptor) + writeLine(fileDescriptor, ' const QModbusDataUnit unit = reply->result();') writeLine(fileDescriptor, ' process%sRegisterValues(unit.values());' % (propertyName[0].upper() + propertyName[1:])) writeLine(fileDescriptor) writeLine(fileDescriptor, ' if (!verifyInitFinished())') @@ -326,8 +328,11 @@ def writePropertyUpdateMethodImplementationsTcp(fileDescriptor, className, regis writeLine(fileDescriptor, ' if (m_currentUpdateReply)') writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' m_currentUpdateReply = read%s();' % (propertyName[0].upper() + propertyName[1:])) - writeLine(fileDescriptor, ' if (!m_currentUpdateReply) {') + writeLine(fileDescriptor, ' // Update registers from %s' % registerDefinition['description']) + writeLine(fileDescriptor, ' qCDebug(dc%s()) << "--> Read \\"%s\\" register:" << %s << "size:" << %s;' % (className, registerDefinition['description'], registerDefinition['address'], registerDefinition['size'])) + writeLine(fileDescriptor, ' QModbusReply *reply = read%s();' % (propertyName[0].upper() + propertyName[1:])) + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' if (!reply) {') writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Error occurred while reading \\"%s\\" registers from" << m_modbusTcpMaster->hostAddress().toString() << m_modbusTcpMaster->errorString();' % (className, registerDefinition['description'])) writeLine(fileDescriptor, ' if (!verifyUpdateFinished())') writeLine(fileDescriptor, ' QTimer::singleShot(%s, this, &%s::sendNextQueuedRequest);' % (queuedRequestsDelay, className)) @@ -335,39 +340,44 @@ def writePropertyUpdateMethodImplementationsTcp(fileDescriptor, className, regis writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' if (m_currentUpdateReply->isFinished()) {') - writeLine(fileDescriptor, ' m_currentUpdateReply->deleteLater(); // Broadcast reply returns immediatly') - writeLine(fileDescriptor, ' m_currentUpdateReply = nullptr;') + writeLine(fileDescriptor, ' if (reply->isFinished()) {') + writeLine(fileDescriptor, ' reply->deleteLater(); // Broadcast reply returns immediatly') writeLine(fileDescriptor, ' if (!verifyUpdateFinished())') writeLine(fileDescriptor, ' QTimer::singleShot(%s, this, &%s::sendNextQueuedRequest);' % (queuedRequestsDelay, className)) writeLine(fileDescriptor) writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' connect(m_currentUpdateReply, &QModbusReply::finished, this, [this](){') - writeLine(fileDescriptor, ' handleModbusError(m_currentUpdateReply->error());') - writeLine(fileDescriptor, ' if (m_currentUpdateReply->error() == QModbusDevice::NoError) {') - writeLine(fileDescriptor, ' const QModbusDataUnit unit = m_currentUpdateReply->result();') - writeLine(fileDescriptor, ' qCDebug(dc%s()) << "<-- Response from \\"%s\\" register" << %s << "size:" << %s << unit.values();' % (className, registerDefinition['description'], registerDefinition['address'], registerDefinition['size'])) + writeLine(fileDescriptor, ' m_currentUpdateReply = reply;') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::finished, reply, &QModbusReply::deleteLater);') + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::finished, this, [this, reply](){') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' m_currentUpdateReply = nullptr;') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' handleModbusError(reply->error());') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' if (reply->error() == QModbusDevice::NoError) {') + writeLine(fileDescriptor, ' const QModbusDataUnit unit = reply->result();') writeLine(fileDescriptor, ' process%sRegisterValues(unit.values());' % (propertyName[0].upper() + propertyName[1:])) writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' m_currentUpdateReply->deleteLater();') - writeLine(fileDescriptor, ' m_currentUpdateReply = nullptr;') writeLine(fileDescriptor, ' if (!verifyUpdateFinished())') writeLine(fileDescriptor, ' QTimer::singleShot(%s, this, &%s::sendNextQueuedRequest);' % (queuedRequestsDelay, className)) writeLine(fileDescriptor) writeLine(fileDescriptor, ' });') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' connect(m_currentUpdateReply, &QModbusReply::errorOccurred, this, [this] (QModbusDevice::Error error){') - writeLine(fileDescriptor, ' QModbusResponse response = m_currentUpdateReply->rawResult();') - writeLine(fileDescriptor, ' if (m_currentUpdateReply->error() == QModbusDevice::ProtocolError && response.isException()) {') + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::errorOccurred, this, [this, reply] (QModbusDevice::Error error){') + writeLine(fileDescriptor, ' QModbusResponse response = reply->rawResult();') + writeLine(fileDescriptor, ' if (reply->error() == QModbusDevice::ProtocolError && response.isException()) {') writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating \\"%s\\" registers from" << m_modbusTcpMaster->hostAddress().toString() << ModbusDataUtils::exceptionCodeToString(response.exceptionCode());' % (className, registerDefinition['description'])) writeLine(fileDescriptor, ' } else {') - writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating \\"%s\\" registers from" << m_modbusTcpMaster->hostAddress().toString() << error << m_currentUpdateReply->errorString();' % (className, registerDefinition['description'])) + writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating \\"%s\\" registers from" << m_modbusTcpMaster->hostAddress().toString() << error << reply->errorString();' % (className, registerDefinition['description'])) writeLine(fileDescriptor, ' }') writeLine(fileDescriptor, ' });') else: + writeLine(fileDescriptor, ' // Update registers from %s' % registerDefinition['description']) + writeLine(fileDescriptor, ' qCDebug(dc%s()) << "--> Read \\"%s\\" register:" << %s << "size:" << %s;' % (className, registerDefinition['description'], registerDefinition['address'], registerDefinition['size'])) writeLine(fileDescriptor, ' QModbusReply *reply = read%s();' % (propertyName[0].upper() + propertyName[1:])) writeLine(fileDescriptor, ' if (!reply) {') writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Error occurred while reading \\"%s\\" registers from" << m_modbusTcpMaster->hostAddress().toString() << m_modbusTcpMaster->errorString();' % (className, registerDefinition['description'])) @@ -419,47 +429,51 @@ def writeBlockUpdateMethodImplementationsTcp(fileDescriptor, className, blockDef writeLine(fileDescriptor, 'void %s::update%sBlock()' % (className, blockName[0].upper() + blockName[1:])) writeLine(fileDescriptor, '{') - writeLine(fileDescriptor, ' // Update register block \"%s\"' % blockName) - writeLine(fileDescriptor, ' qCDebug(dc%s()) << "--> Read block \\"%s\\" registers from:" << %s << "size:" << %s;' % (className, blockName, blockStartAddress, blockSize)) if queuedRequests: if 'readSchedule' in blockDefinition and blockDefinition['readSchedule'] == 'init': - - writeLine(fileDescriptor, ' m_currentInitReply = readBlock%s();' % (blockName[0].upper() + blockName[1:])) - writeLine(fileDescriptor, ' if (!m_currentInitReply) {') + writeLine(fileDescriptor, ' if (m_currentInitReply)') + writeLine(fileDescriptor, ' return;') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' // Update register block \"%s\"' % blockName) + writeLine(fileDescriptor, ' qCDebug(dc%s()) << "--> Read block \\"%s\\" registers from:" << %s << "size:" << %s;' % (className, blockName, blockStartAddress, blockSize)) + writeLine(fileDescriptor, ' QModbusReply *reply = readBlock%s();' % (blockName[0].upper() + blockName[1:])) + writeLine(fileDescriptor, ' if (!reply) {') writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Error occurred while reading init block \\"%s\\" registers";' % (className, blockName)) writeLine(fileDescriptor, ' finishInitialization(false);') writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' if (m_currentInitReply->isFinished()) {') - writeLine(fileDescriptor, ' m_currentInitReply->deleteLater(); // Broadcast reply returns immediatly') - writeLine(fileDescriptor, ' m_currentInitReply = nullptr;') + writeLine(fileDescriptor, ' if (reply->isFinished()) {') + writeLine(fileDescriptor, ' reply->deleteLater(); // Broadcast reply returns immediatly') writeLine(fileDescriptor, ' if (!verifyInitFinished())') writeLine(fileDescriptor, ' QTimer::singleShot(%s, this, &%s::sendNextQueuedInitRequest);' % (queuedRequestsDelay, className)) writeLine(fileDescriptor) writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' connect(m_currentInitReply, &QModbusReply::finished, m_currentInitReply, &QModbusReply::deleteLater);') - writeLine(fileDescriptor, ' connect(m_currentInitReply, &QModbusReply::finished, this, [this](){') - writeLine(fileDescriptor, ' handleModbusError(m_currentInitReply->error());') + writeLine(fileDescriptor, ' m_currentInitReply = reply;') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' if (m_currentInitReply->error() != QModbusDevice::NoError) {') - writeLine(fileDescriptor, ' QModbusResponse response = m_currentInitReply->rawResult();') - writeLine(fileDescriptor, ' if (m_currentInitReply->error() == QModbusDevice::ProtocolError && response.isException()) {') - writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating init block \\"%s\\" registers" << m_currentInitReply->error() << m_currentInitReply->errorString() << ModbusDataUtils::exceptionCodeToString(response.exceptionCode());' % (className, blockName)) + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::finished, reply, &QModbusReply::deleteLater);') + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::finished, this, [this, reply](){') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' m_currentInitReply = nullptr;') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' handleModbusError(reply->error());') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' if (reply->error() != QModbusDevice::NoError) {') + writeLine(fileDescriptor, ' QModbusResponse response = reply->rawResult();') + writeLine(fileDescriptor, ' if (reply->error() == QModbusDevice::ProtocolError && response.isException()) {') + writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating init block \\"%s\\" registers" << reply->error() << reply->errorString() << ModbusDataUtils::exceptionCodeToString(response.exceptionCode());' % (className, blockName)) writeLine(fileDescriptor, ' } else {') - writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating init block \\"%s\\" registers" << m_currentInitReply->error() << m_currentInitReply->errorString();' % (className, blockName)) + writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating init block \\"%s\\" registers" << reply->error() << reply->errorString();' % (className, blockName)) writeLine(fileDescriptor, ' }') - writeLine(fileDescriptor, ' m_currentInitReply = nullptr;') writeLine(fileDescriptor, ' finishInitialization(false);') writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' const QModbusDataUnit unit = m_currentInitReply->result();') - writeLine(fileDescriptor, ' m_currentInitReply = nullptr;') + writeLine(fileDescriptor, ' const QModbusDataUnit unit = reply->result();') writeLine(fileDescriptor) writeLine(fileDescriptor, ' const QVector blockValues = unit.values();') writeLine(fileDescriptor, ' processBlock%sRegisterValues(blockValues);' % (blockName[0].upper() + blockName[1:])) @@ -470,8 +484,11 @@ def writeBlockUpdateMethodImplementationsTcp(fileDescriptor, className, blockDef writeLine(fileDescriptor, ' });') writeLine(fileDescriptor) else: - writeLine(fileDescriptor, ' m_currentUpdateReply = readBlock%s();' % (blockName[0].upper() + blockName[1:])) - writeLine(fileDescriptor, ' if (!m_currentUpdateReply) {') + + writeLine(fileDescriptor, ' // Update register block \"%s\"' % blockName) + writeLine(fileDescriptor, ' qCDebug(dc%s()) << "--> Read block \\"%s\\" registers from:" << %s << "size:" << %s;' % (className, blockName, blockStartAddress, blockSize)) + writeLine(fileDescriptor, ' QModbusReply *reply = readBlock%s();' % (blockName[0].upper() + blockName[1:])) + writeLine(fileDescriptor, ' if (!reply) {') writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Error occurred while reading block \\"%s\\" registers";' % (className, blockName)) writeLine(fileDescriptor, ' if (!verifyUpdateFinished())') writeLine(fileDescriptor, ' QTimer::singleShot(%s, this, &%s::sendNextQueuedRequest);' % (queuedRequestsDelay, className)) @@ -479,38 +496,44 @@ def writeBlockUpdateMethodImplementationsTcp(fileDescriptor, className, blockDef writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' if (m_currentUpdateReply->isFinished()) {') - writeLine(fileDescriptor, ' m_currentUpdateReply->deleteLater(); // Broadcast reply returns immediatly') - writeLine(fileDescriptor, ' m_currentUpdateReply = nullptr;') + writeLine(fileDescriptor, ' if (reply->isFinished()) {') + writeLine(fileDescriptor, ' reply->deleteLater(); // Broadcast reply returns immediatly') writeLine(fileDescriptor, ' if (!verifyUpdateFinished())') writeLine(fileDescriptor, ' QTimer::singleShot(%s, this, &%s::sendNextQueuedRequest);' % (queuedRequestsDelay, className)) writeLine(fileDescriptor) writeLine(fileDescriptor, ' return;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' connect(m_currentUpdateReply, &QModbusReply::finished, this, [this](){') - writeLine(fileDescriptor, ' handleModbusError(m_currentUpdateReply->error());') - writeLine(fileDescriptor, ' if (m_currentUpdateReply->error() == QModbusDevice::NoError) {') - writeLine(fileDescriptor, ' const QModbusDataUnit unit = m_currentUpdateReply->result();') + writeLine(fileDescriptor, ' m_currentUpdateReply = reply;') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::finished, reply, &QModbusReply::deleteLater);') + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::finished, this, [this, reply](){') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' m_currentUpdateReply = nullptr;') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' handleModbusError(reply->error());') + writeLine(fileDescriptor) + writeLine(fileDescriptor, ' if (reply->error() == QModbusDevice::NoError) {') + writeLine(fileDescriptor, ' const QModbusDataUnit unit = reply->result();') writeLine(fileDescriptor, ' const QVector blockValues = unit.values();') writeLine(fileDescriptor, ' processBlock%sRegisterValues(blockValues);' % (blockName[0].upper() + blockName[1:])) - writeLine(fileDescriptor, ' m_currentUpdateReply->deleteLater(); // Broadcast reply returns immediatly') - writeLine(fileDescriptor, ' m_currentUpdateReply = nullptr;') writeLine(fileDescriptor, ' if (!verifyUpdateFinished())') writeLine(fileDescriptor, ' QTimer::singleShot(%s, this, &%s::sendNextQueuedRequest);' % (queuedRequestsDelay, className)) writeLine(fileDescriptor) writeLine(fileDescriptor, ' }') writeLine(fileDescriptor, ' });') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' connect(m_currentUpdateReply, &QModbusReply::errorOccurred, this, [this] (QModbusDevice::Error error){') - writeLine(fileDescriptor, ' QModbusResponse response = m_currentUpdateReply->rawResult();') - writeLine(fileDescriptor, ' if (m_currentUpdateReply->error() == QModbusDevice::ProtocolError && response.isException()) {') - writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating block \\"%s\\" registers" << error << m_currentUpdateReply->errorString() << ModbusDataUtils::exceptionCodeToString(response.exceptionCode());' % (className, blockName)) + writeLine(fileDescriptor, ' connect(reply, &QModbusReply::errorOccurred, this, [reply] (QModbusDevice::Error error){') + writeLine(fileDescriptor, ' QModbusResponse response = reply->rawResult();') + writeLine(fileDescriptor, ' if (reply->error() == QModbusDevice::ProtocolError && response.isException()) {') + writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating block \\"%s\\" registers" << error << reply->errorString() << ModbusDataUtils::exceptionCodeToString(response.exceptionCode());' % (className, blockName)) writeLine(fileDescriptor, ' } else {') - writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating block \\"%s\\" registers" << error << m_currentUpdateReply->errorString();' % (className, blockName)) + writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Modbus reply error occurred while updating block \\"%s\\" registers" << error << reply->errorString();' % (className, blockName)) writeLine(fileDescriptor, ' }') writeLine(fileDescriptor, ' });') else: + writeLine(fileDescriptor, ' // Update register block \"%s\"' % blockName) + writeLine(fileDescriptor, ' qCDebug(dc%s()) << "--> Read block \\"%s\\" registers from:" << %s << "size:" << %s;' % (className, blockName, blockStartAddress, blockSize)) writeLine(fileDescriptor, ' QModbusReply *reply = readBlock%s();' % (blockName[0].upper() + blockName[1:])) writeLine(fileDescriptor, ' if (!reply) {') writeLine(fileDescriptor, ' qCWarning(dc%s()) << "Error occurred while reading block \\"%s\\" registers";' % (className, blockName)) @@ -661,7 +684,6 @@ def writeInitMethodImplementationTcp(fileDescriptor, className, registerDefiniti # Read individual registers for registerDefinition in registerDefinitions: propertyName = registerDefinition['id'] - propertyTyp = getCppDataType(registerDefinition) if 'readSchedule' in registerDefinition and registerDefinition['readSchedule'] == 'init': writeLine(fileDescriptor) @@ -800,6 +822,7 @@ def writeUpdateMethodTcp(fileDescriptor, className, registerDefinitions, blockDe writeLine(fileDescriptor, ' if (!m_updateRequestQueue.isEmpty()) {') writeLine(fileDescriptor, ' qCDebug(dc%s()) << "Tried to update but there are still some update requests pending. Waiting for them to be finished..." << m_updateRequestQueue.count();' % className) + writeLine(fileDescriptor, ' sendNextQueuedRequest();') writeLine(fileDescriptor, ' return true;') writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) diff --git a/libnymea-modbus/tools/connectiontool/toolcommon.py b/libnymea-modbus/tools/connectiontool/toolcommon.py index e6c4f7a..8fb66dc 100644 --- a/libnymea-modbus/tools/connectiontool/toolcommon.py +++ b/libnymea-modbus/tools/connectiontool/toolcommon.py @@ -14,11 +14,8 @@ # along with this program; if not, write to the Free Software # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. -import os import re -import sys import json -import shutil import datetime import logging @@ -615,11 +612,15 @@ def writeEnqueueInitRequestMethodImplementation(fileDescriptor, className): def writeSendNextQueuedRequestMethodImplementation(fileDescriptor, className): writeLine(fileDescriptor, 'void %s::sendNextQueuedRequest()' % (className)) writeLine(fileDescriptor, '{') - writeLine(fileDescriptor, ' if (m_updateRequestQueue.isEmpty())') + writeLine(fileDescriptor, ' if (m_updateRequestQueue.isEmpty()) {') + writeLine(fileDescriptor, ' qCDebug(dc%s()) << "Do not send next request since there are no requests left...";' % className) writeLine(fileDescriptor, ' return;') + writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) - writeLine(fileDescriptor, ' if (m_currentUpdateReply)') + writeLine(fileDescriptor, ' if (m_currentUpdateReply) {') + writeLine(fileDescriptor, ' qCDebug(dc%s()) << "Do not send next request since there is already a request pending...";' % className) writeLine(fileDescriptor, ' return;') + writeLine(fileDescriptor, ' }') writeLine(fileDescriptor) writeLine(fileDescriptor, ' %s::Function function = m_updateRequestQueue.dequeue();' % (className)) writeLine(fileDescriptor, ' (this->*function)();') diff --git a/libnymea-modbus/tools/generate-connection.py b/libnymea-modbus/tools/generate-connection.py index af9604f..de96504 100644 --- a/libnymea-modbus/tools/generate-connection.py +++ b/libnymea-modbus/tools/generate-connection.py @@ -487,8 +487,11 @@ def writeTcpSourceFile(): writeLine(sourceFile, ' // Cleanup before starting to initialize') writeLine(sourceFile, ' m_pendingInitReplies.clear();') writeLine(sourceFile, ' m_pendingUpdateReplies.clear();') + if queuedRequests: + writeLine(sourceFile, ' m_currentUpdateReply = nullptr;') writeLine(sourceFile, ' m_updateRequestQueue.clear();') + writeLine(sourceFile, ' m_currentInitReply = nullptr;') writeLine(sourceFile, ' m_initRequestQueue.clear();') writeLine(sourceFile, ' m_communicationWorking = false;') @@ -503,7 +506,9 @@ def writeTcpSourceFile(): writeLine(sourceFile, ' m_initializing = false;') if queuedRequests: + writeLine(sourceFile, ' m_currentUpdateReply = nullptr;') writeLine(sourceFile, ' m_updateRequestQueue.clear();') + writeLine(sourceFile, ' m_currentInitReply = nullptr;') writeLine(sourceFile, ' m_initRequestQueue.clear();') writeLine(sourceFile, ' }') diff --git a/solax/integrationpluginsolax.cpp b/solax/integrationpluginsolax.cpp index 953db99..85c23b9 100644 --- a/solax/integrationpluginsolax.cpp +++ b/solax/integrationpluginsolax.cpp @@ -128,7 +128,10 @@ void IntegrationPluginSolax::setupThing(ThingSetupInfo *info) qCInfo(dcSolax()) << "Setting up solax on" << address.toString() << port << "unit ID:" << slaveId; SolaxModbusTcpConnection *solaxConnection = new SolaxModbusTcpConnection(address, port, slaveId, this); - connect(info, &ThingSetupInfo::aborted, solaxConnection, &SolaxModbusTcpConnection::deleteLater); + connect(info, &ThingSetupInfo::aborted, solaxConnection, [solaxConnection](){ + solaxConnection->disconnectDevice(); + solaxConnection->deleteLater(); + }); // Reconnect on monitor reachable changed connect(monitor, &NetworkDeviceMonitor::reachableChanged, thing, [=](bool reachable){ @@ -149,9 +152,10 @@ void IntegrationPluginSolax::setupThing(ThingSetupInfo *info) connect(solaxConnection, &SolaxModbusTcpConnection::reachableChanged, thing, [this, thing, solaxConnection](bool reachable){ qCDebug(dcSolax()) << "Reachable changed to" << reachable << "for" << thing; if (reachable) { - // Connected true will be set after successfull init + qCDebug(dcSolax()) << "The connection is now reachable for" << thing << "... start initializing."; solaxConnection->initialize(); } else { + qCDebug(dcSolax()) << "The connection is not reachable any more" << thing; thing->setStateValue("connected", false); foreach (Thing *childThing, myThings().filterByParentId(thing->id())) { childThing->setStateValue("connected", false); @@ -196,9 +200,12 @@ void IntegrationPluginSolax::setupThing(ThingSetupInfo *info) if (!success) { // Try once to reconnect the device solaxConnection->reconnectDevice(); + qCWarning(dcSolax()) << "Unable to initialize" << thing << "Trying to reconnect..."; } else { qCInfo(dcSolax()) << "Connection initialized successfully for" << thing; - solaxConnection->update(); + if (!solaxConnection->update()) { + qCWarning(dcSolax()) << "Unable to update the values from" << thing << "after initializiation."; + } } }); @@ -252,7 +259,7 @@ void IntegrationPluginSolax::setupThing(ThingSetupInfo *info) // Update inverter states - int inverterPower = solaxConnection->powerDc1() + solaxConnection->powerDc1(); + int inverterPower = solaxConnection->powerDc1() + solaxConnection->powerDc2(); int inverterVoltage = solaxConnection->pvVoltage1() + solaxConnection->pvVoltage2(); int inverterCurrent = solaxConnection->pvCurrent1() + solaxConnection->pvCurrent2(); thing->setStateValue(solaxInverterTcpCurrentPowerStateTypeId, -inverterPower); @@ -411,7 +418,6 @@ void IntegrationPluginSolax::setupThing(ThingSetupInfo *info) void IntegrationPluginSolax::postSetupThing(Thing *thing) { - if (thing->thingClassId() == solaxInverterTcpThingClassId) { // Create the update timer if not already set up @@ -420,10 +426,12 @@ void IntegrationPluginSolax::postSetupThing(Thing *thing) m_refreshTimer = hardwareManager()->pluginTimerManager()->registerTimer(2); connect(m_refreshTimer, &PluginTimer::timeout, this, [this] { foreach(SolaxModbusTcpConnection *connection, m_tcpConnections) { - if (connection->initializing()) + if (connection->initializing()) { + qCDebug(dcSolax()) << "Skip updating" << connection->modbusTcpMaster() << "since the connection is still initializing."; continue; + } - //qCDebug(dcSolax()) << "Update connection" << connection->modbusTcpMaster()->hostAddress().toString(); + qCDebug(dcSolax()) << "Updating connection" << connection->modbusTcpMaster()->hostAddress().toString(); connection->update(); } });