From 3f780fdd69cbb59fb0ce9519faa467df9e8600f2 Mon Sep 17 00:00:00 2001 From: Gericom Date: Sun, 29 Mar 2026 11:47:08 +0200 Subject: [PATCH] Improve error handling for parsing banners. Fixes #18 --- .../FileType/Nds/NdsInternalFileInfo.cpp | 68 +++++++++++-------- .../FileType/Nds/NdsInternalFileInfo.h | 11 +-- 2 files changed, 40 insertions(+), 39 deletions(-) diff --git a/arm9/source/romBrowser/FileType/Nds/NdsInternalFileInfo.cpp b/arm9/source/romBrowser/FileType/Nds/NdsInternalFileInfo.cpp index c1a14c3..54c01a4 100644 --- a/arm9/source/romBrowser/FileType/Nds/NdsInternalFileInfo.cpp +++ b/arm9/source/romBrowser/FileType/Nds/NdsInternalFileInfo.cpp @@ -2,52 +2,60 @@ #include #include #include "fat/File.h" -#include "romBrowser/ICoverRepository.h" #include "NdsInternalFileInfo.h" NdsInternalFileInfo::NdsInternalFileInfo(const FastFileRef& fastFileRef) { const auto file = std::make_unique(); - _hasBanner = false; memset(_gameCode, 0, sizeof(_gameCode)); file->Open(fastFileRef, FA_READ); - if (file->Seek(0xC) != FR_OK) - return; - - u32 bytesRead; - if (file->Read(_gameCode, 4, bytesRead) != FR_OK) - return; - - if (file->Seek(0x68) != FR_OK) - return; - u32 bannerOffset; - if (file->Read(&bannerOffset, 4, bytesRead) != FR_OK) - return; - - if (bannerOffset == 0) - return; - - if (file->Seek(bannerOffset) != FR_OK) - return; - - if (file->Read(&_banner, 0xA00, bytesRead) != FR_OK) - return; - - if (_banner.header.version >= NDS_BANNER_VERSION_103) + if (file->Seek(0xC) != FR_OK || + !file->ReadExact(_gameCode, 4) || + file->Seek(0x68) != FR_OK || + !file->ReadExact(&bannerOffset, 4) || + bannerOffset == 0 || + bannerOffset >= file->GetSize() || + file->Seek(bannerOffset) != FR_OK || + !file->ReadExact(&_banner, 0x840)) { - if (file->Read(((u8*)&_banner) + 0xA00, 0x19C0, bytesRead) != FR_OK) - return; + return; } + + if (_banner.header.version >= NDS_BANNER_VERSION_2 && + !file->ReadExact(((u8*)&_banner) + 0x840, 0x100)) + { + return; + } + + if (_banner.header.version >= NDS_BANNER_VERSION_3 && + !file->ReadExact(((u8*)&_banner) + 0x940, 0x100)) + { + return; + } + + if (_banner.header.version >= NDS_BANNER_VERSION_103 && + !file->ReadExact(((u8*)&_banner) + 0xA40, 0x1980)) + { + return; + } + _hasBanner = true; DC_FlushRange(&_banner, sizeof(_banner)); } const char16_t* NdsInternalFileInfo::GetGameTitle() const { - if (!_hasBanner) - return nullptr; - return _banner.title[NDS_BANNER_TITLE_LANGUAGE_ENGLISH]; + return _hasBanner + ? _banner.title[NDS_BANNER_TITLE_LANGUAGE_ENGLISH] + : nullptr; +} + +std::unique_ptr NdsInternalFileInfo::CreateGameIcon() const +{ + return _hasBanner + ? std::make_unique(&_banner) + : nullptr; } diff --git a/arm9/source/romBrowser/FileType/Nds/NdsInternalFileInfo.h b/arm9/source/romBrowser/FileType/Nds/NdsInternalFileInfo.h index 0c7571e..736870a 100644 --- a/arm9/source/romBrowser/FileType/Nds/NdsInternalFileInfo.h +++ b/arm9/source/romBrowser/FileType/Nds/NdsInternalFileInfo.h @@ -12,18 +12,11 @@ public: constexpr const char* GetGameCode() const override { return _gameCode; } const char16_t* GetGameTitle() const override; - - std::unique_ptr CreateGameIcon() const override - { - if (!_hasBanner) - return nullptr; - return std::make_unique(&_banner); - } - + std::unique_ptr CreateGameIcon() const override; const nds_banner_t& GetBanner() const { return _banner; } private: nds_banner_t _banner alignas(32); - bool _hasBanner; + bool _hasBanner = false; char _gameCode[5]; }; \ No newline at end of file