feat: Add applet patches and update tooling/compile instructions
This commit is contained in:
parent
58357a59ee
commit
11cde803ff
10 changed files with 162 additions and 52 deletions
6
.github/workflows/ci.yml
vendored
6
.github/workflows/ci.yml
vendored
|
|
@ -6,13 +6,13 @@ jobs:
|
||||||
build-wups:
|
build-wups:
|
||||||
runs-on: ubuntu-22.04
|
runs-on: ubuntu-22.04
|
||||||
steps:
|
steps:
|
||||||
- uses: actions/checkout@v2
|
- uses: actions/checkout@v4
|
||||||
- name: build toolchain container
|
- name: build toolchain container
|
||||||
run: docker build . -t builder
|
run: docker build . -t builder
|
||||||
- uses: ammaraskar/gcc-problem-matcher@master
|
- uses: ammaraskar/gcc-problem-matcher@master
|
||||||
- name: build WUPS plugin
|
- name: build WUPS plugin
|
||||||
run: docker run --rm -v ${PWD}:/app -w /app builder
|
run: docker run --rm -v ${PWD}:/app -w /app builder
|
||||||
- uses: actions/upload-artifact@master
|
- uses: actions/upload-artifact@v4
|
||||||
with:
|
with:
|
||||||
name: plugin
|
name: meowth
|
||||||
path: "*.wps"
|
path: "*.wps"
|
||||||
|
|
|
||||||
|
|
@ -1,8 +1,8 @@
|
||||||
FROM wiiuenv/devkitppc:20220806
|
FROM ghcr.io/wiiu-env/devkitppc:20241128
|
||||||
|
|
||||||
COPY --from=wiiuenv/libkernel:20220724 /artifacts $DEVKITPRO
|
COPY --from=ghcr.io/wiiu-env/libkernel:20230621 /artifacts $DEVKITPRO
|
||||||
COPY --from=wiiuenv/libmocha:20220903 /artifacts $DEVKITPRO
|
COPY --from=ghcr.io/wiiu-env/libmocha:20240603 /artifacts $DEVKITPRO
|
||||||
COPY --from=wiiuenv/wiiupluginsystem:20220826 /artifacts $DEVKITPRO
|
COPY --from=ghcr.io/wiiu-env/wiiupluginsystem:20240505 /artifacts $DEVKITPRO
|
||||||
|
|
||||||
WORKDIR /app
|
WORKDIR /app
|
||||||
CMD make -f Makefile -j$(nproc)
|
CMD make -f Makefile -j$(nproc)
|
||||||
|
|
|
||||||
15
Makefile
15
Makefile
|
|
@ -28,11 +28,15 @@ INCLUDES := src
|
||||||
#-------------------------------------------------------------------------------
|
#-------------------------------------------------------------------------------
|
||||||
# options for code generation
|
# options for code generation
|
||||||
#-------------------------------------------------------------------------------
|
#-------------------------------------------------------------------------------
|
||||||
CFLAGS := -g -Wall -O2 -ffunction-sections \
|
CFLAGS := -Wall -O2 -ffunction-sections -fdata-sections \
|
||||||
$(MACHDEP)
|
$(MACHDEP)
|
||||||
|
|
||||||
CFLAGS += $(INCLUDE) -D__WIIU__ -D__WUT__ -D__WUPS__
|
CFLAGS += $(INCLUDE) -D__WIIU__ -D__WUT__ -D__WUPS__
|
||||||
|
|
||||||
|
ifeq ($(DEBUG),1)
|
||||||
|
CFLAGS += -DDEBUG -g
|
||||||
|
endif
|
||||||
|
|
||||||
CXXFLAGS := $(CFLAGS) -std=c++20
|
CXXFLAGS := $(CFLAGS) -std=c++20
|
||||||
|
|
||||||
ASFLAGS := -g $(ARCH)
|
ASFLAGS := -g $(ARCH)
|
||||||
|
|
@ -105,7 +109,7 @@ $(BUILD):
|
||||||
#-------------------------------------------------------------------------------
|
#-------------------------------------------------------------------------------
|
||||||
clean:
|
clean:
|
||||||
@echo clean ...
|
@echo clean ...
|
||||||
@rm -fr $(BUILD)/* $(TARGET).wps $(TARGET).elf
|
@rm -fr $(BUILD) $(TARGET).wps $(TARGET).elf
|
||||||
|
|
||||||
#-------------------------------------------------------------------------------
|
#-------------------------------------------------------------------------------
|
||||||
else
|
else
|
||||||
|
|
@ -131,8 +135,13 @@ $(OFILES_SRC) : $(HFILES_BIN)
|
||||||
@echo $(notdir $<)
|
@echo $(notdir $<)
|
||||||
@$(bin2o)
|
@$(bin2o)
|
||||||
|
|
||||||
|
%.pem.o %_pem.h : %.pem
|
||||||
|
#-------------------------------------------------------------------------------
|
||||||
|
@echo $(notdir $<)
|
||||||
|
@$(bin2o)
|
||||||
|
|
||||||
-include $(DEPENDS)
|
-include $(DEPENDS)
|
||||||
|
|
||||||
#-------------------------------------------------------------------------------
|
#-------------------------------------------------------------------------------
|
||||||
endif
|
endif
|
||||||
#-------------------------------------------------------------------------------
|
#-------------------------------------------------------------------------------
|
||||||
20
README.md
20
README.md
|
|
@ -2,6 +2,24 @@
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
Since NSSL is such hot garbage, a lot of games shipped their own static version of OpenSSL. Meowth is here to disable the SSL verification in such titles.
|
Since NSSL is such hot garbage, a lot of games shipped their own static version of OpenSSL.
|
||||||
|
Meowth disables the SSL verification in such titles for development purposes.
|
||||||
|
|
||||||
Based on [Inkay](https://github.com/PretendoNetwork/Inkay).
|
Based on [Inkay](https://github.com/PretendoNetwork/Inkay).
|
||||||
|
|
||||||
|
## Compiling - Docker
|
||||||
|
Meowth's dependencies and build tooling can be handled as a container, which is generally recommended for WUPS
|
||||||
|
development.
|
||||||
|
Using `docker` or `podman`:
|
||||||
|
```shell
|
||||||
|
docker build -t meowth .
|
||||||
|
docker run --rm -v $(pwd):/app meowth make # replace "make" with any other command (make clean, etc.)
|
||||||
|
```
|
||||||
|
|
||||||
|
## Compiling - System
|
||||||
|
Meowth has the following dependencies:
|
||||||
|
- [WiiUPluginSystem](https://github.com/wiiu-env/WiiUPluginSystem)
|
||||||
|
- [libmocha](https://github.com/wiiu-env/libmocha)
|
||||||
|
- [libkernel](https://github.com/wiiu-env/libkernel/)
|
||||||
|
|
||||||
|
Each of these should be `make install`-able, and then Meowth can be compiled with `make`.
|
||||||
56
src/main.cpp
56
src/main.cpp
|
|
@ -16,16 +16,7 @@
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <wups.h>
|
#include <wups.h>
|
||||||
#include <nsysnet/nssl.h>
|
|
||||||
#include <coreinit/cache.h>
|
|
||||||
#include <coreinit/dynload.h>
|
|
||||||
#include <coreinit/mcp.h>
|
#include <coreinit/mcp.h>
|
||||||
#include <coreinit/memory.h>
|
|
||||||
#include <coreinit/memorymap.h>
|
|
||||||
#include <coreinit/memexpheap.h>
|
|
||||||
#include <coreinit/launch.h>
|
|
||||||
#include <sysapp/launch.h>
|
|
||||||
#include "wut_extra.h"
|
|
||||||
#include <utils/logger.h>
|
#include <utils/logger.h>
|
||||||
#include "patcher/ingame.h"
|
#include "patcher/ingame.h"
|
||||||
|
|
||||||
|
|
@ -42,7 +33,7 @@ WUPS_PLUGIN_LICENSE("ISC");
|
||||||
#include <kernel/kernel.h>
|
#include <kernel/kernel.h>
|
||||||
#include <mocha/mocha.h>
|
#include <mocha/mocha.h>
|
||||||
|
|
||||||
static bool is555(MCP_SystemVersion version) {
|
static bool is555(MCPSystemVersion version) {
|
||||||
return (version.major == 5) && (version.minor == 5) && (version.patch >= 5);
|
return (version.major == 5) && (version.minor == 5) && (version.patch >= 5);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -58,12 +49,12 @@ INITIALIZE_PLUGIN() {
|
||||||
}
|
}
|
||||||
|
|
||||||
//get os version
|
//get os version
|
||||||
MCP_SystemVersion os_version;
|
MCPSystemVersion os_version;
|
||||||
int mcp = MCP_Open();
|
int mcp = MCP_Open();
|
||||||
int ret = MCP_GetSystemVersion(mcp, &os_version);
|
int ret = MCP_GetSystemVersion(mcp, &os_version);
|
||||||
if (ret < 0) {
|
if (ret < 0) {
|
||||||
DEBUG_FUNCTION_LINE("getting system version failed (%d/%d)!", mcp, ret);
|
DEBUG_FUNCTION_LINE("getting system version failed (%d/%d)!", mcp, ret);
|
||||||
os_version = (MCP_SystemVersion) {
|
os_version = (MCPSystemVersion) {
|
||||||
.major = 5, .minor = 5, .patch = 5, .region = 'E'
|
.major = 5, .minor = 5, .patch = 5, .region = 'E'
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
@ -91,4 +82,43 @@ ON_APPLICATION_START() {
|
||||||
RunPatcher();
|
RunPatcher();
|
||||||
}
|
}
|
||||||
|
|
||||||
ON_APPLICATION_ENDS() {}
|
// Try to hook the webkit applets fairly early - wish there was a better way to do this...
|
||||||
|
|
||||||
|
DECL_FUNCTION(int, FSOpenFile_miiverse, FSClient *client, FSCmdBlock *block, const char *path, const char *mode, uint32_t *handle, int errorMask) {
|
||||||
|
const char *oma = "vol/content/preload.oma";
|
||||||
|
|
||||||
|
if (strcmp(oma, path) == 0)
|
||||||
|
{
|
||||||
|
WHBLogUdpInit();
|
||||||
|
RunPatcher();
|
||||||
|
}
|
||||||
|
|
||||||
|
return real_FSOpenFile_miiverse(client, block, path, mode, handle, errorMask);
|
||||||
|
}
|
||||||
|
WUPS_MUST_REPLACE_FOR_PROCESS(FSOpenFile_miiverse, WUPS_LOADER_LIBRARY_COREINIT, FSOpenFile, WUPS_FP_TARGET_PROCESS_MIIVERSE);
|
||||||
|
|
||||||
|
DECL_FUNCTION(int, FSOpenFile_tvii, FSClient *client, FSCmdBlock *block, const char *path, const char *mode, uint32_t *handle, int errorMask) {
|
||||||
|
const char *oma = "/vol/content/skin/Skin.dat";
|
||||||
|
|
||||||
|
if (strcmp(oma, path) == 0)
|
||||||
|
{
|
||||||
|
WHBLogUdpInit();
|
||||||
|
RunPatcher();
|
||||||
|
}
|
||||||
|
|
||||||
|
return real_FSOpenFile_tvii(client, block, path, mode, handle, errorMask);
|
||||||
|
}
|
||||||
|
WUPS_MUST_REPLACE_FOR_PROCESS(FSOpenFile_tvii, WUPS_LOADER_LIBRARY_COREINIT, FSOpenFile, WUPS_FP_TARGET_PROCESS_TVII);
|
||||||
|
|
||||||
|
DECL_FUNCTION(int, FSOpenFile_eshop, FSClient *client, FSCmdBlock *block, const char *path, const char *mode, uint32_t *handle, int errorMask) {
|
||||||
|
const char *oma = "vol/content/preload.oma";
|
||||||
|
|
||||||
|
if (strcmp(oma, path) == 0)
|
||||||
|
{
|
||||||
|
WHBLogUdpInit();
|
||||||
|
RunPatcher();
|
||||||
|
}
|
||||||
|
|
||||||
|
return real_FSOpenFile_eshop(client, block, path, mode, handle, errorMask);
|
||||||
|
}
|
||||||
|
WUPS_MUST_REPLACE_FOR_PROCESS(FSOpenFile_eshop, WUPS_LOADER_LIBRARY_COREINIT, FSOpenFile, WUPS_FP_TARGET_PROCESS_ESHOP);
|
||||||
|
|
|
||||||
|
|
@ -21,6 +21,7 @@
|
||||||
#include "patches/youtube.h"
|
#include "patches/youtube.h"
|
||||||
#include "patches/just_dance.h"
|
#include "patches/just_dance.h"
|
||||||
#include "patches/watch_dogs.h"
|
#include "patches/watch_dogs.h"
|
||||||
|
#include "patches/webkit_applets.h"
|
||||||
|
|
||||||
void RunPatcher() {
|
void RunPatcher() {
|
||||||
auto orplinfo = TryGetRPLInfo();
|
auto orplinfo = TryGetRPLInfo();
|
||||||
|
|
@ -57,4 +58,5 @@ void RunPatcher() {
|
||||||
Patch_youtube(titleVer, titleId, rpls);
|
Patch_youtube(titleVer, titleId, rpls);
|
||||||
Patch_just_dance(titleVer, titleId, rpls);
|
Patch_just_dance(titleVer, titleId, rpls);
|
||||||
Patch_watch_dogs(titleVer, titleId, rpls);
|
Patch_watch_dogs(titleVer, titleId, rpls);
|
||||||
|
Patch_webkit_applets(titleVer, titleId, rpls);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
60
src/patcher/patches/webkit_applets.cpp
Normal file
60
src/patcher/patches/webkit_applets.cpp
Normal file
|
|
@ -0,0 +1,60 @@
|
||||||
|
//
|
||||||
|
// Created by ash on 23/07/23.
|
||||||
|
//
|
||||||
|
|
||||||
|
#include "webkit_applets.h"
|
||||||
|
#include "utils/logger.h"
|
||||||
|
#include "patcher/patcher.h"
|
||||||
|
|
||||||
|
void Patch_webkit_applets(uint32_t titleVer, uint64_t titleId, const rplinfo& rpls)
|
||||||
|
{
|
||||||
|
if ((titleId == 0x00050010'1004B000 && titleVer == 65) ||
|
||||||
|
(titleId == 0x00050010'1004B100 && titleVer == 65) ||
|
||||||
|
(titleId == 0x00050010'1004B200 && titleVer == 65))
|
||||||
|
{
|
||||||
|
// libopenssl is identical between all regions
|
||||||
|
auto rpx = FindRPL(rpls, "libopenssl.rpl");
|
||||||
|
if (!rpx) return;
|
||||||
|
|
||||||
|
DEBUG_FUNCTION_LINE("Detected NNID Settings v%d - patching...", titleVer);
|
||||||
|
// OpenSSL ssl_verify_cert_chain
|
||||||
|
PatchInstruction((void*)(rpx->textAddr + 0x0005c138), 0x40820020, 0x60000000);
|
||||||
|
PatchInstruction((void*)(rpx->textAddr + 0x0005c150), 0x38600000, 0x38600001);
|
||||||
|
}
|
||||||
|
else if ((titleId == 0x00050030'1001600A && titleVer == 113) ||
|
||||||
|
(titleId == 0x00050030'1001610A && titleVer == 113) ||
|
||||||
|
(titleId == 0x00050030'1001620A && titleVer == 113))
|
||||||
|
{
|
||||||
|
auto rpx = FindRPL(rpls, "libopenssl.rpl");
|
||||||
|
if (!rpx) return;
|
||||||
|
|
||||||
|
DEBUG_FUNCTION_LINE("Detected Miiverse Applet v%d - patching...", titleVer);
|
||||||
|
// OpenSSL ssl_verify_cert_chain
|
||||||
|
PatchInstruction((void*)(rpx->textAddr + 0x00043c80), 0x40820020, 0x60000000);
|
||||||
|
PatchInstruction((void*)(rpx->textAddr + 0x00043c98), 0x38600000, 0x38600001);
|
||||||
|
}
|
||||||
|
else if ((titleId == 0x00050030'1001400A && titleVer == 131) ||
|
||||||
|
(titleId == 0x00050030'1001410A && titleVer == 131) ||
|
||||||
|
(titleId == 0x00050030'1001420A && titleVer == 131))
|
||||||
|
{
|
||||||
|
auto rpx = FindRPL(rpls, "libopenssl.rpl");
|
||||||
|
if (!rpx) return;
|
||||||
|
|
||||||
|
DEBUG_FUNCTION_LINE("Detected Nintendo eShop v%d - patching...", titleVer);
|
||||||
|
// OpenSSL ssl_verify_cert_chain
|
||||||
|
PatchInstruction((void*)(rpx->textAddr + 0x00043c80), 0x40820020, 0x60000000);
|
||||||
|
PatchInstruction((void*)(rpx->textAddr + 0x00043c98), 0x38600000, 0x38600001);
|
||||||
|
}
|
||||||
|
else if ((titleId == 0x00050030'1001300A && titleVer == 81) ||
|
||||||
|
(titleId == 0x00050030'1001310A && titleVer == 81) ||
|
||||||
|
(titleId == 0x00050030'1001320A && titleVer == 81))
|
||||||
|
{
|
||||||
|
auto rpx = FindRPL(rpls, "libopenssl.rpl");
|
||||||
|
if (!rpx) return;
|
||||||
|
|
||||||
|
DEBUG_FUNCTION_LINE("Detected Nintendo TVii v%d - patching...", titleVer);
|
||||||
|
// OpenSSL ssl_verify_cert_chain
|
||||||
|
PatchInstruction((void*)(rpx->textAddr + 0x00042ee4), 0x40820020, 0x60000000);
|
||||||
|
PatchInstruction((void*)(rpx->textAddr + 0x00042efc), 0x38600000, 0x38600001);
|
||||||
|
}
|
||||||
|
}
|
||||||
12
src/patcher/patches/webkit_applets.h
Normal file
12
src/patcher/patches/webkit_applets.h
Normal file
|
|
@ -0,0 +1,12 @@
|
||||||
|
//
|
||||||
|
// Created by ash on 23/07/23.
|
||||||
|
//
|
||||||
|
|
||||||
|
#ifndef MEOWTH_ACCOUNT_SETTINGS_H
|
||||||
|
#define MEOWTH_ACCOUNT_SETTINGS_H
|
||||||
|
|
||||||
|
#include "patcher/rplinfo.h"
|
||||||
|
|
||||||
|
void Patch_webkit_applets(uint32_t titleVer, uint64_t titleId, const rplinfo& rpls);
|
||||||
|
|
||||||
|
#endif //MEOWTH_ACCOUNT_SETTINGS_H
|
||||||
|
|
@ -1,27 +1,27 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#ifdef __cplusplus
|
|
||||||
extern "C" {
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <whb/log.h>
|
#include <whb/log.h>
|
||||||
#include <whb/log_udp.h>
|
#include <whb/log_udp.h>
|
||||||
#include <whb/log_cafe.h>
|
#include <whb/log_cafe.h>
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C" {
|
||||||
|
#endif
|
||||||
|
|
||||||
#define __FILENAME_X__ (strrchr(__FILE__, '\\') ? strrchr(__FILE__, '\\') + 1 : __FILE__)
|
#define __FILENAME_X__ (strrchr(__FILE__, '\\') ? strrchr(__FILE__, '\\') + 1 : __FILE__)
|
||||||
#define __FILENAME__ (strrchr(__FILE__, '/') ? strrchr(__FILE__, '/') + 1 : __FILENAME_X__)
|
#define __FILENAME__ (strrchr(__FILE__, '/') ? strrchr(__FILE__, '/') + 1 : __FILENAME_X__)
|
||||||
|
|
||||||
#define OSFATAL_FUNCTION_LINE(FMT, ARGS...)do { \
|
#define OSFATAL_FUNCTION_LINE(FMT, ARGS...)do { \
|
||||||
OSFatal_printf("[%s]%s@L%04d: " FMT "",__FILENAME__,__FUNCTION__, __LINE__, ## ARGS); \
|
OSFatal_printf("[%s]%s@L%04d: " FMT "","Meowth",__FUNCTION__, __LINE__, ## ARGS); \
|
||||||
} while (0)
|
} while (0)
|
||||||
|
|
||||||
#define DEBUG_FUNCTION_LINE(FMT, ARGS...)do { \
|
#define DEBUG_FUNCTION_LINE(FMT, ARGS...)do { \
|
||||||
WHBLogPrintf("[%23s]%30s@L%04d: " FMT "",__FILENAME__,__FUNCTION__, __LINE__, ## ARGS); \
|
WHBLogPrintf("[%23s]%30s@L%04d: " FMT "","Meowth",__FUNCTION__, __LINE__, ## ARGS); \
|
||||||
} while (0);
|
} while (0);
|
||||||
|
|
||||||
#define DEBUG_FUNCTION_LINE_WRITE(FMT, ARGS...)do { \
|
#define DEBUG_FUNCTION_LINE_WRITE(FMT, ARGS...)do { \
|
||||||
WHBLogWritef("[%23s]%30s@L%04d: " FMT "",__FILENAME__,__FUNCTION__, __LINE__, ## ARGS); \
|
WHBLogWritef("[%23s]%30s@L%04d: " FMT "","Meowth",__FUNCTION__, __LINE__, ## ARGS); \
|
||||||
} while (0);
|
} while (0);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
|
|
|
||||||
|
|
@ -1,21 +0,0 @@
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <assert.h>
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
|
||||||
extern "C" {
|
|
||||||
#endif
|
|
||||||
|
|
||||||
//remove all this if wut adds it and it causes errors
|
|
||||||
typedef struct {
|
|
||||||
uint32_t major;
|
|
||||||
uint32_t minor;
|
|
||||||
uint32_t patch;
|
|
||||||
char region;
|
|
||||||
} MCP_SystemVersion;
|
|
||||||
static_assert(sizeof(MCP_SystemVersion) == 0x10);
|
|
||||||
int MCP_GetSystemVersion(int handle, MCP_SystemVersion* version);
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
Loading…
Reference in a new issue