1
0
Fork 0
mirror of https://github.com/HamletDuFromage/aio-switch-updater.git synced 2024-12-29 10:56:01 +00:00

Made ini avoidance more robust, added a download payload option and cleaned stuff up

This commit is contained in:
flb 2020-09-21 20:36:46 +02:00
parent 1b56d6f15a
commit 2feb6901d6
17 changed files with 150 additions and 61 deletions

View file

@ -45,7 +45,7 @@ DATA := data
INCLUDES := include lib/minizip/include INCLUDES := include lib/minizip/include
APP_TITLE := AIO Switch Updater APP_TITLE := AIO Switch Updater
APP_AUTHOR := HamletDuFromage APP_AUTHOR := HamletDuFromage
APP_VERSION := 1.0.3 APP_VERSION := 1.1.0
#ROMFS := $(BUILD)/romfs #ROMFS := $(BUILD)/romfs
BOREALIS_PATH := lib/borealis BOREALIS_PATH := lib/borealis

View file

@ -1,8 +1,6 @@
#pragma once #pragma once
#include "utils.hpp"
#include "JC_color_swapper.hpp" #include "JC_color_swapper.hpp"
#include "constants.hpp"
#include "confirm_page.hpp" #include "confirm_page.hpp"
#include "worker_page.hpp" #include "worker_page.hpp"

View file

@ -2,10 +2,9 @@
#include <borealis.hpp> #include <borealis.hpp>
#include <chrono> #include <chrono>
#include <algorithm>
#include "utils.hpp" #include "utils.hpp"
#include "download.hpp"
#include "constants.hpp"
#include "main_frame.hpp" #include "main_frame.hpp"
class ConfirmPage : public brls::View class ConfirmPage : public brls::View

View file

@ -19,6 +19,8 @@
#define CFW_URL "https://hamletdufromage.github.io/switch-cfw/cfw.html" #define CFW_URL "https://hamletdufromage.github.io/switch-cfw/cfw.html"
#define CFW_FILENAME "/config/aio-switch-updater/cfw.zip" #define CFW_FILENAME "/config/aio-switch-updater/cfw.zip"
#define PAYLOAD_URL "https://hamletdufromage.github.io/switch-payloads/payloads.html"
#define CHEATS_RELEASE_URL "https://github.com/HamletDuFromage/switch-cheats-db/releases/tag/v1.0" #define CHEATS_RELEASE_URL "https://github.com/HamletDuFromage/switch-cheats-db/releases/tag/v1.0"
#define CHEATS_URL_TITLES "https://github.com/HamletDuFromage/switch-cheats-db/releases/download/v1.0/titles.zip" #define CHEATS_URL_TITLES "https://github.com/HamletDuFromage/switch-cheats-db/releases/download/v1.0/titles.zip"
#define CHEATS_URL_CONTENTS "https://github.com/HamletDuFromage/switch-cheats-db/releases/download/v1.0/contents.zip" #define CHEATS_URL_CONTENTS "https://github.com/HamletDuFromage/switch-cheats-db/releases/download/v1.0/contents.zip"

View file

@ -0,0 +1,17 @@
#pragma once
#include "utils.hpp"
#include "confirm_page.hpp"
#include "worker_page.hpp"
class DownloadPayloadPage : public brls::AppletFrame
{
private:
brls::Label* label;
brls::Label* notFound;
brls::List* list;
std::vector<brls::ListItem*> items;
public:
DownloadPayloadPage();
};

View file

@ -22,7 +22,6 @@
#include "progress_event.hpp" #include "progress_event.hpp"
#include "constants.hpp" #include "constants.hpp"
#include "utils.hpp"
static constexpr u32 MaxTitleCount = 64000; static constexpr u32 MaxTitleCount = 64000;
@ -39,6 +38,7 @@ typedef struct Title {
} Title; } Title;
void extract(const char* filename, const char* workingPath = ROOT_PATH, int overwriteInis = 1); void extract(const char* filename, const char* workingPath = ROOT_PATH, int overwriteInis = 1);
void extract(const char * filename, const char* workingPath, const char* toExclude);
std::string formatApplicationId(u64 ApplicationId); std::string formatApplicationId(u64 ApplicationId);
std::vector<Title> getInstalledTitlesNs(); std::vector<Title> getInstalledTitlesNs();
std::vector<Title> excludeTitles(const char* path, std::vector<Title> listedTitles); std::vector<Title> excludeTitles(const char* path, std::vector<Title> listedTitles);

View file

@ -4,15 +4,12 @@
#include <string> #include <string>
#include "download.hpp" #include "download.hpp"
#include "extract.hpp" #include "extract.hpp"
#include "constants.hpp"
#include "confirm_page.hpp" #include "confirm_page.hpp"
#include "worker_page.hpp" #include "worker_page.hpp"
#include "utils.hpp"
class ListDownloadTab : public brls::List class ListDownloadTab : public brls::List
{ {
private: private:
std::tuple<std::vector<std::string>, std::vector<std::string>> links;
std::vector<brls::ListItem*> linkItems; std::vector<brls::ListItem*> linkItems;
brls::Label *notFound; brls::Label *notFound;
brls::Label *description; brls::Label *description;

View file

@ -2,7 +2,6 @@
#include <borealis.hpp> #include <borealis.hpp>
#include "utils.hpp"
#include "about_tab.hpp" #include "about_tab.hpp"
#include "list_download_tab.hpp" #include "list_download_tab.hpp"
#include "tools_tab.hpp" #include "tools_tab.hpp"

View file

@ -5,6 +5,7 @@
#include "worker_page.hpp" #include "worker_page.hpp"
#include "app_page.hpp" #include "app_page.hpp"
#include "payload_page.hpp" #include "payload_page.hpp"
#include "download_payload_page.hpp"
#include "JC_page.hpp" #include "JC_page.hpp"
#include "extract.hpp" #include "extract.hpp"
#include "utils.hpp" #include "utils.hpp"
@ -18,6 +19,7 @@ class ToolsTab : public brls::List
brls::ListItem* JCcolor; brls::ListItem* JCcolor;
brls::ListItem* updateApp; brls::ListItem* updateApp;
brls::ListItem* rebootPayload; brls::ListItem* rebootPayload;
brls::ListItem* downloadPaysload;
brls::StagedAppletFrame* stagedFrame; brls::StagedAppletFrame* stagedFrame;
public: public:

View file

@ -23,4 +23,5 @@ std::string formatApplicationId(u64 ApplicationId);
std::set<std::string> readLineByLine(const char * path); std::set<std::string> readLineByLine(const char * path);
std::vector<std::string> fetchPayloads(); std::vector<std::string> fetchPayloads();
void shut_down(bool reboot = false); void shut_down(bool reboot = false);
int showDialogBox(std::string text, std::string opt1, std::string opt2);
std::string getLatestTag(const char *url); std::string getLatestTag(const char *url);

View file

@ -1,5 +1,4 @@
#include "confirm_page.hpp" #include "confirm_page.hpp"
#include <algorithm>
ConfirmPage::ConfirmPage(brls::StagedAppletFrame* frame, std::string text, bool done): done(done) ConfirmPage::ConfirmPage(brls::StagedAppletFrame* frame, std::string text, bool done): done(done)
{ {

View file

@ -174,7 +174,6 @@ std::string fetchTitle(const char *url){
/* check for errors */ /* check for errors */
std::string ver = "-1"; std::string ver = "-1";
std::string s = std::string(chunk.memory); std::string s = std::string(chunk.memory);
//std::cout << "start html " << s.substr(0, 199) << std::endl;
std::regex rgx("<title>.+</title>"); std::regex rgx("<title>.+</title>");
std::smatch match; std::smatch match;
if (std::regex_search(s, match, rgx)){ if (std::regex_search(s, match, rgx)){

View file

@ -0,0 +1,51 @@
#include "download_payload_page.hpp"
DownloadPayloadPage::DownloadPayloadPage() : AppletFrame(true, true)
{
this->setTitle("Download payloads");
list = new brls::List();
label = new brls::Label(
brls::LabelStyle::DESCRIPTION,
"Select a payload to download to " + std::string(BOOTLOADER_PL_PATH) + ".",
true
);
list->addView(label);
std::tuple<std::vector<std::string>, std::vector<std::string>> links = fetchLinks(PAYLOAD_URL);
int nbLinks = std::get<0>(links).size();
if(nbLinks){
items.reserve(nbLinks);
for (int i = 0; i<nbLinks; i++){
std::string url = std::get<1>(links)[i];
std::string path = std::string(BOOTLOADER_PL_PATH) + std::get<0>(links)[i];
std::string text("Downloading:\n" + std::get<0>(links)[i] + "\n\nFrom:\n" + url);
items[i] = new brls::ListItem(std::get<0>(links)[i]);
items[i]->getClickEvent()->subscribe([&, text, url, path](brls::View* view) {
createTree(BOOTLOADER_PL_PATH);
brls::StagedAppletFrame* stagedFrame = new brls::StagedAppletFrame();
stagedFrame->setTitle("Getting payload");
stagedFrame->addStage(
new ConfirmPage(stagedFrame, text)
);
stagedFrame->addStage(
new WorkerPage(stagedFrame, "Downloading...", [url, path](){downloadFile(url.c_str(), path.c_str(), OFF);})
);
stagedFrame->addStage(
new ConfirmPage(stagedFrame, "All done!", true)
);
brls::Application::pushView(stagedFrame);
});
list->addView(items[i]);
}
}
else{
notFound = new brls::Label(
brls::LabelStyle::DESCRIPTION,
"Could not find a download link, make sure the Switch has access to the internet.\n"\
"If this problem persists, please open an issue on Github",
true
);
notFound->setHorizontalAlign(NVG_ALIGN_CENTER);
list->addView(notFound);
}
this->setContentView(list);
}

View file

@ -9,8 +9,12 @@ void extract(const char * filename, const char* workingPath, int overwriteInis){
ProgressEvent::instance().setTotalSteps(entries.size() + 1); ProgressEvent::instance().setTotalSteps(entries.size() + 1);
for (int i = 0; i < (int) entries.size(); i++){ for (int i = 0; i < (int) entries.size(); i++){
if(overwriteInis == 0){ if(overwriteInis == 0){
if(entries[i].name.substr(entries[i].name.length() - 4) != ".ini") if(entries[i].name.substr(entries[i].name.length() - 4) == ".ini"){
if(!std::filesystem::exists("/" + entries[i].name)) unzipper.extractEntry(entries[i].name);
}
else{
unzipper.extractEntry(entries[i].name); unzipper.extractEntry(entries[i].name);
}
} }
else else
unzipper.extractEntry(entries[i].name); unzipper.extractEntry(entries[i].name);
@ -21,6 +25,28 @@ void extract(const char * filename, const char* workingPath, int overwriteInis){
ProgressEvent::instance().setStep(ProgressEvent::instance().getMax()); ProgressEvent::instance().setStep(ProgressEvent::instance().getMax());
} }
void extract(const char * filename, const char* workingPath, const char* toExclude){
ProgressEvent::instance().reset();
ProgressEvent::instance().setStep(1);
chdir(workingPath);
zipper::Unzipper unzipper(filename);
std::vector<zipper::ZipEntry> entries = unzipper.entries();
ProgressEvent::instance().setTotalSteps(entries.size() + 1);
for (int i = 0; i < (int) entries.size(); i++){
if("/" + entries[i].name == toExclude){
if(!std::filesystem::exists(toExclude)) {
unzipper.extractEntry(entries[i].name);
}
}
else {
unzipper.extractEntry(entries[i].name);
}
ProgressEvent::instance().setStep(i);
}
unzipper.close();
ProgressEvent::instance().setStep(ProgressEvent::instance().getMax());
}
std::vector<Title> getInstalledTitlesNs(){ std::vector<Title> getInstalledTitlesNs(){
// This function has been cobbled together from the "app_controldata" example in devkitpro. // This function has been cobbled together from the "app_controldata" example in devkitpro.
@ -76,7 +102,6 @@ std::vector<Title> getInstalledTitlesNs(){
if (R_FAILED(rc)) { if (R_FAILED(rc)) {
totalFailed++; totalFailed++;
std::cout << "nsGetApplicationControlData() failed: 0x" << std::hex << rc << " for Title ID: " << formatApplicationId(recs[i].application_id) << std::endl;
} }
if (outsize < sizeof(buf->nacp)) { if (outsize < sizeof(buf->nacp)) {
@ -165,17 +190,20 @@ void extractCheats(const char * zipPath, std::vector<Title> titles, CFW cfw, boo
switch(cfw){ switch(cfw){
case ams: case ams:
offset = std::string(CONTENTS_PATH).length(); offset = std::string(CONTENTS_PATH).length();
createTree(AMS_CONTENTS); std::filesystem::create_directory(AMS_PATH);
std::filesystem::create_directory(AMS_CONTENTS);
chdir(AMS_PATH); chdir(AMS_PATH);
break; break;
case rnx: case rnx:
offset = std::string(CONTENTS_PATH).length(); offset = std::string(CONTENTS_PATH).length();
createTree(REINX_CONTENTS); std::filesystem::create_directory(REINX_PATH);
std::filesystem::create_directory(REINX_CONTENTS);
chdir(REINX_PATH); chdir(REINX_PATH);
break; break;
case sxos: case sxos:
offset = std::string(TITLES_PATH).length(); offset = std::string(TITLES_PATH).length();
createTree(SXOS_TITLES); std::filesystem::create_directory(SXOS_PATH);
std::filesystem::create_directory(SXOS_TITLES);
chdir(SXOS_PATH); chdir(SXOS_PATH);
break; break;
} }
@ -217,11 +245,6 @@ void extractCheats(const char * zipPath, std::vector<Title> titles, CFW cfw, boo
k++; k++;
} }
} }
brls::Logger::debug("Titles size:");
std::cout << titles.size() << std::endl;
brls::Logger::debug("Parents size:");
std::cout << parents.size() << std::endl;
size_t lastL = 0; size_t lastL = 0;
std::string name; std::string name;

View file

@ -3,6 +3,7 @@
ListDownloadTab::ListDownloadTab(archiveType type) : ListDownloadTab::ListDownloadTab(archiveType type) :
brls::List() brls::List()
{ {
std::tuple<std::vector<std::string>, std::vector<std::string>> links;
std::string operation = "Getting "; std::string operation = "Getting ";
this->description = new brls::Label(brls::LabelStyle::DESCRIPTION, "", true); this->description = new brls::Label(brls::LabelStyle::DESCRIPTION, "", true);
switch(type){ switch(type){
@ -89,13 +90,13 @@ ListDownloadTab::ListDownloadTab(archiveType type) :
} }
else{ else{
notFound = new brls::Label( notFound = new brls::Label(
brls::LabelStyle::DESCRIPTION, brls::LabelStyle::DESCRIPTION,
"Could not find a download link, make sure the Switch has access to the internet.\n"\ "Could not find a download link, make sure the Switch has access to the internet.\n"\
"If this problem persists, please open an issue on Github", "If this problem persists, please open an issue on Github",
true true
); );
notFound->setHorizontalAlign(NVG_ALIGN_CENTER); notFound->setHorizontalAlign(NVG_ALIGN_CENTER);
this->addView(notFound); this->addView(notFound);
} }
} }

View file

@ -31,6 +31,18 @@ ToolsTab::ToolsTab() : brls::List()
}); });
this->addView(JCcolor); this->addView(JCcolor);
downloadPaysload = new brls::ListItem("Dowload payloads to " + std::string(BOOTLOADER_PL_PATH));
downloadPaysload->getClickEvent()->subscribe([&](brls::View* view){
brls::Application::pushView(new DownloadPayloadPage());
});
this->addView(downloadPaysload);
rebootPayload = new brls::ListItem("Shut down / Inject payload");
rebootPayload->getClickEvent()->subscribe([&](brls::View* view){
brls::Application::pushView(new PayloadPage());
});
this->addView(rebootPayload);
std::string tag = getLatestTag(TAGS_INFO); std::string tag = getLatestTag(TAGS_INFO);
if(!tag.empty()){ if(!tag.empty()){
updateApp = new brls::ListItem("Update the app (v" + tag +")"); updateApp = new brls::ListItem("Update the app (v" + tag +")");
@ -54,11 +66,4 @@ ToolsTab::ToolsTab() : brls::List()
}); });
this->addView(updateApp); this->addView(updateApp);
} }
rebootPayload = new brls::ListItem("Shut down / Inject payload");
rebootPayload->getClickEvent()->subscribe([&](brls::View* view){
brls::Application::pushView(new PayloadPage());
});
this->addView(rebootPayload);
} }

View file

@ -75,40 +75,41 @@ void downloadArchive(std::string url, archiveType type){
int dialogResult = -1; int dialogResult = -1;
void extractArchive(archiveType type){ int showDialogBox(std::string text, std::string opt1, std::string opt2){
int overwriteInis = -1; int result = -1;
std::vector<Title> titles; brls::Dialog* dialog = new brls::Dialog(text);
brls::Dialog* dialog = new brls::Dialog("Do you want to overwrite existing .ini files?"); brls::GenericEvent::Callback callback1 = [dialog](brls::View* view) {
brls::GenericEvent::Callback noCallback = [dialog](brls::View* view) {
dialogResult = 0; dialogResult = 0;
dialog->close(); dialog->close();
}; };
brls::GenericEvent::Callback yesCallback = [dialog](brls::View* view) { brls::GenericEvent::Callback callback2 = [dialog](brls::View* view) {
dialogResult = 1; dialogResult = 1;
dialog->close(); dialog->close();
}; };
dialog->addButton("No", noCallback); dialog->addButton(opt1, callback1);
dialog->addButton("Yes", yesCallback); dialog->addButton(opt2, callback2);
dialog->setCancelable(false); dialog->setCancelable(false);
dialog->open();
while(result == -1){
usleep(1);
result = dialogResult;
}
dialogResult = -1;
return result;
}
void extractArchive(archiveType type){
int overwriteInis = 0;
std::vector<Title> titles;
switch(type){ switch(type){
case sigpatches: case sigpatches:
if(isArchive(SIGPATCHES_FILENAME)) { if(isArchive(SIGPATCHES_FILENAME)) {
std::string backup(HEKATE_IPL_PATH); std::string backup(HEKATE_IPL_PATH);
backup += ".old"; backup += ".old";
if(std::filesystem::exists(HEKATE_IPL_PATH)){ if(std::filesystem::exists(HEKATE_IPL_PATH)){
dialog->open(); overwriteInis = showDialogBox("Do you want to overwrite existing " + std::string(HEKATE_IPL_PATH) +"?", "No", "Yes");
while(overwriteInis == -1){
usleep(1);
overwriteInis = dialogResult;
}
dialogResult = -1;
if(overwriteInis == 0){ if(overwriteInis == 0){
std::filesystem::remove(backup); extract(SIGPATCHES_FILENAME, ROOT_PATH, HEKATE_IPL_PATH);
std::filesystem::rename(HEKATE_IPL_PATH, backup);
extract(SIGPATCHES_FILENAME);
std::filesystem::remove(HEKATE_IPL_PATH);
std::filesystem::rename(backup, HEKATE_IPL_PATH);
} }
else{ else{
extract(SIGPATCHES_FILENAME); extract(SIGPATCHES_FILENAME);
@ -133,12 +134,7 @@ void extractArchive(archiveType type){
extract(APP_FILENAME); extract(APP_FILENAME);
break; break;
case cfw: case cfw:
dialog->open(); overwriteInis = showDialogBox("Do you want to overwrite existing .ini config files?", "No", "Yes");
while(overwriteInis == -1){
usleep(1);
overwriteInis = dialogResult;
}
dialogResult = -1;
extract(CFW_FILENAME, ROOT_PATH, overwriteInis); extract(CFW_FILENAME, ROOT_PATH, overwriteInis);
break; break;
} }