diff --git a/VortexEngine/src/Modes/Modes.cpp b/VortexEngine/src/Modes/Modes.cpp index 9980509ed4..2b96c53745 100644 --- a/VortexEngine/src/Modes/Modes.cpp +++ b/VortexEngine/src/Modes/Modes.cpp @@ -712,7 +712,36 @@ bool Modes::setFlag(uint8_t flag, bool enable, bool save) m_globalFlags &= ~flag; } DEBUG_LOGF("Toggled instant on/off to %s", enable ? "on" : "off"); - return !save || saveHeader(); + if (!save) { + // if save is not requested then just return here + return true; + } + // otherwise need to update the global flags field of the save header in storage + ByteStream headerBuffer; + // read out the storage header so we can update the flag field + if (!Storage::read(0, headerBuffer) || !headerBuffer.size()) { + // if cannot read the save header then just save it normally + return saveHeader(); + } + // layout of the save header, this struct is never really used anywhere else + // except here the actual layout of the save header is dictated by + // saveHeader() and serializeSaveHeader() + struct SaveHeader { + uint8_t vMajor; + uint8_t vMinor; + uint8_t globalFlags; + uint8_t brightness; + uint8_t numModes; + }; + // data cannot be NULL since size is non zero + SaveHeader *pHeader = (SaveHeader *)headerBuffer.data(); + // update the global flags field in the header + pHeader->globalFlags = m_globalFlags; + // need to force the crc to recalc since we modified the data, just mark the + // CRC as dirty and Storage::write() will re-calculate the CRC if it's dirty + headerBuffer.setCRCDirty(); + // write the save header back to storage + return Storage::write(0, headerBuffer); } #ifdef VORTEX_LIB diff --git a/VortexEngine/src/Serial/ByteStream.cpp b/VortexEngine/src/Serial/ByteStream.cpp index f77ebae5e9..56ae424044 100644 --- a/VortexEngine/src/Serial/ByteStream.cpp +++ b/VortexEngine/src/Serial/ByteStream.cpp @@ -338,6 +338,15 @@ bool ByteStream::isCRCDirty() const return (m_pData && (m_pData->flags & BUFFER_FLAG_DIRTY) != 0); } +void ByteStream::setCRCDirty() +{ + if (!m_pData) { + return; + } + // set the dirty flag + m_pData->flags |= BUFFER_FLAG_DIRTY; +} + bool ByteStream::serialize8(uint8_t byte) { //DEBUG_LOGF("Serialize8(): %u", byte); @@ -350,7 +359,7 @@ bool ByteStream::serialize8(uint8_t byte) // walk forward m_pData->size += sizeof(uint8_t); // dirty the crc - m_pData->flags |= BUFFER_FLAG_DIRTY; + setCRCDirty(); return true; } @@ -366,7 +375,7 @@ bool ByteStream::serialize16(uint16_t bytes) // walk forward m_pData->size += sizeof(uint16_t); // dirty the crc - m_pData->flags |= BUFFER_FLAG_DIRTY; + setCRCDirty(); return true; } @@ -382,7 +391,7 @@ bool ByteStream::serialize32(uint32_t bytes) // walk forward m_pData->size += sizeof(uint32_t); // dirty the crc - m_pData->flags |= BUFFER_FLAG_DIRTY; + setCRCDirty(); return true; } diff --git a/VortexEngine/src/Serial/ByteStream.h b/VortexEngine/src/Serial/ByteStream.h index 558cfc6e9f..937901f570 100644 --- a/VortexEngine/src/Serial/ByteStream.h +++ b/VortexEngine/src/Serial/ByteStream.h @@ -76,6 +76,8 @@ class ByteStream // check whether the data in the buffer has changed since the // crc has been re-calculated, if it is dirty, call recalcCRC bool isCRCDirty() const; + // mark the CRC as dirty (manually modified the buffer or something) + void setCRCDirty(); // serialize a byte into the buffer bool serialize8(uint8_t byte);