Make JSON reading safer

- Check that the file actually opened before reading it
- If the JSON was discarded, then make just use an empty object
This commit is contained in:
Pk11
2021-03-23 04:47:49 -05:00
parent 5343661069
commit 77edd99749
7 changed files with 65 additions and 39 deletions
-6
View File
@@ -50,19 +50,15 @@ public:
std::vector<std::string> GetInstalled(const std::string &unistoreName, const std::string &entry) const; std::vector<std::string> GetInstalled(const std::string &unistoreName, const std::string &entry) const;
void SetUpdated(const std::string &unistoreName, const std::string &entry, const std::string &updated) { void SetUpdated(const std::string &unistoreName, const std::string &entry, const std::string &updated) {
if (this->metadataJson.is_discarded()) return;
this->metadataJson[unistoreName][entry]["updated"] = updated; this->metadataJson[unistoreName][entry]["updated"] = updated;
}; };
void SetMarks(const std::string &unistoreName, const std::string &entry, int marks) { void SetMarks(const std::string &unistoreName, const std::string &entry, int marks) {
if (this->metadataJson.is_discarded()) return;
this->metadataJson[unistoreName][entry]["marks"] = marks; this->metadataJson[unistoreName][entry]["marks"] = marks;
}; };
/* TODO: Handle this better. */ /* TODO: Handle this better. */
void SetInstalled(const std::string &unistoreName, const std::string &entry, const std::string &name) { void SetInstalled(const std::string &unistoreName, const std::string &entry, const std::string &name) {
if (this->metadataJson.is_discarded()) return;
const std::vector<std::string> installs = this->GetInstalled(unistoreName, entry); const std::vector<std::string> installs = this->GetInstalled(unistoreName, entry);
bool write = true; bool write = true;
@@ -82,8 +78,6 @@ public:
/* Remove installed state from a download list entry. */ /* Remove installed state from a download list entry. */
void RemoveInstalled(const std::string &unistoreName, const std::string &entry, const std::string &name) { void RemoveInstalled(const std::string &unistoreName, const std::string &entry, const std::string &name) {
if (this->metadataJson.is_discarded()) return;
const std::vector<std::string> installs = this->GetInstalled(unistoreName, entry); const std::vector<std::string> installs = this->GetInstalled(unistoreName, entry);
int idx = -1; int idx = -1;
+21 -6
View File
@@ -59,9 +59,14 @@ static const std::vector<Structs::ButtonPos> mainButtons = {
const std::string &file: The file of the UniStore. const std::string &file: The file of the UniStore.
*/ */
static void DeleteStore(const std::string &file) { static void DeleteStore(const std::string &file) {
nlohmann::json storeJson;
FILE *temp = fopen((std::string(_STORE_PATH) + file).c_str(), "rt"); FILE *temp = fopen((std::string(_STORE_PATH) + file).c_str(), "rt");
nlohmann::json storeJson = nlohmann::json::parse(temp, nullptr, false); if (temp) {
fclose(temp); storeJson = nlohmann::json::parse(temp, nullptr, false);
fclose(temp);
}
if (storeJson.is_discarded())
storeJson = {};
/* Check, if Spritesheet exist on UniStore. */ /* Check, if Spritesheet exist on UniStore. */
if (storeJson["storeInfo"].contains("sheet") && storeJson["storeInfo"]["sheet"].is_array()) { if (storeJson["storeInfo"].contains("sheet") && storeJson["storeInfo"]["sheet"].is_array()) {
@@ -105,9 +110,14 @@ static bool DownloadStore() {
if (URL != "") doSheet = DownloadUniStore(URL, -1, file, true); if (URL != "") doSheet = DownloadUniStore(URL, -1, file, true);
if (doSheet) { if (doSheet) {
nlohmann::json storeJson;
FILE *temp = fopen(file.c_str(), "rt"); FILE *temp = fopen(file.c_str(), "rt");
nlohmann::json storeJson = nlohmann::json::parse(temp, nullptr, false); if (temp) {
fclose(temp); storeJson = nlohmann::json::parse(temp, nullptr, false);
fclose(temp);
}
if (storeJson.is_discarded())
storeJson = { };
if (doSheet) { if (doSheet) {
if (storeJson["storeInfo"].contains("sheetURL") && storeJson["storeInfo"]["sheetURL"].is_array()) { if (storeJson["storeInfo"].contains("sheetURL") && storeJson["storeInfo"]["sheetURL"].is_array()) {
@@ -158,9 +168,14 @@ static bool UpdateStore(const std::string &URL) {
if (URL != "") doSheet = DownloadUniStore(URL, -1, file, false); if (URL != "") doSheet = DownloadUniStore(URL, -1, file, false);
if (doSheet) { if (doSheet) {
nlohmann::json storeJson;
FILE *temp = fopen(file.c_str(), "rt"); FILE *temp = fopen(file.c_str(), "rt");
nlohmann::json storeJson = nlohmann::json::parse(temp, nullptr, false); if (temp) {
fclose(temp); storeJson = nlohmann::json::parse(temp, nullptr, false);
fclose(temp);
}
if (storeJson.is_discarded())
storeJson = { };
if (doSheet) { if (doSheet) {
if (storeJson["storeInfo"].contains("sheetURL") && storeJson["storeInfo"]["sheetURL"].is_array()) { if (storeJson["storeInfo"].contains("sheetURL") && storeJson["storeInfo"]["sheetURL"].is_array()) {
+15 -10
View File
@@ -43,8 +43,12 @@ Meta::Meta() {
} }
FILE *temp = fopen(_META_PATH, "rt"); FILE *temp = fopen(_META_PATH, "rt");
this->metadataJson = nlohmann::json::parse(temp, nullptr, false); if (temp) {
fclose(temp); this->metadataJson = nlohmann::json::parse(temp, nullptr, false);
fclose(temp);
}
if (this->metadataJson.is_discarded())
this->metadataJson = { };
if (config->metadata()) this->ImportMetadata(); if (config->metadata()) this->ImportMetadata();
} }
@@ -59,9 +63,15 @@ void Meta::ImportMetadata() {
} }
Msg::DisplayMsg(Lang::get("FETCHING_METADATA")); Msg::DisplayMsg(Lang::get("FETCHING_METADATA"));
FILE *old = fopen("sdmc:/3ds/Universal-Updater/updates.json", "r");
nlohmann::json oldJson = nlohmann::json::parse(old, nullptr, false); nlohmann::json oldJson;
fclose(old); FILE *old = fopen("sdmc:/3ds/Universal-Updater/updates.json", "rt");
if (old) {
oldJson = nlohmann::json::parse(old, nullptr, false);
fclose(old);
}
if (oldJson.is_discarded())
oldJson = { };
std::vector<UniStoreInfo> info = GetUniStoreInfo(_STORE_PATH); // Fetch UniStores. std::vector<UniStoreInfo> info = GetUniStoreInfo(_STORE_PATH); // Fetch UniStores.
@@ -83,7 +93,6 @@ void Meta::ImportMetadata() {
const std::string &entry: The Entry name. const std::string &entry: The Entry name.
*/ */
std::string Meta::GetUpdated(const std::string &unistoreName, const std::string &entry) const { std::string Meta::GetUpdated(const std::string &unistoreName, const std::string &entry) const {
if (this->metadataJson.is_discarded()) return "";
if (!this->metadataJson.contains(unistoreName)) return ""; // UniStore Name does not exist. if (!this->metadataJson.contains(unistoreName)) return ""; // UniStore Name does not exist.
if (!this->metadataJson[unistoreName].contains(entry)) return ""; // Entry does not exist. if (!this->metadataJson[unistoreName].contains(entry)) return ""; // Entry does not exist.
@@ -103,8 +112,6 @@ std::string Meta::GetUpdated(const std::string &unistoreName, const std::string
int Meta::GetMarks(const std::string &unistoreName, const std::string &entry) const { int Meta::GetMarks(const std::string &unistoreName, const std::string &entry) const {
int temp = 0; int temp = 0;
if (this->metadataJson.is_discarded()) return temp;
if (!this->metadataJson.contains(unistoreName)) return temp; // UniStore Name does not exist. if (!this->metadataJson.contains(unistoreName)) return temp; // UniStore Name does not exist.
if (!this->metadataJson[unistoreName].contains(entry)) return temp; // Entry does not exist. if (!this->metadataJson[unistoreName].contains(entry)) return temp; // Entry does not exist.
@@ -137,8 +144,6 @@ bool Meta::UpdateAvailable(const std::string &unistoreName, const std::string &e
const std::string &entry: The Entry name. const std::string &entry: The Entry name.
*/ */
std::vector<std::string> Meta::GetInstalled(const std::string &unistoreName, const std::string &entry) const { std::vector<std::string> Meta::GetInstalled(const std::string &unistoreName, const std::string &entry) const {
if (this->metadataJson.is_discarded()) return { };
if (!this->metadataJson.contains(unistoreName)) return { }; // UniStore Name does not exist. if (!this->metadataJson.contains(unistoreName)) return { }; // UniStore Name does not exist.
if (!this->metadataJson[unistoreName].contains(entry)) return { }; // Entry does not exist. if (!this->metadataJson[unistoreName].contains(entry)) return { }; // Entry does not exist.
+2
View File
@@ -231,6 +231,8 @@ void Store::LoadFromFile(const std::string &file) {
this->storeJson = nlohmann::json::parse(in, nullptr, false); this->storeJson = nlohmann::json::parse(in, nullptr, false);
fclose(in); fclose(in);
if (this->storeJson.is_discarded())
this->storeJson = { };
/* Check, if valid. */ /* Check, if valid. */
if (this->storeJson.contains("storeInfo") && this->storeJson.contains("storeContent")) { if (this->storeJson.contains("storeInfo") && this->storeJson.contains("storeContent")) {
+7 -9
View File
@@ -110,9 +110,13 @@ Config::Config() {
this->initialize(); this->initialize();
} }
FILE *file = fopen("sdmc:/3ds/Universal-Updater/Config.json", "r"); FILE *file = fopen("sdmc:/3ds/Universal-Updater/Config.json", "rt");
this->json = nlohmann::json::parse(file, nullptr, false); if (file) {
fclose(file); this->json = nlohmann::json::parse(file, nullptr, false);
fclose(file);
}
if (this->json.is_discarded())
this->json = { };
/* Let us create a new one. */ /* Let us create a new one. */
if (!this->json.contains("Version")) this->initialize(); if (!this->json.contains("Version")) this->initialize();
@@ -174,34 +178,28 @@ void Config::save() {
/* Helper functions. */ /* Helper functions. */
bool Config::getBool(const std::string &key) { bool Config::getBool(const std::string &key) {
if (this->json.is_discarded()) return false;
if (!this->json.contains(key)) return false; if (!this->json.contains(key)) return false;
return this->json.at(key).get_ref<const bool &>(); return this->json.at(key).get_ref<const bool &>();
} }
void Config::setBool(const std::string &key, bool v) { void Config::setBool(const std::string &key, bool v) {
if (this->json.is_discarded()) return;
this->json[key] = v; this->json[key] = v;
}; };
int Config::getInt(const std::string &key) { int Config::getInt(const std::string &key) {
if (this->json.is_discarded()) return 0;
if (!this->json.contains(key)) return 0; if (!this->json.contains(key)) return 0;
return this->json.at(key).get_ref<const int64_t &>(); return this->json.at(key).get_ref<const int64_t &>();
} }
void Config::setInt(const std::string &key, int v) { void Config::setInt(const std::string &key, int v) {
if (this->json.is_discarded()) return;
this->json[key] = v; this->json[key] = v;
}; };
std::string Config::getString(const std::string &key) { std::string Config::getString(const std::string &key) {
if (this->json.is_discarded()) return "";
if (!this->json.contains(key)) return ""; if (!this->json.contains(key)) return "";
return this->json.at(key).get_ref<const std::string &>(); return this->json.at(key).get_ref<const std::string &>();
} }
void Config::setString(const std::string &key, const std::string &v) { void Config::setString(const std::string &key, const std::string &v) {
if (this->json.is_discarded()) return;
this->json[key] = v; this->json[key] = v;
}; };
+8 -4
View File
@@ -113,11 +113,15 @@ UniStoreInfo GetInfo(const std::string &file, const std::string &fileName) {
if(*(u32*)(fileName.c_str() + fileName.length() - 4) == (1886349435 & ~(1 << 3))) return Temp; if(*(u32*)(fileName.c_str() + fileName.length() - 4) == (1886349435 & ~(1 << 3))) return Temp;
} }
nlohmann::json JSON = nullptr; nlohmann::json JSON;
FILE *temp = fopen(file.c_str(), "rt");
if(temp) {
JSON = nlohmann::json::parse(temp, nullptr, false);
fclose(temp);
}
if (JSON.is_discarded())
JSON = { };
FILE *temp = fopen(file.c_str(), "r");
JSON = nlohmann::json::parse(temp, nullptr, false);
fclose(temp);
if (!JSON.contains("storeInfo")) return Temp; // storeInfo does not exist. if (!JSON.contains("storeInfo")) return Temp; // storeInfo does not exist.
+12 -4
View File
@@ -42,14 +42,22 @@ void Lang::load(const std::string &lang) {
/* Check if exist. */ /* Check if exist. */
if (access(("romfs:/lang/" + lang + "/app.json").c_str(), F_OK) == 0) { if (access(("romfs:/lang/" + lang + "/app.json").c_str(), F_OK) == 0) {
values = fopen(("romfs:/lang/" + lang + "/app.json").c_str(), "rt"); values = fopen(("romfs:/lang/" + lang + "/app.json").c_str(), "rt");
appJson = nlohmann::json::parse(values, nullptr, false); if (values) {
fclose(values); appJson = nlohmann::json::parse(values, nullptr, false);
fclose(values);
}
if (appJson.is_discarded())
appJson = { };
return; return;
} else { } else {
values = fopen("romfs:/lang/en/app.json", "rt"); values = fopen("romfs:/lang/en/app.json", "rt");
appJson = nlohmann::json::parse(values, nullptr, false); if (values) {
fclose(values); appJson = nlohmann::json::parse(values, nullptr, false);
fclose(values);
}
if (appJson.is_discarded())
appJson = { };
return; return;
} }
} }