mirror of
https://github.com/TwilitRealm/dusklight
synced 2026-08-20 13:24:40 -04:00
27d27e6d94
* Add offsets for Wii USA R0/R2, JPN, and PAL Also fix an oopsie where l_pos and l_normal's offsets were swapped * Allow loading Wii discs * Change GameVersion::GcnJpn checks to isRegionJpn() * Change GameVersion::GcnPal checks to isRegionPal() * Add platformSelect and regionSelect templates, simplify a ton of code * Add *_get() macros to simplify REL loads * Actually accept Wii USA Rev. 2 discs * Show the Wii USA revision in prelaunch's disc status * l_normal isn't in Wii RELs, so I'll just hardcode it * Account for various BLO differences Fix crash when opening the map on Wii USA Rev 0 and Wii PAL * Use the streamed version of the file select music * Update language selection * Fix the d-pad/cross button text for Wii PAL Resizing panes that are already 120.0f wide is harmless, so I didn't bother with a GameVersion check * Fix brightness check discrepancy, use IF_DUSK_BLOCK macros when ideal * Update docs and the issue template
141 lines
4.3 KiB
C++
141 lines
4.3 KiB
C++
#include "iso_validate.hpp"
|
|
|
|
#include <borealis/disc.hpp>
|
|
|
|
#include <array>
|
|
#include <string_view>
|
|
|
|
#include "dusk/logging.h"
|
|
#include "dusk/settings.h"
|
|
|
|
namespace {
|
|
|
|
const char* verification_state_name(dusk::DiscVerificationState state) noexcept {
|
|
switch (state) {
|
|
case dusk::DiscVerificationState::Success:
|
|
return "verified";
|
|
case dusk::DiscVerificationState::HashMismatch:
|
|
return "hash mismatch";
|
|
case dusk::DiscVerificationState::Unknown:
|
|
default:
|
|
return "unknown";
|
|
}
|
|
}
|
|
|
|
} // namespace
|
|
|
|
namespace dusk::iso {
|
|
namespace {
|
|
|
|
constexpr auto AcceptedDiscs = std::to_array<borealis::disc::AcceptedDisc>({
|
|
{
|
|
.gameId = "GZ2E01",
|
|
.expectedHash = borealis::disc::parse_xxh3_128("14e886f08e548a000afde98a3195e788"),
|
|
},
|
|
{
|
|
.gameId = "GZ2J01",
|
|
.expectedHash = borealis::disc::parse_xxh3_128("5967dc7a6a553652f4d2050aeef6f368"),
|
|
},
|
|
{
|
|
.gameId = "GZ2P01",
|
|
.expectedHash = borealis::disc::parse_xxh3_128("9ef597588b0035ca9e91b333fa9a8a7e"),
|
|
},
|
|
{
|
|
.gameId = "RZDE01", .revision = 0,
|
|
.expectedHash = borealis::disc::parse_xxh3_128("b3d91fbea59e5c66934d04c01566728e"),
|
|
},
|
|
{
|
|
.gameId = "RZDE01", .revision = 2,
|
|
.expectedHash = borealis::disc::parse_xxh3_128("c3ec420921a1b36d6ae43f576491d25c"),
|
|
},
|
|
{
|
|
.gameId = "RZDJ01",
|
|
.expectedHash = borealis::disc::parse_xxh3_128("d3866821c7fc6999e6e8bbef8b6875aa"),
|
|
},
|
|
{
|
|
.gameId = "RZDP01",
|
|
.expectedHash = borealis::disc::parse_xxh3_128("6095a924a57e5fb4294ac96fb85a09a1"),
|
|
},
|
|
});
|
|
|
|
constexpr auto RecognizedGameIds = std::to_array<std::string_view>({"RZDK01"});
|
|
|
|
constexpr borealis::disc::Catalog DiscCatalog{
|
|
.acceptedDiscs = AcceptedDiscs,
|
|
.recognizedGameIds = RecognizedGameIds,
|
|
};
|
|
|
|
ValidationError validation_error(borealis::disc::Status status) noexcept {
|
|
switch (status) {
|
|
case borealis::disc::Status::Success:
|
|
return ValidationError::Success;
|
|
case borealis::disc::Status::IOError:
|
|
return ValidationError::IOError;
|
|
case borealis::disc::Status::InvalidImage:
|
|
return ValidationError::InvalidImage;
|
|
case borealis::disc::Status::UnknownGame:
|
|
return ValidationError::WrongGame;
|
|
case borealis::disc::Status::UnsupportedVersion:
|
|
return ValidationError::WrongVersion;
|
|
case borealis::disc::Status::Canceled:
|
|
return ValidationError::Canceled;
|
|
case borealis::disc::Status::HashMismatch:
|
|
return ValidationError::HashMismatch;
|
|
case borealis::disc::Status::Failed:
|
|
default:
|
|
return ValidationError::Unknown;
|
|
}
|
|
}
|
|
|
|
Region region_from_game_id(std::string_view gameId) noexcept {
|
|
if (gameId.size() >= 4) {
|
|
switch (gameId[3]) {
|
|
case 'P':
|
|
return Region::Europe;
|
|
case 'J':
|
|
return Region::Japan;
|
|
case 'K':
|
|
return Region::Korea;
|
|
default:
|
|
break;
|
|
}
|
|
}
|
|
return Region::NorthAmerica;
|
|
}
|
|
|
|
void update_info(const borealis::disc::Result& result, DiscInfo& info) noexcept {
|
|
if (!result.metadata.gameId.empty()) {
|
|
info.platform = result.metadata.platform;
|
|
info.region = region_from_game_id(result.metadata.gameId);
|
|
info.revision = result.metadata.revision;
|
|
}
|
|
}
|
|
|
|
} // namespace
|
|
|
|
ValidationError validate(const char* path, VerificationStatus& status, DiscInfo& info) {
|
|
const auto result = borealis::disc::verify(
|
|
path == nullptr ? std::string_view{} : std::string_view{path}, DiscCatalog, &status);
|
|
update_info(result, info);
|
|
return validation_error(result.status);
|
|
}
|
|
|
|
ValidationError inspect(const char* path, DiscInfo& info) {
|
|
const auto result = borealis::disc::inspect(
|
|
path == nullptr ? std::string_view{} : std::string_view{path}, DiscCatalog);
|
|
update_info(result, info);
|
|
return validation_error(result.status);
|
|
}
|
|
|
|
bool isPal(const char* path) {
|
|
DiscInfo info{};
|
|
return inspect(path, info) == ValidationError::Success && info.region == Region::Europe;
|
|
}
|
|
|
|
void log_verification_state(std::string_view path, DiscVerificationState state) {
|
|
const std::string pathText = path.empty() ? "<none>" : std::string(path);
|
|
DuskLog.info(
|
|
"Disc verification status: {} (path: {})", verification_state_name(state), pathText);
|
|
}
|
|
} // namespace dusk::iso
|