From e0684c5776b56920ede8c0a01d978cb24c7aebfa Mon Sep 17 00:00:00 2001 From: w3irDv <170813473+w3irDv@users.noreply.github.com> Date: Sun, 27 Oct 2024 17:00:43 +0100 Subject: [PATCH] batch restore - mocked version - add vWii restores --- include/menu/BackupSetListState.h | 4 +- include/menu/BatchRestoreOptions.h | 9 ++-- include/savemng.h | 1 + src/main.cpp | 5 ++ src/menu/BRTitleSelectState.cpp | 77 ++++++++++++++++++++--------- src/menu/BackupSetListState.cpp | 6 +-- src/menu/BatchRestoreOptions.cpp | 79 ++++++++++++++++++------------ src/menu/BatchRestoreState.cpp | 4 +- src/savemng.cpp | 19 ++++--- 9 files changed, 132 insertions(+), 72 deletions(-) diff --git a/include/menu/BackupSetListState.h b/include/menu/BackupSetListState.h index b170aeb..cd3f582 100644 --- a/include/menu/BackupSetListState.h +++ b/include/menu/BackupSetListState.h @@ -8,7 +8,7 @@ class BackupSetListState : public ApplicationState { public: BackupSetListState(); - BackupSetListState(Title *titles, int titlesCount, bool vWiiRestore); + BackupSetListState(Title *titles, int titlesCount, bool isWiiUBatchRestore); static void resetCursorPosition(); static void resetCursorAndScroll(); @@ -44,5 +44,5 @@ class BackupSetListState : public ApplicationState { Title *titles; int titlesCount; - bool vWiiRestore; + bool isWiiUBatchRestore; }; \ No newline at end of file diff --git a/include/menu/BatchRestoreOptions.h b/include/menu/BatchRestoreOptions.h index 6ec5d5f..29bfe8b 100644 --- a/include/menu/BatchRestoreOptions.h +++ b/include/menu/BatchRestoreOptions.h @@ -9,7 +9,7 @@ class BatchRestoreOptions : public ApplicationState { public: - BatchRestoreOptions(Title *titles, int titlesCount, bool vWiiRestore); + BatchRestoreOptions(Title *titles, int titlesCount, bool isWiiUBatchRestore); enum eState { STATE_BATCH_RESTORE_OPTIONS_MENU, @@ -35,7 +35,10 @@ class BatchRestoreOptions : public ApplicationState { Title *titles; int titlesCount = 0; - int cursorPos = 0; + int cursorPos; + int minCursorPos; + + bool isWiiUBatchRestore; + - bool vWiiRestore; }; \ No newline at end of file diff --git a/include/savemng.h b/include/savemng.h index e00b6d8..4a9fe15 100644 --- a/include/savemng.h +++ b/include/savemng.h @@ -50,6 +50,7 @@ struct Title { bool saveInit; bool isTitleOnUSB; bool isTitleDupe; + bool is_Wii; uint16_t dupeID; uint8_t *iconBuf; uint64_t accountSaveSize; diff --git a/src/main.cpp b/src/main.cpp index b0331be..c1449d8 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -239,10 +239,14 @@ static Title *loadWiiUTitles(int run) { titles[wiiuTitlesCount].highID = highID; titles[wiiuTitlesCount].lowID = lowID; + titles[wiiuTitlesCount].is_Wii = ((highID & 0xFFFFFFF0) == 0x00010000); titles[wiiuTitlesCount].isTitleOnUSB = isTitleOnUSB; titles[wiiuTitlesCount].listID = wiiuTitlesCount; if (loadTitleIcon(&titles[wiiuTitlesCount]) < 0) titles[wiiuTitlesCount].iconBuf = nullptr; + + //titles[wiiuTitlesCount].is_Wii = false; + WHBLogPrintf("count %d -- iconbuf %u",wiiuTitlesCount,titles[wiiuTitlesCount].iconBuf); wiiuTitlesCount++; @@ -374,6 +378,7 @@ static Title *loadWiiTitles() { titles[i].highID = strtoul(highID, nullptr, 16); titles[i].lowID = strtoul(data->d_name, nullptr, 16); + titles[i].is_Wii = true; titles[i].listID = i; memcpy(titles[i].productCode, &titles[i].lowID, 4); diff --git a/src/menu/BRTitleSelectState.cpp b/src/menu/BRTitleSelectState.cpp index 120f45f..3c54ebf 100644 --- a/src/menu/BRTitleSelectState.cpp +++ b/src/menu/BRTitleSelectState.cpp @@ -42,35 +42,49 @@ BRTitleSelectState::BRTitleSelectState(int sduser, int wiiuuser, bool common, bo this->titles[i].currentBackup.batchRestoreState = NOT_TRIED; if ( this->titles[i].currentBackup.hasBatchBackup == false ) continue; + WHBLogPrintf("get id %u",i); + WHBLogPrintf("shortname %s",this->titles[i].shortName); + uint32_t highID = this->titles[i].highID; uint32_t lowID = this->titles[i].lowID; - + bool isWii = titles[i].is_Wii; + WHBLogPrintf("is wii %s",isWii ? "si" : "no"); std::string srcPath = getDynamicBackupPath(highID, lowID, 0); - std::string usersavePath = srcPath+"/"+getSDacc()[sduser].persistentID; - WHBLogPrintf("check user - %u",i); - WHBLogPrintf("check empty path - %s",usersavePath.c_str()); + if (! isWii) { + std::string usersavePath = srcPath+"/"+getSDacc()[sduser].persistentID; + WHBLogPrintf("check user - %u",i); + WHBLogPrintf("check empty path - %s",usersavePath.c_str()); - if (! folderEmpty(usersavePath.c_str())) - this->titles[i].currentBackup.hasUserSavedata = true; + if (! folderEmpty(usersavePath.c_str())) + this->titles[i].currentBackup.hasUserSavedata = true; - std::string commonSavePath = srcPath+"/common"; - if (! folderEmpty(commonSavePath.c_str())) - this->titles[i].currentBackup.hasCommonSavedata = true; + std::string commonSavePath = srcPath+"/common"; + if (! folderEmpty(commonSavePath.c_str())) + this->titles[i].currentBackup.hasCommonSavedata = true; - if ( sduser != -1 && common == false && ! this->titles[i].currentBackup.hasUserSavedata) - continue; + if ( sduser != -1 && common == false && ! this->titles[i].currentBackup.hasUserSavedata) + continue; - // shouldn't happen for wii u titles, but ... - if ( sduser != -1 && ! this->titles[i].currentBackup.hasCommonSavedata && ! this->titles[i].currentBackup.hasUserSavedata ) - continue; + // shouldn't happen for wii u titles, but ... + if ( sduser != -1 && ! this->titles[i].currentBackup.hasCommonSavedata && ! this->titles[i].currentBackup.hasUserSavedata ) + continue; + + WHBLogPrintf("candiadte/select set to true - %u", i); + WHBLogPrintf("init select wiiU - is wii %s",isWii ? "si" : "no"); + this->titles[i].currentBackup.candidateToBeRestored = true; // backup has enough data to try restore + this->titles[i].currentBackup.selected = true; // from candidates list, user can select/deselest at wish - WHBLogPrintf("set to true - %u", i); - this->titles[i].currentBackup.candidateToBeRestored = true; // backup has enough data to try restore - this->titles[i].currentBackup.selected = true; // from candidates list, user can select/deselest at wish + } + else + { + WHBLogPrintf("init select wii - is wii %s",isWii ? "si" : "no"); + this->titles[i].currentBackup.candidateToBeRestored = true; + this->titles[i].currentBackup.selected = true; + } // to recover title from "candidate title" index this->c2t.push_back(i); } @@ -101,34 +115,51 @@ void BRTitleSelectState::render() { } if (this->state == STATE_BATCH_RESTORE_TITLE_SELECT) { if ((this->titles == nullptr) || (this->titlesCount == 0 || (this->candidatesCount == 0))) { - promptError(LanguageUtils::gettext("No Wii U titles found.")); + promptError(LanguageUtils::gettext("No titles matching criterias found.")); this->noTitles = true; } consolePrintPos(39, 0, LanguageUtils::gettext("%s Sort: %s \ue084"), (this->titleSort > 0) ? (this->sortAscending ? "\ue083 \u2193" : "\ue083 \u2191") : "", this->sortNames[this->titleSort]); for (int i = 0; i < MAX_TITLE_SHOW; i++) { + WHBLogPrintf("iteracio %d",i); if (i + this->scroll < 0 || i + this->scroll >= (int) this->candidatesCount) break; + bool isWii = this->titles[c2t[i + this->scroll]].is_Wii; DrawUtils::setFontColor(static_cast(0x00FF00FF)); + WHBLogPrintf("candidates %d",candidatesCount); + WHBLogPrintf("scroll %d ",scroll); + WHBLogPrintf("c2t %d",c2t[i + this->scroll]); + if (!this->titles[c2t[i + this->scroll]].currentBackup.selected) DrawUtils::setFontColor(static_cast(0xFFFF00FF)); if (strcmp(this->titles[c2t[i + this->scroll]].shortName, "DONT TOUCH ME") == 0) DrawUtils::setFontColor(static_cast(0xFF0000FF)); if (this->titles[c2t[i + this->scroll]].currentBackup.batchRestoreState == KO) DrawUtils::setFontColor(static_cast(0xFF0000FF)); - if (strlen(this->titles[c2t[i + this->scroll]].shortName) != 0u) + WHBLogPrintf("nom"); + if (strlen(this->titles[c2t[i + this->scroll]].shortName) != 0u) { consolePrintPos(M_OFF, i + 2, " %s %s%s%s [%s]", this->titles[c2t[i + this->scroll]].shortName, this->titles[c2t[i + this->scroll]].isTitleOnUSB ? "(USB)" : "(NAND)", this->titles[c2t[i + this->scroll]].isTitleDupe ? " [D]" : "", this->titles[c2t[i + this->scroll]].currentBackup.selected ? LanguageUtils::gettext(" [Restore]" ) : LanguageUtils::gettext(" [Skip]"), titleStateAfterBR[this->titles[c2t[i + this->scroll]].currentBackup.batchRestoreState]); - - else - consolePrintPos(M_OFF, i + 2, " %08lx%08lx", this->titles[i + this->scroll].highID, + WHBLogPrintf("shortname %s",this->titles[c2t[i + this->scroll]].shortName); + } + else { + consolePrintPos(M_OFF, i + 2, " %08lx%08lx", this->titles[c2t[i + this->scroll]].highID, + this->titles[c2t[i + this->scroll]].lowID); + WHBLogPrintf("nameid %08lx%08lx",this->titles[c2t[i + this->scroll]].highID, this->titles[c2t[i + this->scroll]].lowID); + } DrawUtils::setFontColor(COLOR_TEXT); + WHBLogPrintf("icona"); if (this->titles[c2t[i + this->scroll]].iconBuf != nullptr) { - DrawUtils::drawTGA((M_OFF + 4) * 12 - 2, (i + 3) * 24, 0.18, this->titles[c2t[i + this->scroll]].iconBuf); + if (isWii) + DrawUtils::drawRGB5A3((M_OFF + 2) * 12 - 2, (i + 3) * 24 + 3, 0.25, + titles[c2t[i + this->scroll]].iconBuf); + else + DrawUtils::drawTGA((M_OFF + 4) * 12 - 2, (i + 3) * 24, 0.18, this->titles[c2t[i + this->scroll]].iconBuf); + WHBLogPrintf(" drawTGA -- var1 %d var2 %d c2t %d iconBuf %u",(M_OFF + 4) * 12 - 2,(i + 3) * 24,c2t[i + this->scroll],this->titles[c2t[i + this->scroll]].iconBuf); } } consolePrintPos(-1, 2 + cursorPos, "\u2192"); diff --git a/src/menu/BackupSetListState.cpp b/src/menu/BackupSetListState.cpp index 9088950..0f0ff31 100644 --- a/src/menu/BackupSetListState.cpp +++ b/src/menu/BackupSetListState.cpp @@ -21,10 +21,10 @@ BackupSetListState::BackupSetListState() { this->sortAscending = BackupSetList::sortAscending; } -BackupSetListState::BackupSetListState(Title *titles, int titlesCount, bool vWiiRestore) : +BackupSetListState::BackupSetListState(Title *titles, int titlesCount, bool isWiiUBatchRestore) : titles(titles), titlesCount(titlesCount), - vWiiRestore(vWiiRestore) { + isWiiUBatchRestore(isWiiUBatchRestore) { finalScreen = false; } @@ -101,7 +101,7 @@ ApplicationState::eSubState BackupSetListState::update(Input *input) { else // is a step in batchRestore { this->state = STATE_DO_SUBSTATE; - this->subState = std::make_unique(titles, titlesCount, vWiiRestore); + this->subState = std::make_unique(titles, titlesCount, isWiiUBatchRestore); } } if (input->get(TRIGGER, PAD_BUTTON_Y)) { diff --git a/src/menu/BatchRestoreOptions.cpp b/src/menu/BatchRestoreOptions.cpp index 0ac6bb7..590464a 100644 --- a/src/menu/BatchRestoreOptions.cpp +++ b/src/menu/BatchRestoreOptions.cpp @@ -15,9 +15,13 @@ extern Account *sdacc; extern uint8_t sdaccn; BatchRestoreOptions::BatchRestoreOptions(Title *titles, - int titlesCount,bool vWiiRestore) : titles(titles), - titlesCount(titlesCount), vWiiRestore(vWiiRestore) { + int titlesCount,bool isWiiUBatchRestore) : titles(titles), + titlesCount(titlesCount), isWiiUBatchRestore(isWiiUBatchRestore) { WHBLogPrintf("batchRestore constructor"); + WHBLogPrintf("restore type %s",isWiiUBatchRestore ? "wiiU" : "vWii"); + minCursorPos = isWiiUBatchRestore ? 0 : 3; + cursorPos = minCursorPos; + WHBLogPrintf("cursorPos %d minCursospos %d",cursorPos,minCursorPos); for (int i = 0; ititlesCount; i++) { this->titles[i].currentBackup= { .hasBatchBackup = false, @@ -29,24 +33,35 @@ BatchRestoreOptions::BatchRestoreOptions(Title *titles, }; if (this->titles[i].highID == 0 || this->titles[i].lowID == 0) continue; - if ((this->titles[i].saveInit == false) || (this->titles[i].isTitleDupe == true && this->titles[i].isTitleOnUSB == false)) + if (! this->titles[i].saveInit) + continue; + if (this->titles[i].isTitleDupe && ! this->titles[i].isTitleOnUSB) continue; if (strcmp(this->titles[i].shortName, "DONT TOUCH ME") == 0) // skip CBHC savedata continue; + if (this->titles[i].is_Wii && isWiiUBatchRestore) // wii titles installed as wiiU will need special treatment + continue; uint32_t highID = this->titles[i].highID; uint32_t lowID = this->titles[i].lowID; std::string srcPath = getDynamicBackupPath(highID, lowID, 0); DIR *dir = opendir(srcPath.c_str()); if (dir != nullptr) { - struct dirent *data; - while ((data = readdir(dir)) != nullptr) { - if(strcmp(data->d_name,".") == 0 || strcmp(data->d_name,"..") == 0 || ! (data->d_type & DT_DIR)) - continue; - if (data->d_name[0] == '8') - batchSDUsers.insert(data->d_name); - this->titles[i].currentBackup.hasBatchBackup=true; - WHBLogPrintf("has backup %d",i); - } + if (isWiiUBatchRestore) { + struct dirent *data; + while ((data = readdir(dir)) != nullptr) { + if(strcmp(data->d_name,".") == 0 || strcmp(data->d_name,"..") == 0 || ! (data->d_type & DT_DIR)) + continue; + if (data->d_name[0] == '8') + batchSDUsers.insert(data->d_name); + this->titles[i].currentBackup.hasBatchBackup=true; + WHBLogPrintf("has backup %d",i); + } + } else { + this->titles[i].currentBackup.hasBatchBackup = ! folderEmpty (srcPath.c_str()); + if (this->titles[i].currentBackup.hasBatchBackup) + WHBLogPrintf("has backup %d",i); + } + } closedir(dir); } @@ -76,32 +91,33 @@ void BatchRestoreOptions::render() { if (this->state == STATE_BATCH_RESTORE_OPTIONS_MENU) { - consolePrintPos(M_OFF, 3, LanguageUtils::gettext("Select SD user to copy from:")); - if (sduser == -1) - consolePrintPos(M_OFF, 4, " < %s >", LanguageUtils::gettext("all users")); - else - consolePrintPos(M_OFF, 4, " < %s >", getSDacc()[sduser].persistentID); - } + if (isWiiUBatchRestore) { + consolePrintPos(M_OFF, 3, LanguageUtils::gettext("Select SD user to copy from:")); + if (sduser == -1) + consolePrintPos(M_OFF, 4, " < %s >", LanguageUtils::gettext("all users")); + else + consolePrintPos(M_OFF, 4, " < %s >", getSDacc()[sduser].persistentID); + + consolePrintPos(M_OFF, 6 , LanguageUtils::gettext("Select Wii U user to copy to")); + if (this->wiiuuser == -1) + consolePrintPos(M_OFF, 7, " < %s >", LanguageUtils::gettext("same user than in source")); + else + consolePrintPos(M_OFF, 7, " < %s (%s) >", + getWiiUacc()[wiiuuser].miiName, getWiiUacc()[wiiuuser].persistentID); - consolePrintPos(M_OFF, 6 , LanguageUtils::gettext("Select Wii U user to copy to")); - if (this->wiiuuser == -1) - consolePrintPos(M_OFF, 7, " < %s >", LanguageUtils::gettext("same user than in source")); - else - consolePrintPos(M_OFF, 7, " < %s (%s) >", - getWiiUacc()[wiiuuser].miiName, getWiiUacc()[wiiuuser].persistentID); - - if (this->wiiuuser > -1) { - consolePrintPos(M_OFF, 9, LanguageUtils::gettext("Include 'common' save?")); - consolePrintPos(M_OFF, 10, " < %s >", common ? LanguageUtils::gettext("yes") : LanguageUtils::gettext("no ")); + if (this->wiiuuser > -1) { + consolePrintPos(M_OFF, 9, LanguageUtils::gettext("Include 'common' save?")); + consolePrintPos(M_OFF, 10, " < %s >", common ? LanguageUtils::gettext("yes") : LanguageUtils::gettext("no ")); + } } - consolePrintPos(M_OFF, 12, LanguageUtils::gettext(" Wipe Target users before restoring: < %s >"), wipeBeforeRestore ? LanguageUtils::gettext("Yes") : LanguageUtils::gettext("No")); consolePrintPos(M_OFF, 13, LanguageUtils::gettext(" Backup all data before restoring (strongly recommended): < %s >"), fullBackup ? LanguageUtils::gettext("Yes"):LanguageUtils::gettext("No")); consolePrintPos(M_OFF, 4 + (cursorPos < 3 ? cursorPos * 3 : cursorPos + 5 ), "\u2192"); consolePrintPosAligned(17, 4, 2, LanguageUtils::gettext("\ue000: Ok! Go to Title selection \ue001: Back")); - } + } +} ApplicationState::eSubState BatchRestoreOptions::update(Input *input) { if (this->state == STATE_BATCH_RESTORE_OPTIONS_MENU) { @@ -120,7 +136,8 @@ ApplicationState::eSubState BatchRestoreOptions::update(Input *input) { //this->subState = std::make_unique(); } if (input->get(TRIGGER, PAD_BUTTON_UP)) { - if (--cursorPos == -1) + //if (--cursorPos == -1) + if (--cursorPos < minCursorPos) ++cursorPos; if (cursorPos == 2 && sduser == -1 ) --cursorPos; diff --git a/src/menu/BatchRestoreState.cpp b/src/menu/BatchRestoreState.cpp index 3a97e71..d30d9dc 100644 --- a/src/menu/BatchRestoreState.cpp +++ b/src/menu/BatchRestoreState.cpp @@ -37,11 +37,11 @@ ApplicationState::eSubState BatchRestoreState::update(Input *input) { switch (cursorPos) { case 0: this->state = STATE_DO_SUBSTATE; - this->subState = std::make_unique(this->wiiutitles, this->wiiuTitlesCount, false); + this->subState = std::make_unique(this->wiiutitles, this->wiiuTitlesCount, true); break; case 1: this->state = STATE_DO_SUBSTATE; - this->subState = std::make_unique(this->wiititles, this->vWiiTitlesCount, true); + this->subState = std::make_unique(this->wiititles, this->vWiiTitlesCount, false); break; default: return SUBSTATE_RUNNING; diff --git a/src/savemng.cpp b/src/savemng.cpp index b9b628f..fa148d7 100644 --- a/src/savemng.cpp +++ b/src/savemng.cpp @@ -187,13 +187,14 @@ static int32_t loadFilePart(const char *fPath, uint32_t start, uint32_t size, ui fclose(file); } return ret; -} +} int32_t loadTitleIcon(Title *title) { uint32_t highID = title->highID; uint32_t lowID = title->lowID; bool isUSB = title->isTitleOnUSB; - bool isWii = ((highID & 0xFFFFFFF0) == 0x00010000); + bool isWii = title->is_Wii; + //bool isWii = ((highID & 0xFFFFFFF0) == 0x00010000); std::string path; if (isWii) { @@ -788,7 +789,7 @@ bool hasAccountSave(Title *title, bool inSD, bool iine, uint32_t user, uint8_t s uint32_t highID = title->highID; uint32_t lowID = title->lowID; bool isUSB = title->isTitleOnUSB; - bool isWii = ((highID & 0xFFFFFFF0) == 0x00010000); + bool isWii = title->is_Wii; if (highID == 0 || lowID == 0) return false; @@ -841,7 +842,7 @@ bool hasCommonSave(Title *title, bool inSD, bool iine, uint8_t slot, int version uint32_t highID = title->highID; uint32_t lowID = title->lowID; bool isUSB = title->isTitleOnUSB; - bool isWii = ((highID & 0xFFFFFFF0) == 0x00010000); + bool isWii = title->is_Wii; if (isWii) return false; @@ -1009,7 +1010,7 @@ void backupAllSave(Title *titles, int count, const std::string & batchDatetime) uint32_t highID = titles[i].highID; uint32_t lowID = titles[i].lowID; bool isUSB = titles[i].isTitleOnUSB; - bool isWii = ((highID & 0xFFFFFFF0) == 0x00010000); + bool isWii = titles[i].is_Wii; if ((sourceStorage == 0 && !isUSB) || (sourceStorage == 1 && isUSB)) // backup first WiiU USB savedata to slot 0 continue; uint8_t slot = getEmptySlot(highID,lowID,batchDatetime); @@ -1035,7 +1036,7 @@ void backupSavedata(Title *title, uint8_t slot, int8_t wiiuuser, bool common) { uint32_t highID = title->highID; uint32_t lowID = title->lowID; bool isUSB = title->isTitleOnUSB; - bool isWii = ((highID & 0xFFFFFFF0) == 0x00010000); + bool isWii = title->is_Wii; const std::string path = (isWii ? "storage_slccmpt01:/title" : (isUSB ? (getUSB() + "/usr/save").c_str() : "storage_mlc01:/usr/save")); std::string srcPath = StringUtils::stringFormat("%s/%08x/%08x/%s", path.c_str(), highID, lowID, isWii ? "data" : "user"); std::string dstPath; @@ -1139,7 +1140,8 @@ int restoreSavedata(Title *title, uint8_t slot, int8_t sduser, int8_t wiiuuser, uint32_t highID = title->highID; uint32_t lowID = title->lowID; bool isUSB = title->isTitleOnUSB; - bool isWii = ((highID & 0xFFFFFFF0) == 0x00010000); + bool isWii = title->is_Wii; + WHBLogPrintf("title type %s", isWii ? "vWii":"wiiU"); std::string srcPath; srcPath = getDynamicBackupPath(highID, lowID, slot); const std::string path = (isWii ? "storage_slccmpt01:/title" : (isUSB ? (getUSB() + "/usr/save").c_str() : "storage_mlc01:/usr/save")); @@ -1301,7 +1303,8 @@ int wipeSavedata(Title *title, int8_t wiiuuser, bool common, bool interactive /* uint32_t highID = title->highID; uint32_t lowID = title->lowID; bool isUSB = title->isTitleOnUSB; - bool isWii = ((highID & 0xFFFFFFF0) == 0x00010000); + bool isWii = title->is_Wii; + WHBLogPrintf("title type %s", isWii ? "vWii":"wiiU"); std::string srcPath; std::string commonPath; std::string path;