Merge pull request #357 from OFFTKP/master

Clean up smdh getting
This commit is contained in:
Paris Oplopoios 2023-12-28 00:30:48 +02:00 committed by GitHub
commit e536f5d635
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
9 changed files with 45 additions and 52 deletions

View file

@ -389,7 +389,6 @@ if(ENABLE_VULKAN)
endif() endif()
if(ANDROID) if(ANDROID)
set(HEADER_FILES ${HEADER_FILES} include/jni_driver.hpp)
set(ALL_SOURCES ${ALL_SOURCES} src/jni_driver.cpp) set(ALL_SOURCES ${ALL_SOURCES} src/jni_driver.cpp)
endif() endif()

View file

@ -3,6 +3,7 @@
#include <filesystem> #include <filesystem>
#include <fstream> #include <fstream>
#include <optional> #include <optional>
#include <span>
#include "PICA/gpu.hpp" #include "PICA/gpu.hpp"
#include "cheats.hpp" #include "cheats.hpp"
@ -127,4 +128,6 @@ class Emulator {
std::filesystem::path getConfigPath(); std::filesystem::path getConfigPath();
std::filesystem::path getAndroidAppPath(); std::filesystem::path getAndroidAppPath();
std::span<u8> getSMDH();
}; };

View file

@ -1,8 +0,0 @@
#include <vector>
#include "helpers.hpp"
class Pandroid {
public:
static void onSmdhLoaded(const std::vector<u8>& smdh);
};

View file

@ -65,6 +65,7 @@ struct NCCH {
std::vector<u8> saveData; std::vector<u8> saveData;
// The cart region. Only the CXI's region matters to us. Necessary to get past region locking // The cart region. Only the CXI's region matters to us. Necessary to get past region locking
std::optional<Regions> region = std::nullopt; std::optional<Regions> region = std::nullopt;
std::vector<u8> smdh;
// Returns true on success, false on failure // Returns true on success, false on failure
// Partition index/offset/size must have been set before this // Partition index/offset/size must have been set before this

View file

@ -6,10 +6,6 @@
#include "loader/ncch.hpp" #include "loader/ncch.hpp"
#include "memory.hpp" #include "memory.hpp"
#ifdef __ANDROID__
#include "jni_driver.hpp"
#endif
#include <iostream> #include <iostream>
bool NCCH::loadFromHeader(Crypto::AESEngine &aesEngine, IOFile& file, const FSInfo &info) { bool NCCH::loadFromHeader(Crypto::AESEngine &aesEngine, IOFile& file, const FSInfo &info) {
@ -30,6 +26,7 @@ bool NCCH::loadFromHeader(Crypto::AESEngine &aesEngine, IOFile& file, const FSIn
codeFile.clear(); codeFile.clear();
saveData.clear(); saveData.clear();
smdh.clear();
partitionInfo = info; partitionInfo = info;
size = u64(*(u32*)&header[0x104]) * mediaUnit; // TODO: Maybe don't type pun because big endian will break size = u64(*(u32*)&header[0x104]) * mediaUnit; // TODO: Maybe don't type pun because big endian will break
@ -223,11 +220,10 @@ bool NCCH::loadFromHeader(Crypto::AESEngine &aesEngine, IOFile& file, const FSIn
} }
} else if (std::strcmp(name, "icon") == 0) { } else if (std::strcmp(name, "icon") == 0) {
// Parse icon file to extract region info and more in the future (logo, etc) // Parse icon file to extract region info and more in the future (logo, etc)
std::vector<u8> tmp; smdh.resize(fileSize);
tmp.resize(fileSize); readFromFile(file, exeFS, smdh.data(), fileOffset + exeFSHeaderSize, fileSize);
readFromFile(file, exeFS, tmp.data(), fileOffset + exeFSHeaderSize, fileSize);
if (!parseSMDH(tmp)) { if (!parseSMDH(smdh)) {
printf("Failed to parse SMDH!\n"); printf("Failed to parse SMDH!\n");
} }
} }
@ -259,11 +255,6 @@ bool NCCH::parseSMDH(const std::vector<u8>& smdh) {
return false; return false;
} }
// In the Android version, notify the application that we're loading an SMDH file, to extract data for the title list
#ifdef __ANDROID__
Pandroid::onSmdhLoaded(smdh);
#endif
// Bitmask showing which regions are allowed. // Bitmask showing which regions are allowed.
// https://www.3dbrew.org/wiki/SMDH#Region_Lockout // https://www.3dbrew.org/wiki/SMDH#Region_Lockout
const u32 regionMasks = *(u32*)&smdh[0x2018]; const u32 regionMasks = *(u32*)&smdh[0x2018];

View file

@ -252,6 +252,17 @@ bool Emulator::loadELF(std::ifstream& file) {
return true; return true;
} }
std::span<u8> Emulator::getSMDH() {
switch (romType) {
case ROMType::NCSD:
case ROMType::CXI:
return memory.getCXI()->smdh;
default: {
return std::span<u8>();
}
}
}
#ifdef PANDA3DS_ENABLE_DISCORD_RPC #ifdef PANDA3DS_ENABLE_DISCORD_RPC
void Emulator::updateDiscord() { void Emulator::updateDiscord() {
if (config.discordRpcEnabled) { if (config.discordRpcEnabled) {

View file

@ -1,5 +1,3 @@
#include "jni_driver.hpp"
#include <EGL/egl.h> #include <EGL/egl.h>
#include <android/log.h> #include <android/log.h>
#include <jni.h> #include <jni.h>
@ -15,7 +13,6 @@ HIDService* hidService = nullptr;
RendererGL* renderer = nullptr; RendererGL* renderer = nullptr;
bool romLoaded = false; bool romLoaded = false;
JavaVM* jvm = nullptr; JavaVM* jvm = nullptr;
const char* alberClass = "com/panda3ds/pandroid/AlberDriver";
#define AlberFunction(type, name) JNIEXPORT type JNICALL Java_com_panda3ds_pandroid_AlberDriver_##name #define AlberFunction(type, name) JNIEXPORT type JNICALL Java_com_panda3ds_pandroid_AlberDriver_##name
@ -36,20 +33,6 @@ JNIEnv* jniEnv() {
return env; return env;
} }
void Pandroid::onSmdhLoaded(const std::vector<u8>& smdh) {
JNIEnv* env = jniEnv();
int size = smdh.size();
jbyteArray result = env->NewByteArray(size);
env->SetByteArrayRegion(result, 0, size, (jbyte*)smdh.data());
auto classLoader = env->FindClass(alberClass);
auto method = env->GetStaticMethodID(classLoader, "OnSmdhLoaded", "([B)V");
env->CallStaticVoidMethod(classLoader, method, result);
env->DeleteLocalRef(result);
}
extern "C" { extern "C" {
AlberFunction(void, Setup)(JNIEnv* env, jobject obj) { env->GetJavaVM(&jvm); } AlberFunction(void, Setup)(JNIEnv* env, jobject obj) { env->GetJavaVM(&jvm); }
@ -104,6 +87,15 @@ AlberFunction(void, SetCirclepadAxis)(JNIEnv* env, jobject obj, jint x, jint y)
hidService->setCirclepadX((s16)x); hidService->setCirclepadX((s16)x);
hidService->setCirclepadY((s16)y); hidService->setCirclepadY((s16)y);
} }
AlberFunction(jbyteArray, GetSmdh)(JNIEnv* env, jobject obj) {
std::span<u8> smdh = emulator->getSMDH();
jbyteArray result = env->NewByteArray(smdh.size());
env->SetByteArrayRegion(result, 0, smdh.size(), (jbyte*)smdh.data());
return result;
}
} }
#undef AlberFunction #undef AlberFunction

View file

@ -2,11 +2,6 @@ package com.panda3ds.pandroid;
import android.util.Log; import android.util.Log;
import com.panda3ds.pandroid.data.SMDH;
import com.panda3ds.pandroid.data.game.GameMetadata;
import com.panda3ds.pandroid.utils.Constants;
import com.panda3ds.pandroid.utils.GameUtils;
public class AlberDriver { public class AlberDriver {
AlberDriver() { super(); } AlberDriver() { super(); }
@ -23,14 +18,7 @@ public class AlberDriver {
public static native void TouchScreenUp(); public static native void TouchScreenUp();
public static native void TouchScreenDown(int x, int y); public static native void TouchScreenDown(int x, int y);
public static void OnSmdhLoaded(byte[] buffer) { public static native byte[] GetSmdh();
SMDH smdh = new SMDH(buffer);
Log.i(Constants.LOG_TAG, "Loaded rom SDMH");
Log.i(Constants.LOG_TAG, String.format("Are you playing '%s' published by '%s'", smdh.getTitle(), smdh.getPublisher()));
GameMetadata game = GameUtils.getCurrentGame();
GameUtils.removeGame(game);
GameUtils.addGame(GameMetadata.applySMDH(game, smdh));
}
static { System.loadLibrary("Alber"); } static { System.loadLibrary("Alber"); }
} }

View file

@ -8,9 +8,12 @@ import android.opengl.GLSurfaceView;
import android.util.Log; import android.util.Log;
import com.panda3ds.pandroid.AlberDriver; import com.panda3ds.pandroid.AlberDriver;
import com.panda3ds.pandroid.utils.Constants; import com.panda3ds.pandroid.utils.Constants;
import com.panda3ds.pandroid.utils.GameUtils;
import com.panda3ds.pandroid.view.renderer.ConsoleRenderer; import com.panda3ds.pandroid.view.renderer.ConsoleRenderer;
import com.panda3ds.pandroid.view.renderer.layout.ConsoleLayout; import com.panda3ds.pandroid.view.renderer.layout.ConsoleLayout;
import com.panda3ds.pandroid.view.renderer.layout.DefaultScreenLayout; import com.panda3ds.pandroid.view.renderer.layout.DefaultScreenLayout;
import com.panda3ds.pandroid.data.SMDH;
import com.panda3ds.pandroid.data.game.GameMetadata;
import javax.microedition.khronos.egl.EGLConfig; import javax.microedition.khronos.egl.EGLConfig;
import javax.microedition.khronos.opengles.GL10; import javax.microedition.khronos.opengles.GL10;
@ -76,6 +79,19 @@ public class PandaGlRenderer implements GLSurfaceView.Renderer, ConsoleRenderer
AlberDriver.Initialize(); AlberDriver.Initialize();
AlberDriver.LoadRom(romPath); AlberDriver.LoadRom(romPath);
// Load the SMDH
byte[] smdhData = AlberDriver.GetSmdh();
if (smdhData.length == 0) {
Log.w(Constants.LOG_TAG, "Failed to load SMDH");
} else {
SMDH smdh = new SMDH(smdhData);
Log.i(Constants.LOG_TAG, "Loaded rom SDMH");
Log.i(Constants.LOG_TAG, String.format("Are you playing '%s' published by '%s'", smdh.getTitle(), smdh.getPublisher()));
GameMetadata game = GameUtils.getCurrentGame();
GameUtils.removeGame(game);
GameUtils.addGame(GameMetadata.applySMDH(game, smdh));
}
} }
public void onDrawFrame(GL10 unused) { public void onDrawFrame(GL10 unused) {