2021-01-17 21:15:13 +00:00
|
|
|
// Copyright 2021 Dolphin Emulator Project
|
2021-07-05 01:22:19 +00:00
|
|
|
// SPDX-License-Identifier: GPL-2.0-or-later
|
2021-01-17 21:15:13 +00:00
|
|
|
|
|
|
|
#include <string>
|
|
|
|
|
|
|
|
#include <jni.h>
|
|
|
|
|
|
|
|
#include "jni/AndroidCommon/AndroidCommon.h"
|
2021-01-18 11:22:26 +00:00
|
|
|
#include "jni/AndroidCommon/IDCache.h"
|
2021-01-17 21:15:13 +00:00
|
|
|
|
2022-07-16 10:18:10 +00:00
|
|
|
#include "Common/FatFsUtil.h"
|
2022-01-09 20:51:07 +00:00
|
|
|
#include "Common/ScopeGuard.h"
|
2022-07-16 10:18:10 +00:00
|
|
|
|
2022-01-09 20:57:07 +00:00
|
|
|
#include "Core/CommonTitles.h"
|
2021-01-17 22:16:23 +00:00
|
|
|
#include "Core/HW/WiiSave.h"
|
2022-01-09 20:57:07 +00:00
|
|
|
#include "Core/IOS/ES/ES.h"
|
|
|
|
#include "Core/IOS/IOS.h"
|
2021-01-17 21:15:13 +00:00
|
|
|
#include "Core/WiiUtils.h"
|
2022-07-16 10:18:10 +00:00
|
|
|
|
2021-04-18 13:39:34 +00:00
|
|
|
#include "DiscIO/NANDImporter.h"
|
2021-01-17 21:15:13 +00:00
|
|
|
|
2021-01-17 22:16:23 +00:00
|
|
|
// The hardcoded values here must match WiiUtils.java
|
|
|
|
static jint ConvertCopyResult(WiiSave::CopyResult result)
|
|
|
|
{
|
|
|
|
switch (result)
|
|
|
|
{
|
|
|
|
case WiiSave::CopyResult::Success:
|
|
|
|
return 0;
|
|
|
|
case WiiSave::CopyResult::Error:
|
|
|
|
return 1;
|
|
|
|
case WiiSave::CopyResult::Cancelled:
|
|
|
|
return 2;
|
|
|
|
case WiiSave::CopyResult::CorruptedSource:
|
|
|
|
return 3;
|
|
|
|
case WiiSave::CopyResult::TitleMissing:
|
|
|
|
return 4;
|
|
|
|
default:
|
|
|
|
ASSERT(false);
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
|
|
|
static_assert(static_cast<int>(WiiSave::CopyResult::NumberOfEntries) == 5);
|
|
|
|
}
|
|
|
|
|
2022-01-09 20:50:23 +00:00
|
|
|
static jint ConvertUpdateResult(WiiUtils::UpdateResult result)
|
|
|
|
{
|
|
|
|
switch (result)
|
|
|
|
{
|
|
|
|
case WiiUtils::UpdateResult::Succeeded:
|
|
|
|
return 0;
|
|
|
|
case WiiUtils::UpdateResult::AlreadyUpToDate:
|
|
|
|
return 1;
|
|
|
|
case WiiUtils::UpdateResult::RegionMismatch:
|
|
|
|
return 2;
|
|
|
|
case WiiUtils::UpdateResult::MissingUpdatePartition:
|
|
|
|
return 3;
|
|
|
|
case WiiUtils::UpdateResult::DiscReadFailed:
|
|
|
|
return 4;
|
|
|
|
case WiiUtils::UpdateResult::ServerFailed:
|
|
|
|
return 5;
|
|
|
|
case WiiUtils::UpdateResult::DownloadFailed:
|
|
|
|
return 6;
|
|
|
|
case WiiUtils::UpdateResult::ImportFailed:
|
|
|
|
return 7;
|
|
|
|
case WiiUtils::UpdateResult::Cancelled:
|
|
|
|
return 8;
|
|
|
|
default:
|
|
|
|
ASSERT(false);
|
2022-04-03 09:04:40 +00:00
|
|
|
return 7;
|
2022-01-09 20:50:23 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
static_assert(static_cast<int>(WiiUtils::UpdateResult::NumberOfEntries) == 9);
|
|
|
|
}
|
|
|
|
|
2021-01-17 21:15:13 +00:00
|
|
|
extern "C" {
|
|
|
|
|
|
|
|
JNIEXPORT jboolean JNICALL Java_org_dolphinemu_dolphinemu_utils_WiiUtils_installWAD(JNIEnv* env,
|
|
|
|
jclass,
|
|
|
|
jstring jFile)
|
|
|
|
{
|
|
|
|
const std::string path = GetJString(env, jFile);
|
|
|
|
return static_cast<jboolean>(WiiUtils::InstallWAD(path));
|
|
|
|
}
|
2021-01-17 22:16:23 +00:00
|
|
|
|
2021-01-18 11:22:26 +00:00
|
|
|
JNIEXPORT jint JNICALL Java_org_dolphinemu_dolphinemu_utils_WiiUtils_importWiiSave(
|
|
|
|
JNIEnv* env, jclass, jstring jFile, jobject jCanOverwrite)
|
2021-01-17 22:16:23 +00:00
|
|
|
{
|
|
|
|
const std::string path = GetJString(env, jFile);
|
2021-01-18 11:22:26 +00:00
|
|
|
const auto can_overwrite = [&] {
|
|
|
|
const jmethodID get = IDCache::GetBooleanSupplierGet();
|
|
|
|
return static_cast<bool>(env->CallBooleanMethod(jCanOverwrite, get));
|
|
|
|
};
|
2021-01-17 22:16:23 +00:00
|
|
|
|
|
|
|
return ConvertCopyResult(WiiSave::Import(path, can_overwrite));
|
|
|
|
}
|
2021-04-18 13:39:34 +00:00
|
|
|
|
|
|
|
JNIEXPORT void JNICALL Java_org_dolphinemu_dolphinemu_utils_WiiUtils_importNANDBin(JNIEnv* env,
|
|
|
|
jclass,
|
|
|
|
jstring jFile)
|
|
|
|
{
|
|
|
|
const std::string path = GetJString(env, jFile);
|
|
|
|
|
|
|
|
return DiscIO::NANDImporter().ImportNANDBin(
|
|
|
|
path,
|
|
|
|
[] {
|
|
|
|
// This callback gets called every now and then in case we want to update the GUI. However,
|
|
|
|
// we have no way of knowing what the current progress is, so we can't do anything
|
|
|
|
// especially useful. DolphinQt chooses to show the elapsed time, for reference.
|
|
|
|
},
|
|
|
|
[] {
|
|
|
|
// This callback gets called if the NAND file does not have decryption keys appended to it.
|
|
|
|
// We're supposed to ask the user for a separate file containing keys, but this is probably
|
|
|
|
// more work to implement on Android than it's worth, as this case almost never comes up.
|
|
|
|
PanicAlertFmtT("The decryption keys need to be appended to the NAND backup file.");
|
|
|
|
return "";
|
|
|
|
});
|
|
|
|
}
|
2022-01-09 20:51:07 +00:00
|
|
|
|
|
|
|
JNIEXPORT jint JNICALL Java_org_dolphinemu_dolphinemu_utils_WiiUtils_doOnlineUpdate(
|
|
|
|
JNIEnv* env, jclass, jstring jRegion, jobject jCallback)
|
|
|
|
{
|
|
|
|
const std::string region = GetJString(env, jRegion);
|
|
|
|
|
|
|
|
jobject jCallbackGlobal = env->NewGlobalRef(jCallback);
|
|
|
|
Common::ScopeGuard scope_guard([jCallbackGlobal, env] { env->DeleteGlobalRef(jCallbackGlobal); });
|
|
|
|
|
|
|
|
const auto callback = [&jCallbackGlobal](int processed, int total, u64 title_id) {
|
|
|
|
JNIEnv* env = IDCache::GetEnvForThread();
|
|
|
|
return static_cast<bool>(env->CallBooleanMethod(
|
|
|
|
jCallbackGlobal, IDCache::GetWiiUpdateCallbackFunction(), processed, total, title_id));
|
|
|
|
};
|
|
|
|
|
|
|
|
WiiUtils::UpdateResult result = WiiUtils::DoOnlineUpdate(callback, region);
|
|
|
|
|
|
|
|
return ConvertUpdateResult(result);
|
|
|
|
}
|
2022-01-09 20:57:07 +00:00
|
|
|
|
2022-04-03 09:04:40 +00:00
|
|
|
JNIEXPORT jint JNICALL Java_org_dolphinemu_dolphinemu_utils_WiiUtils_doDiscUpdate(JNIEnv* env,
|
|
|
|
jclass,
|
|
|
|
jstring jPath,
|
|
|
|
jobject jCallback)
|
|
|
|
{
|
|
|
|
const std::string path = GetJString(env, jPath);
|
|
|
|
|
|
|
|
jobject jCallbackGlobal = env->NewGlobalRef(jCallback);
|
|
|
|
Common::ScopeGuard scope_guard([jCallbackGlobal, env] { env->DeleteGlobalRef(jCallbackGlobal); });
|
|
|
|
|
|
|
|
const auto callback = [&jCallbackGlobal](int processed, int total, u64 title_id) {
|
|
|
|
JNIEnv* env = IDCache::GetEnvForThread();
|
|
|
|
return static_cast<bool>(env->CallBooleanMethod(
|
|
|
|
jCallbackGlobal, IDCache::GetWiiUpdateCallbackFunction(), processed, total, title_id));
|
|
|
|
};
|
|
|
|
|
|
|
|
WiiUtils::UpdateResult result = WiiUtils::DoDiscUpdate(callback, path);
|
|
|
|
|
|
|
|
return ConvertUpdateResult(result);
|
|
|
|
}
|
|
|
|
|
2022-01-09 20:57:07 +00:00
|
|
|
JNIEXPORT jboolean JNICALL
|
|
|
|
Java_org_dolphinemu_dolphinemu_utils_WiiUtils_isSystemMenuInstalled(JNIEnv* env, jclass)
|
|
|
|
{
|
|
|
|
IOS::HLE::Kernel ios;
|
2023-05-13 03:01:29 +00:00
|
|
|
const auto tmd = ios.GetESCore().FindInstalledTMD(Titles::SYSTEM_MENU);
|
2022-01-09 20:57:07 +00:00
|
|
|
|
|
|
|
return tmd.IsValid();
|
|
|
|
}
|
2022-01-09 20:58:45 +00:00
|
|
|
|
2022-10-21 21:22:49 +00:00
|
|
|
JNIEXPORT jboolean JNICALL
|
|
|
|
Java_org_dolphinemu_dolphinemu_utils_WiiUtils_isSystemMenuvWii(JNIEnv* env, jclass)
|
|
|
|
{
|
|
|
|
IOS::HLE::Kernel ios;
|
2023-05-13 03:01:29 +00:00
|
|
|
const auto tmd = ios.GetESCore().FindInstalledTMD(Titles::SYSTEM_MENU);
|
2022-10-21 21:22:49 +00:00
|
|
|
|
|
|
|
return tmd.IsvWii();
|
|
|
|
}
|
|
|
|
|
2022-01-09 20:58:45 +00:00
|
|
|
JNIEXPORT jstring JNICALL
|
|
|
|
Java_org_dolphinemu_dolphinemu_utils_WiiUtils_getSystemMenuVersion(JNIEnv* env, jclass)
|
|
|
|
{
|
|
|
|
IOS::HLE::Kernel ios;
|
2023-05-13 03:01:29 +00:00
|
|
|
const auto tmd = ios.GetESCore().FindInstalledTMD(Titles::SYSTEM_MENU);
|
2022-01-09 20:58:45 +00:00
|
|
|
|
|
|
|
if (!tmd.IsValid())
|
|
|
|
{
|
|
|
|
return ToJString(env, "");
|
|
|
|
}
|
|
|
|
|
2022-10-21 21:22:49 +00:00
|
|
|
return ToJString(env, DiscIO::GetSysMenuVersionString(tmd.GetTitleVersion(), tmd.IsvWii()));
|
2022-01-09 20:58:45 +00:00
|
|
|
}
|
2022-07-16 10:18:10 +00:00
|
|
|
|
|
|
|
JNIEXPORT jboolean JNICALL
|
|
|
|
Java_org_dolphinemu_dolphinemu_utils_WiiUtils_syncSdFolderToSdImage(JNIEnv* env, jclass)
|
|
|
|
{
|
2023-02-26 19:18:37 +00:00
|
|
|
return static_cast<jboolean>(Common::SyncSDFolderToSDImage([]() { return false; }, false));
|
2022-07-16 10:18:10 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
JNIEXPORT jboolean JNICALL
|
|
|
|
Java_org_dolphinemu_dolphinemu_utils_WiiUtils_syncSdImageToSdFolder(JNIEnv* env, jclass)
|
|
|
|
{
|
2023-02-26 19:18:37 +00:00
|
|
|
return static_cast<jboolean>(Common::SyncSDImageToSDFolder([]() { return false; }));
|
2022-07-16 10:18:10 +00:00
|
|
|
}
|
2021-01-17 21:15:13 +00:00
|
|
|
}
|