SystemGui/Sources/PICUploader/HexRecord.cpp

199 lines
4.9 KiB
C++

#include "HexRecord.h"
#include <QByteArray>
#include <QDataStream>
CHexRecord::CHexRecord(void)
{
mRecordData = NULL;
}
CHexRecord::~CHexRecord(void)
{
mStartAddress = 0;
mRecordSize = 0;
mRecordType = 0;
mExtendedAddress = 0;
// delete[] mRecordData;
}
int CHexRecord::DecodeRawRecord(QString *RawRecordData, unsigned int HighAddress)
{
bool OK;
// CString RecordString;
QString RecordString;
bool IsAllFF = true;
int StartIndex = RawRecordData->indexOf(QChar(':'));
if(StartIndex == -1)
return -1;
RecordString = RawRecordData->right(RawRecordData->length()-1); //Remove all that is left of ':'
QString RecordSizeString;
RecordSizeString = RecordString.mid(0,2);
//sscanf_s(RecordSizeString.GetBuffer(),"%x",&mRecordSize);
mRecordSize = RecordSizeString.toUInt(&OK,16);
QString RecordAddress;
RecordAddress = RecordString.mid(2,4);
//sscanf_s(RecordAddress.GetBuffer(),"%x",&mStartAddress);
mStartAddress = RecordAddress.toUInt(&OK,16);
mStartAddress |= (HighAddress & 0xFFFF0000);
if(mStartAddress == 0x1d0097F0)
{
mStartAddress = mStartAddress;
}
QString RecordTypeString;
RecordTypeString = RecordString.mid(6,2);
//sscanf_s(RecordTypeString.GetBuffer(),"%x",&mRecordType);
mRecordType = RecordTypeString.toUInt(&OK,16);
RecordString = RecordString.right(RecordString.length()- 8);
if(mRecordType >= MAX_RECORD_TYPE)
return RET_UNKNOWN_RECORD_TYPE;
if(mRecordSize %2 != 0)
{
mRecordSize++;//Pad the last word if we do not have an even number of bytes in the record.
}
switch(mRecordType)
{
case DATA_RECORD_TYPE: //0x00
{
char *DataPtr;
QString DataString;
// mRecordData = new char[mRecordSize/*+10*/]; //I have no clue why I have to allocate more space but if I don't delete[] crashes. I think it's a scanf bug...
// DataPtr = mRecordData.data();
for(unsigned int i = 0; i < mRecordSize; i++)
{
DataString = RecordString.mid(2*i,2);
char DataByte = (char)DataString.toUShort(&OK,16);
//sscanf_s(DataString.GetBuffer(),"%x",&mRecordData[i],sizeof(char)/*DataPtr*/);
//mRecordData[i] = (char)DataString.toUShort(&OK,16);
mRecordData.append(DataByte);
if((unsigned char)DataByte != 0xFF)
IsAllFF = false;
//DataPtr++;
}
if(mRecordSize %2 != 0) //Is this really needed?
{
//*DataPtr++ = 0xFF; //Pad the last word if we do not have an even number of bytes in the record.
mRecordData.append(0xFF);
}
mRecordSize /= 4; //Transfom the size in WORD size...
//#ifdef IGNORE_ALL_FF_RECORDS
if(IsAllFF)
{
return RET_IGNORED_ALL_FF_RECORD;
}
else
return RET_DATA_RECORD;
//#else
// return RET_DATA_RECORD;
//#endif
break;
}
case EOF_RECORD_TYPE: //0x01
{
return RET_EOF_RECORD;
break;
}
case EXTENDED_ADDRESS_TYPE: //0x02
{
return RET_UNMANAGED_RECORD_TYPE;
break;
}
case START_SEGMENT_ADDRESS_TYPE: //0x03
{
return RET_UNMANAGED_RECORD_TYPE;
break;
}
case EXTENDED_LINEAR_ADDRESS_TYPE: //0x04
{
QString ExtendedAddressString;
ExtendedAddressString = RecordString.mid(0,4);
//sscanf_s(ExtendedAddressString.GetBuffer(),"%x",&mExtendedAddress);
mExtendedAddress = ExtendedAddressString.toUInt(&OK,16);
mExtendedAddress <<= 16;
return RET_EXTENDED_LINEAR_ADDRESS;
break;
}
case START_LINEAR_ADDRESS_TYPE: //0x05
{
return RET_UNMANAGED_RECORD_TYPE;
break;
}
default:
{
return RET_UNKNOWN_RECORD_TYPE;
}
}
}
unsigned int CHexRecord::AppendRecord(CHexRecord *NewRecord)
{
unsigned int NewSize;
NewSize = GetRecordSizeInBytes() + NewRecord->GetRecordSizeInBytes();
// char *NewBuff = new char[NewSize];
// memcpy(NewBuff,mRecordData,GetRecordSizeInBytes());
// memcpy(&NewBuff[GetRecordSizeInBytes()],NewRecord->GetDataBuffer(),NewRecord->GetRecordSizeInBytes());
//delete[] mRecordData;
//mRecordData = NewBuff;
mRecordData.append(NewRecord->GetData());
mRecordSize = NewSize/4;
return 1;
}
CHexRecord& CHexRecord::operator = (const CHexRecord &rhs)
{
if(this == &rhs)
return *this;
mExtendedAddress = rhs.mExtendedAddress;
mRecordSize = rhs.mRecordSize;
mStartAddress = rhs.mStartAddress;
mRecordType = rhs.mRecordType;
mRecordData = rhs.mRecordData;
// mRecordData = new char[mRecordSize*4];
// memcpy(mRecordData,rhs.mRecordData,mRecordSize*4);
return *this;
}
QByteArray CHexRecord::GetRecord()
{
QByteArray Record;
Record.clear();
QDataStream Strm(&Record,QIODevice::WriteOnly);
//Header
Strm << HEX_RECORD_HEADER;
//Size
Strm << GetRecordSizeInBytes();
//Address
Strm << GetStartAddress();
//Data
Record.append(mRecordData);
return Record;
}