#include "ModbusRepository.h" #include #include #include //#include "EngLog.h" CModbusRepository::CModbusRepository() { } int CModbusRepository::AddHRDataMap(quint16 StartAddress, quint16 Length) { mMutex.lockForWrite(); for(int i= 0; i < mHoldingRegisters.size(); i++) { if((StartAddress >= mHoldingRegisters.at(i).mStartAddress && StartAddress <= mHoldingRegisters.at(i).mEndAddress) || (StartAddress + Length - 1 >= mHoldingRegisters.at(i).mStartAddress && StartAddress + Length - 1 <= mHoldingRegisters.at(i).mEndAddress)) { mMutex.unlock(); return RET_ERROR; //The data map overlaps an existing map. } } CHRDataMap NewHRMap(StartAddress,Length); mHoldingRegisters.append(NewHRMap); mMutex.unlock(); // CEngLog::instance()->AddLogString(QString("Création d'une zone registre modbus à l'adresse: %1 de taille %2").arg(StartAddress).arg(Length)); return RET_OK; } bool CModbusRepository::IsHRValid(quint16 StartAddress, quint16 Length, int *index) { mMutex.lockForRead(); for(int i= 0; i < mHoldingRegisters.size(); i++) { if((StartAddress >= mHoldingRegisters.at(i).mStartAddress && StartAddress + Length - 1 <= mHoldingRegisters.at(i).mEndAddress)) { if(index != 0) { *index = i; } mMutex.unlock(); return true; } } mMutex.unlock(); return false; } QByteArray CModbusRepository::GetHRData(quint16 StartAddress, quint16 Length, bool *OK) { QByteArray Data; int RegisterIndex = 0; if(IsHRValid(StartAddress,Length, &RegisterIndex) == false) { if(OK != 0) { *OK = false; } } else { mMutex.lockForRead(); int DataIndex = StartAddress - mHoldingRegisters.at(RegisterIndex).mStartAddress; for(int i = 0; i < Length; i++) { quint16 CurReg = mHoldingRegisters.at(RegisterIndex).mRegistersData.at(DataIndex++); quint8 HighByte, LowByte; LowByte = CurReg & 0x00FF; HighByte = (CurReg >> 8) & 0x00FF; Data.append(HighByte); Data.append(LowByte); } mMutex.unlock(); if(OK != 0) *OK = true; } return Data; } int CModbusRepository::WriteHRData(quint16 StartAddress, quint16 Length, QByteArray Data) { int RegisterIndex; if(IsHRValid(StartAddress,Length, &RegisterIndex) == false) { return RET_ERROR; } if(Length*2 != Data.size()) { return RET_ERROR; } mMutex.lockForWrite(); int DataIndex = StartAddress - mHoldingRegisters.at(RegisterIndex).mStartAddress; for(int i = 0; i < Length; i++) { quint8 HighByte = Data.at(i*2); quint8 LowByte = Data.at(i*2 + 1); qint16 Word = HighByte; Word <<= 8; Word += LowByte; Word = Word &0xFFFF; mHoldingRegisters[RegisterIndex].mRegistersData[DataIndex++] = Word; } mMutex.unlock(); emit RepoChanged(StartAddress,Length); return RET_OK; } int CModbusRepository::WriteSingleReg(quint16 Address, quint16 Value) { int RegisterIndex; if(IsHRValid(Address,1, &RegisterIndex) == false) { return RET_ERROR; } mMutex.lockForWrite(); int DataIndex = Address - mHoldingRegisters.at(RegisterIndex).mStartAddress; mHoldingRegisters[RegisterIndex].mRegistersData[DataIndex] = Value; mMutex.unlock(); emit RepoChanged(Address,1); return RET_OK; } int CModbusRepository::WriteMultipleRegs(quint16 StartAddress, QList Data) { int RegisterIndex; if(IsHRValid(StartAddress,Data.size(), &RegisterIndex) == false) { return RET_ERROR; } mMutex.lockForWrite(); int DataIndex = StartAddress - mHoldingRegisters.at(RegisterIndex).mStartAddress; for(int i = 0; i < Data.size(); i++) { mHoldingRegisters[RegisterIndex].mRegistersData[DataIndex++] = Data.at(i); } mMutex.unlock(); emit RepoChanged(StartAddress,Data.size()); return RET_OK; } QList CModbusRepository::GetRegs(quint16 StartAddress, quint16 Length, bool *OK) { int RegisterIndex; if(IsHRValid(StartAddress,Length, &RegisterIndex) == false) { if(OK != 0) { *OK = false; } return QList(); } if(OK != 0) { *OK = true; } int DataIndex = StartAddress - mHoldingRegisters.at(RegisterIndex).mStartAddress; return mHoldingRegisters[RegisterIndex].mRegistersData.mid(DataIndex,Length); } quint16 CModbusRepository::GetSingleReg(quint16 Address, bool *OK) { int RegisterIndex; if(IsHRValid(Address,1, &RegisterIndex) == false) { if(OK != 0) *OK = false; return 0; } if(OK != 0) *OK = true; mMutex.lockForRead(); int DataIndex = Address - mHoldingRegisters.at(RegisterIndex).mStartAddress; quint16 Data = mHoldingRegisters[RegisterIndex].mRegistersData[DataIndex]; mMutex.unlock(); return Data; } CHRDataMap::CHRDataMap(quint16 StartAddress, quint16 Length) { mStartAddress = StartAddress; mLength = Length; for(int i = 0; i < Length; i++) { mRegistersData.append(0); } mEndAddress = StartAddress + Length - 1; }