From f69599d280408b26f32395dc89ca72eac135b2d1 Mon Sep 17 00:00:00 2001 From: chenzihan Date: Wed, 9 Jul 2025 21:23:19 +0800 Subject: [PATCH 1/4] Signed-off-by: chenzihan fix:add Sync Ptable --- services/ptable_parse/ptable.cpp | 33 +++++++ services/ptable_parse/ptable.h | 5 +- services/ptable_parse/ufs_ptable.cpp | 135 ++++++++++++++++++++++++++- services/ptable_parse/ufs_ptable.h | 6 ++ 4 files changed, 177 insertions(+), 2 deletions(-) diff --git a/services/ptable_parse/ptable.cpp b/services/ptable_parse/ptable.cpp index d91e4b2a..757c5cb0 100644 --- a/services/ptable_parse/ptable.cpp +++ b/services/ptable_parse/ptable.cpp @@ -48,6 +48,22 @@ bool Ptable::CorrectBufByPtnList(uint8_t *imageBuf, uint64_t imgBufSize, const s return false; } +bool SyncABLunPtableDevice(const int sourceSlot) +{ + UNUSED(sourceSlot); + return false; +} + +bool GetABLunPartitionInfo(const int sourceSlot, const std::string &srcNode, + const std::string &tgtNode, uint32_t &offset) +{ + UNUSED(sourceSlot); + UNUSED(partitionName); + UNUSED(partitionName); + UNUSED(offset); + return false; +} + uint32_t Ptable::GetPtablePartitionNum() const { return partitionInfo_.size(); @@ -529,6 +545,23 @@ void Ptable::ParsePartitionName(const uint8_t *data, const uint32_t dataLen, return; } +bool Ptable::WritePartitionName(const std::string &name, const uint32_t nameLen, + uint8_t *data, const uint32_t dataLen) +{ + // 2 : convert utf16 to utf8 , 2 bytes for 1 charactor + if (data == nullptr || dataLen == 0 || nameLen == 0 || dataLen < nameLen * 2) { + LOG(ERROR) << "Invalid parameters"; + return false; + } + // convert utf16 to utf8 , 2 bytes for 1 charactor of partition name + for (uint32_t n = 0; n < nameLen; n++) { + data[n * 2] = static_cast(tolower(name[n])); + data[n * 2 + 1] = 0; + } + LOG(INFO) << "Write Partition Name success: " << name; + return true; +} + bool Ptable::WriteBufferToPath(const std::string &path, const uint64_t offset, const uint8_t *buffer, const uint32_t size) { diff --git a/services/ptable_parse/ptable.h b/services/ptable_parse/ptable.h index 7bab2056..f03e38ef 100644 --- a/services/ptable_parse/ptable.h +++ b/services/ptable_parse/ptable.h @@ -93,7 +93,9 @@ public: virtual void AddChildPtable(std::unique_ptr child) {} virtual bool CorrectBufByPtnList(uint8_t *imageBuf, uint64_t imgBufSize, const std::vector &srcInfo, const std::vector &dstInfo); - + virtual bool SyncABLunPtableDevice(const int sourceSlot); + virtual bool GetABLunPartitionInfo(const int sourceSlot, const std::string &srcNode, + const std::string &tgtNode, uint32_t &offset); int GetEndPtnIndex() { return endPtnIndex_; @@ -232,6 +234,7 @@ public: const uint32_t blockSize, GPTHeaderInfo& gptHeaderInfo); void ParsePartitionName(const uint8_t *data, const uint32_t dataLen, std::string &name, const uint32_t nameLen); + void WritePartitionName(std::string &name, const uint32_t nameLen, uint8_t *data, const uint32_t dataLen); uint32_t CalculateCrc32(const uint8_t *buffer, const uint32_t len); bool WritePtablePartition(const std::string &path, uint64_t offset, const uint8_t *buffer, uint32_t size); bool CheckFileExist(const std::string &fileName); diff --git a/services/ptable_parse/ufs_ptable.cpp b/services/ptable_parse/ufs_ptable.cpp index 4a0989fa..77ebd663 100644 --- a/services/ptable_parse/ufs_ptable.cpp +++ b/services/ptable_parse/ufs_ptable.cpp @@ -23,8 +23,12 @@ #include "log/log.h" #include "securec.h" #include "updater/updater_const.h" +#include "utils.h" namespace Updater { +constexpr const uint32_t LUN_FOR_SLOT_A = 3; +constexpr const uint32_t LUN_FOR_SLOT_B = 4; + uint32_t UfsPtable::GetDeviceLunNum() { return deviceLunNum_; @@ -614,7 +618,7 @@ bool UfsPtable::EditPartitionBuf(uint8_t *imageBuf, uint64_t imgBufSize, std::ve } return true; } - + bool UfsPtable::GetPtableImageBuffer(uint8_t *imageBuf, const uint32_t imgBufSize) { uint32_t imgBlockSize = ptableData_.lbaLen; // 512 @@ -664,4 +668,133 @@ bool UfsPtable::GetPtableImageBuffer(uint8_t *imageBuf, const uint32_t imgBufSiz } return true; } + +void UfsPtable::GetTgtPartitionName(std::string &name, const int sourceSlot) +{ + LOG(INFO) << "Get target PartitionName. source: " << name; + if (name.size() < PARTITION_AB_SUFFIX_SIZE) { + name += (sourceSlot == SLOT_A ? PARTITION_B_SUFFIX : PARTITION_A_SUFFIX); + LOG(INFO) << "Get target PartitionName: " << name; + return; + } + std::string suffix = name.substr(name.size() - PARTITION_AB_SUFFIX_SIZE, PARTITION_AB_SUFFIX_SIZE); + std::string partitionName = name.substr(0, name.size() - PARTITION_AB_SUFFIX_SIZE); + if (strcasecmp(suffix.c_str(), PARTITION_A_SUFFIX) == 0) { + name = partitionName + PARTITION_B_SUFFIX; + } else if (strcasecmp(suffix.c_str(), PARTITION_B_SUFFIX) == 0) { + name = partitionName + PARTITION_A_SUFFIX; + } else { + name += (sourceSlot == SLOT_A ? PARTITION_B_SUFFIX : PARTITION_A_SUFFIX); + } + return; +} + +bool UfsPtable::EditABPartition(uint8_t *gptImage, const uint32_t blockSize, const int sourceSlot) +{ + uint32_t partEntryCnt = blockSize / PARTITION_ENTRY_SIZE; // blockSize = 4096 + uint32_t partition0 = GET_LLWORD_FROM_BYTE(gptImage + blockSize + PARTITION_ENTRIES_OFFSET); + + uint32_t count = 0; + uint8_t *data = nullptr; + for (uint32_t i = 0; i < (MAX_PARTITION_NUM / partEntryCnt) && count < MAX_PARTITION_NUM; i++) { + data = gptImage + (partition0 + i) * blockSize; + for (uint32_t j = 0; j < partEntryCnt; j++) { + uint8_t typeGuid[GPT_PARTITION_TYPE_GUID_LEN] = {0}; + if (memcpy_s(typeGuid, sizeof(typeGuid), &data[(j * PARTITION_ENTRY_SIZE)], sizeof(typeGuid)) != EOK) { + LOG(ERROR) << "memcpy guid fail"; + } + if (typeGuid[0] == 0x00 && typeGuid[1] == 0x00) { // 0x00 means no partition + i = MAX_PARTITION_NUM / partEntryCnt; + break; + } + uint8_t *nameOffset = data + (j * PARTITION_ENTRY_SIZE + GPT_PARTITION_NAME_OFFSET); + // 2 bytes for 1 charactor of partition name + std::string name; + ParsePartitionName(nameOffset, MAX_GPT_NAME_SIZE, name, MAX_GPT_NAME_SIZE / 2); + GetTgtPartitionName(name, sourceSlot); + if (!WritePartitionName(name, name.length(), nameOffset, MAX_GPT_NAME_SIZE)) { + LOG(ERROR) << "Write PartitionName failed: " << name; + return false; + } + count++; + } + } + LOG(INFO) << "start to Calculate Crc32"; + // Updating CRC of the Partition entry array in both headers + uint32_t partCount = GET_LWORD_FROM_BYTE(gptImage + blockSize + PARTITION_COUNT_OFFSET); + uint32_t entrySize = GET_LWORD_FROM_BYTE(gptImage + blockSize + PENTRY_SIZE_OFFSET); + // mbr len + gptHeader len = 2 blockSize + uint32_t crcValue = CalculateCrc32(gptImage + (blockSize * 2), partCount * entrySize); + PUT_LONG(gptImage + blockSize + PARTITION_CRC_OFFSET, crcValue); + // Clearing CRC fields to calculate + PUT_LONG(gptImage + blockSize + HEADER_CRC_OFFSET, 0); + crcValue = CalculateCrc32(gptImage + blockSize, GPT_CRC_LEN); + PUT_LONG(gptImage + blockSize + HEADER_CRC_OFFSET, crcValue); + return true; +} + +bool UfsPtable::ModifyBufferPartitionName(uint8_t *buffer, const uint32_t bufferSize, const int sourceSlot) +{ + LOG(INFO) << "start to modify partition name in buffer"; + if (buffer == nullptr || bufferSize == 0) { + LOG(ERROR) << "invaild input"; + return false; + } + uint32_t blockSize = GetDeviceBlockSize(); + if (blockSize == 0) { + LOG(ERROR) << "invaild blockSize: " << blockSize; + return false; + } + + if (!EditABPartition(buffer, blockSize, sourceSlot)) { + LOG(ERROR) << "Edit AB PartitionName failed"; + return false; + } + LOG(INFO) << "modify partition name in buffer finished"; + return true; +} + +bool UfsPtable::SyncABLunPtableDevice(const int sourceSlot) +{ + LOG(INFO) << "start to sync ABLun Ptable in Device"; + std::string srcNodePath = GetDeviceLunNodePath(sourceSlot == SLOT_A ? LUN_FOR_SLOT_A : LUN_FOR_SLOT_B); + uint32_t len = ptableData_.writeDeviceLunSize; + std::unique_ptr buffer = std::make_unique(len); + if (buffer == nullptr) { + LOG(ERROR) << "new buffer failed!"; + return false; + } + if (!MemReadWithOffset(srcNodePath, 0, buffer.get(), len)) { + LOG(ERROR) << "read ptable from " << srcNodePath << " failed!"; + return false; + } + if (!ModifyBufferPartitionName(buffer.get(), len, sourceSlot)) { + LOG(ERROR) << "Modify PartitionName failed!"; + return false; + } + std::string tgtNodePath = GetDeviceLunNodePath(sourceSlot == SLOT_A ? LUN_FOR_SLOT_B : LUN_FOR_SLOT_A); + if (!WriteBufferToPath(tgtNodePath, 0, buffer.get(), len)) { + LOG(ERROR) << "write first gpt fail"; + return false; + } + LOG(INFO) << "Sync ABLun Ptable in Device success"; + return true; +} + +bool UfsPtable::GetABLunPartitionInfo(const int sourceSlot, std::string &srcNode, + std::string &tgtNode, uint32_t &offset) +{ + srcNode = GetDeviceLunNodePath(sourceSlot == SLOT_A ? LUN_FOR_SLOT_A : LUN_FOR_SLOT_B); + tgtNode = GetDeviceLunNodePath(sourceSlot == SLOT_A ? LUN_FOR_SLOT_B : LUN_FOR_SLOT_A); + offset = ptableData_.writeDeviceLunSize; + if (offset == 0) { + LOG(ERROR) << "invalid offset"; + return false; + } + if (!CheckFileExist(srcNode) || !CheckFileExist(tgtNode)) { + LOG(ERROR) << "Node is not exist. srcNode:" << srcNode << " tgtNode:" << (tgtNode); + return false; + } + return true; +} } // namespace Updater diff --git a/services/ptable_parse/ufs_ptable.h b/services/ptable_parse/ufs_ptable.h index a3cde0e3..f8b3979d 100644 --- a/services/ptable_parse/ufs_ptable.h +++ b/services/ptable_parse/ufs_ptable.h @@ -33,6 +33,9 @@ public: bool GetPtableImageBuffer(uint8_t *imageBuf, const uint32_t imgBufSize) override; bool CorrectBufByPtnList(uint8_t *imageBuf, uint64_t imgBufSize, const std::vector &srcInfo, const std::vector &dstInfo) override; + bool SyncABLunPtableDevice(const int sourceSlot) override; + bool GetABLunPartitionInfo(const int sourceSlot, const std::string &srcNode, + const std::string &tgtNode, uint32_t &offset) override; #ifndef UPDATER_UT protected: #else @@ -68,6 +71,9 @@ private: #else public: #endif + bool EditABPartition(uint8_t *gptImage, const uint32_t blockSize, const int sourceSlot); + void GetTgtPartitionName(std::string &name, const int sourceSlot); + bool ModifyBufferPartitionName(uint8_t *buffer, const uint32_t bufferSize, const int sourceSlot); bool WriteBackupPartitionTable(uint32_t lunIdx, uint64_t lunSize); bool UfsReadGpt(const uint8_t *gptImage, const uint32_t len, const uint32_t lun, const uint32_t blockSize); void UfsReadGptEntry(const uint8_t *gptImage, const uint32_t lun, -- Gitee From 6257d555fda83b8628c005df99bf47de5e75d598 Mon Sep 17 00:00:00 2001 From: chenzihan Date: Thu, 10 Jul 2025 09:20:14 +0800 Subject: [PATCH 2/4] Signed-off-by: chenzihan fix:add --- services/ptable_parse/ptable.cpp | 4 ++-- services/ptable_parse/ptable.h | 1 + services/ptable_parse/ufs_ptable.cpp | 2 +- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/services/ptable_parse/ptable.cpp b/services/ptable_parse/ptable.cpp index 757c5cb0..3efefee0 100644 --- a/services/ptable_parse/ptable.cpp +++ b/services/ptable_parse/ptable.cpp @@ -555,8 +555,8 @@ bool Ptable::WritePartitionName(const std::string &name, const uint32_t nameLen, } // convert utf16 to utf8 , 2 bytes for 1 charactor of partition name for (uint32_t n = 0; n < nameLen; n++) { - data[n * 2] = static_cast(tolower(name[n])); - data[n * 2 + 1] = 0; + data[n * 2] = static_cast(tolower(name[n])); // 2 : 2 bytes + data[n * 2 + 1] = 0; // 2 : 2 bytes } LOG(INFO) << "Write Partition Name success: " << name; return true; diff --git a/services/ptable_parse/ptable.h b/services/ptable_parse/ptable.h index f03e38ef..fa78ad5c 100644 --- a/services/ptable_parse/ptable.h +++ b/services/ptable_parse/ptable.h @@ -96,6 +96,7 @@ public: virtual bool SyncABLunPtableDevice(const int sourceSlot); virtual bool GetABLunPartitionInfo(const int sourceSlot, const std::string &srcNode, const std::string &tgtNode, uint32_t &offset); + int GetEndPtnIndex() { return endPtnIndex_; diff --git a/services/ptable_parse/ufs_ptable.cpp b/services/ptable_parse/ufs_ptable.cpp index 77ebd663..a8078d1f 100644 --- a/services/ptable_parse/ufs_ptable.cpp +++ b/services/ptable_parse/ufs_ptable.cpp @@ -710,7 +710,7 @@ bool UfsPtable::EditABPartition(uint8_t *gptImage, const uint32_t blockSize, con uint8_t *nameOffset = data + (j * PARTITION_ENTRY_SIZE + GPT_PARTITION_NAME_OFFSET); // 2 bytes for 1 charactor of partition name std::string name; - ParsePartitionName(nameOffset, MAX_GPT_NAME_SIZE, name, MAX_GPT_NAME_SIZE / 2); + ParsePartitionName(nameOffset, MAX_GPT_NAME_SIZE, name, MAX_GPT_NAME_SIZE / 2); // 2 : 2 bytes GetTgtPartitionName(name, sourceSlot); if (!WritePartitionName(name, name.length(), nameOffset, MAX_GPT_NAME_SIZE)) { LOG(ERROR) << "Write PartitionName failed: " << name; -- Gitee From aa60f8d9f47d36db145c594c5cb0f0b10e0d62b3 Mon Sep 17 00:00:00 2001 From: chenzihan Date: Thu, 10 Jul 2025 11:27:59 +0800 Subject: [PATCH 3/4] Signed-off-by: chenzihan fix:add --- services/ptable_parse/ptable.cpp | 10 +++++----- services/ptable_parse/ptable.h | 2 +- services/ptable_parse/ufs_ptable.h | 4 ++-- services/updater.cpp | 6 ++++++ 4 files changed, 14 insertions(+), 8 deletions(-) diff --git a/services/ptable_parse/ptable.cpp b/services/ptable_parse/ptable.cpp index 3efefee0..1babb1c7 100644 --- a/services/ptable_parse/ptable.cpp +++ b/services/ptable_parse/ptable.cpp @@ -50,17 +50,17 @@ bool Ptable::CorrectBufByPtnList(uint8_t *imageBuf, uint64_t imgBufSize, const s bool SyncABLunPtableDevice(const int sourceSlot) { - UNUSED(sourceSlot); + (void)sourceSlot; return false; } bool GetABLunPartitionInfo(const int sourceSlot, const std::string &srcNode, const std::string &tgtNode, uint32_t &offset) { - UNUSED(sourceSlot); - UNUSED(partitionName); - UNUSED(partitionName); - UNUSED(offset); + (void)sourceSlot; + (void)partitionName; + (void)partitionName; + (void)offset; return false; } diff --git a/services/ptable_parse/ptable.h b/services/ptable_parse/ptable.h index fa78ad5c..344b8557 100644 --- a/services/ptable_parse/ptable.h +++ b/services/ptable_parse/ptable.h @@ -235,7 +235,7 @@ public: const uint32_t blockSize, GPTHeaderInfo& gptHeaderInfo); void ParsePartitionName(const uint8_t *data, const uint32_t dataLen, std::string &name, const uint32_t nameLen); - void WritePartitionName(std::string &name, const uint32_t nameLen, uint8_t *data, const uint32_t dataLen); + bool WritePartitionName(const std::string &name, const uint32_t nameLen, uint8_t *data, const uint32_t dataLen); uint32_t CalculateCrc32(const uint8_t *buffer, const uint32_t len); bool WritePtablePartition(const std::string &path, uint64_t offset, const uint8_t *buffer, uint32_t size); bool CheckFileExist(const std::string &fileName); diff --git a/services/ptable_parse/ufs_ptable.h b/services/ptable_parse/ufs_ptable.h index f8b3979d..80589fe3 100644 --- a/services/ptable_parse/ufs_ptable.h +++ b/services/ptable_parse/ufs_ptable.h @@ -34,8 +34,8 @@ public: bool CorrectBufByPtnList(uint8_t *imageBuf, uint64_t imgBufSize, const std::vector &srcInfo, const std::vector &dstInfo) override; bool SyncABLunPtableDevice(const int sourceSlot) override; - bool GetABLunPartitionInfo(const int sourceSlot, const std::string &srcNode, - const std::string &tgtNode, uint32_t &offset) override; + bool GetABLunPartitionInfo(const int sourceSlot, std::string &srcNode, + std::string &tgtNode, uint32_t &offset) override; #ifndef UPDATER_UT protected: #else diff --git a/services/updater.cpp b/services/updater.cpp index 31630744..78ed1177 100644 --- a/services/updater.cpp +++ b/services/updater.cpp @@ -307,6 +307,12 @@ UpdaterStatus SetUpdateSlotParam(UpdaterParams &upParams, bool isUpdateCurrSlot) if (!Utils::IsVabDevice()) { return UPDATE_SUCCESS; } + if (!isUpdateCurrSlot && upParams.updatePackage.size() == 1) { + std::string pkgPath = upParams.updatePackage[0]; + if (pkgPath.find("updater.zip") != std::string::npos) { + isUpdateCurrSlot = true; + } + } int currentSlot = GetCurrentSlot(); if (currentSlot < 1 || currentSlot > 2) { // 2 : max slot LOG(ERROR) << "GetCurrentSlot failed"; -- Gitee From 2450176d2fa374a4e8b8e084710fc54f4d55c736 Mon Sep 17 00:00:00 2001 From: chenzihan Date: Thu, 10 Jul 2025 11:49:30 +0800 Subject: [PATCH 4/4] Signed-off-by: chenzihan fix:add --- services/ptable_parse/ptable.cpp | 7 +++---- services/ptable_parse/ptable.h | 4 ++-- 2 files changed, 5 insertions(+), 6 deletions(-) diff --git a/services/ptable_parse/ptable.cpp b/services/ptable_parse/ptable.cpp index 1babb1c7..d2a062f4 100644 --- a/services/ptable_parse/ptable.cpp +++ b/services/ptable_parse/ptable.cpp @@ -54,12 +54,11 @@ bool SyncABLunPtableDevice(const int sourceSlot) return false; } -bool GetABLunPartitionInfo(const int sourceSlot, const std::string &srcNode, - const std::string &tgtNode, uint32_t &offset) +bool GetABLunPartitionInfo(const int sourceSlot, std::string &srcNode, std::string &tgtNode, uint32_t &offset) { (void)sourceSlot; - (void)partitionName; - (void)partitionName; + (void)srcNode; + (void)tgtNode; (void)offset; return false; } diff --git a/services/ptable_parse/ptable.h b/services/ptable_parse/ptable.h index 344b8557..f88c5e86 100644 --- a/services/ptable_parse/ptable.h +++ b/services/ptable_parse/ptable.h @@ -94,8 +94,8 @@ public: virtual bool CorrectBufByPtnList(uint8_t *imageBuf, uint64_t imgBufSize, const std::vector &srcInfo, const std::vector &dstInfo); virtual bool SyncABLunPtableDevice(const int sourceSlot); - virtual bool GetABLunPartitionInfo(const int sourceSlot, const std::string &srcNode, - const std::string &tgtNode, uint32_t &offset); + virtual bool GetABLunPartitionInfo(const int sourceSlot, std::string &srcNode, + std::string &tgtNode, uint32_t &offset); int GetEndPtnIndex() { -- Gitee