Implement almost working SD card cheats
This commit is contained in:
parent
e354bd4dc2
commit
738a750593
@ -5,118 +5,113 @@
|
||||
#include <fcntl.h>
|
||||
#include "common/fs_defs.h"
|
||||
#include "../dynamic_libs/fs_functions.h"
|
||||
#include "../utils/logger.h"
|
||||
|
||||
|
||||
int MountFS(void *pClient, void *pCmd, char **mount_path)
|
||||
{
|
||||
int result = -1;
|
||||
int MountFS(void *pClient, void *pCmd, char **mount_path) {
|
||||
int result = -1;
|
||||
|
||||
void *mountSrc = malloc(FS_MOUNT_SOURCE_SIZE);
|
||||
if(!mountSrc)
|
||||
return -3;
|
||||
void *mountSrc = malloc(FS_MOUNT_SOURCE_SIZE);
|
||||
if (!mountSrc)
|
||||
return -3;
|
||||
|
||||
char* mountPath = (char*) malloc(FS_MAX_MOUNTPATH_SIZE);
|
||||
if(!mountPath) {
|
||||
free(mountSrc);
|
||||
return -4;
|
||||
}
|
||||
char *mountPath = (char *) malloc(FS_MAX_MOUNTPATH_SIZE);
|
||||
if (!mountPath) {
|
||||
free(mountSrc);
|
||||
return -4;
|
||||
}
|
||||
|
||||
memset(mountSrc, 0, FS_MOUNT_SOURCE_SIZE);
|
||||
memset(mountPath, 0, FS_MAX_MOUNTPATH_SIZE);
|
||||
memset(mountSrc, 0, FS_MOUNT_SOURCE_SIZE);
|
||||
memset(mountPath, 0, FS_MAX_MOUNTPATH_SIZE);
|
||||
|
||||
// Mount sdcard
|
||||
if (FSGetMountSource(pClient, pCmd, FS_SOURCETYPE_EXTERNAL, mountSrc, -1) == 0)
|
||||
{
|
||||
result = FSMount(pClient, pCmd, mountSrc, mountPath, FS_MAX_MOUNTPATH_SIZE, -1);
|
||||
if((result == 0) && mount_path) {
|
||||
*mount_path = (char*)malloc(strlen(mountPath) + 1);
|
||||
if(*mount_path)
|
||||
strcpy(*mount_path, mountPath);
|
||||
}
|
||||
}
|
||||
// Mount sdcard
|
||||
result = FSGetMountSource(pClient, pCmd, FS_SOURCETYPE_EXTERNAL, mountSrc, -1);
|
||||
if (result == 0) {
|
||||
result = FSMount(pClient, pCmd, mountSrc, mountPath, FS_MAX_MOUNTPATH_SIZE, -1);
|
||||
if ((result == 0) && mount_path) {
|
||||
*mount_path = (char *) malloc(strlen(mountPath) + 1);
|
||||
if (*mount_path)
|
||||
strcpy(*mount_path, mountPath);
|
||||
} else {
|
||||
log_printf("FSMount error: %i\n", result);
|
||||
}
|
||||
} else {
|
||||
log_printf("FSGetMountSource error: %i\n", result);
|
||||
}
|
||||
|
||||
free(mountPath);
|
||||
free(mountSrc);
|
||||
return result;
|
||||
free(mountPath);
|
||||
free(mountSrc);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
int UmountFS(void *pClient, void *pCmd, const char *mountPath)
|
||||
{
|
||||
int result = -1;
|
||||
result = FSUnmount(pClient, pCmd, mountPath, -1);
|
||||
|
||||
return result;
|
||||
int UmountFS(void *pClient, void *pCmd, const char *mountPath) {
|
||||
return FSUnmount(pClient, pCmd, mountPath, -1);
|
||||
}
|
||||
|
||||
int LoadFileToMem(const char *filepath, u8 **inbuffer, u32 *size)
|
||||
{
|
||||
// Always initialize input
|
||||
int LoadFileToMem(const char *filepath, u8 **inbuffer, u32 *size) {
|
||||
// Always initialize input
|
||||
*inbuffer = NULL;
|
||||
if(size)
|
||||
*size = 0;
|
||||
if (size)
|
||||
*size = 0;
|
||||
|
||||
int iFd = open(filepath, O_RDONLY);
|
||||
int iFd = open(filepath, O_RDONLY);
|
||||
if (iFd < 0)
|
||||
return -1;
|
||||
|
||||
u32 filesize = lseek(iFd, 0, SEEK_END);
|
||||
lseek(iFd, 0, SEEK_SET);
|
||||
lseek(iFd, 0, SEEK_SET);
|
||||
|
||||
u8 *buffer = (u8 *) malloc(filesize);
|
||||
if (buffer == NULL)
|
||||
{
|
||||
close(iFd);
|
||||
if (buffer == NULL) {
|
||||
close(iFd);
|
||||
return -2;
|
||||
}
|
||||
|
||||
u32 blocksize = 0x4000;
|
||||
u32 done = 0;
|
||||
int readBytes = 0;
|
||||
u32 blocksize = 0x4000;
|
||||
u32 done = 0;
|
||||
int readBytes = 0;
|
||||
|
||||
while(done < filesize)
|
||||
{
|
||||
if(done + blocksize > filesize) {
|
||||
blocksize = filesize - done;
|
||||
}
|
||||
readBytes = read(iFd, buffer + done, blocksize);
|
||||
if(readBytes <= 0)
|
||||
break;
|
||||
done += readBytes;
|
||||
}
|
||||
while (done < filesize) {
|
||||
if (done + blocksize > filesize) {
|
||||
blocksize = filesize - done;
|
||||
}
|
||||
readBytes = read(iFd, buffer + done, blocksize);
|
||||
if (readBytes <= 0)
|
||||
break;
|
||||
done += readBytes;
|
||||
}
|
||||
|
||||
close(iFd);
|
||||
close(iFd);
|
||||
|
||||
if (done != filesize)
|
||||
{
|
||||
if (done != filesize) {
|
||||
free(buffer);
|
||||
return -3;
|
||||
}
|
||||
|
||||
*inbuffer = buffer;
|
||||
|
||||
//! sign is optional input
|
||||
if(size)
|
||||
*size = filesize;
|
||||
//! sign is optional input
|
||||
if (size)
|
||||
*size = filesize;
|
||||
|
||||
return filesize;
|
||||
}
|
||||
|
||||
int CheckFile(const char * filepath)
|
||||
{
|
||||
if(!filepath)
|
||||
int CheckFile(const char *filepath) {
|
||||
if (!filepath)
|
||||
return 0;
|
||||
|
||||
struct stat filestat;
|
||||
|
||||
char dirnoslash[strlen(filepath)+2];
|
||||
char dirnoslash[strlen(filepath) + 2];
|
||||
snprintf(dirnoslash, sizeof(dirnoslash), "%s", filepath);
|
||||
|
||||
while(dirnoslash[strlen(dirnoslash)-1] == '/')
|
||||
dirnoslash[strlen(dirnoslash)-1] = '\0';
|
||||
while (dirnoslash[strlen(dirnoslash) - 1] == '/')
|
||||
dirnoslash[strlen(dirnoslash) - 1] = '\0';
|
||||
|
||||
char * notRoot = strrchr(dirnoslash, '/');
|
||||
if(!notRoot)
|
||||
{
|
||||
char *notRoot = strrchr(dirnoslash, '/');
|
||||
if (!notRoot) {
|
||||
strcat(dirnoslash, "/");
|
||||
}
|
||||
|
||||
@ -126,35 +121,29 @@ int CheckFile(const char * filepath)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CreateSubfolder(const char * fullpath)
|
||||
{
|
||||
if(!fullpath)
|
||||
int CreateSubfolder(const char *fullpath) {
|
||||
if (!fullpath)
|
||||
return 0;
|
||||
|
||||
int result = 0;
|
||||
|
||||
char dirnoslash[strlen(fullpath)+1];
|
||||
char dirnoslash[strlen(fullpath) + 1];
|
||||
strcpy(dirnoslash, fullpath);
|
||||
|
||||
int pos = strlen(dirnoslash)-1;
|
||||
while(dirnoslash[pos] == '/')
|
||||
{
|
||||
int pos = strlen(dirnoslash) - 1;
|
||||
while (dirnoslash[pos] == '/') {
|
||||
dirnoslash[pos] = '\0';
|
||||
pos--;
|
||||
}
|
||||
|
||||
if(CheckFile(dirnoslash))
|
||||
{
|
||||
if (CheckFile(dirnoslash)) {
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
char parentpath[strlen(dirnoslash)+2];
|
||||
} else {
|
||||
char parentpath[strlen(dirnoslash) + 2];
|
||||
strcpy(parentpath, dirnoslash);
|
||||
char * ptr = strrchr(parentpath, '/');
|
||||
char *ptr = strrchr(parentpath, '/');
|
||||
|
||||
if(!ptr)
|
||||
{
|
||||
if (!ptr) {
|
||||
//!Device root directory (must be with '/')
|
||||
strcat(parentpath, "/");
|
||||
struct stat filestat;
|
||||
@ -170,11 +159,10 @@ int CreateSubfolder(const char * fullpath)
|
||||
result = CreateSubfolder(parentpath);
|
||||
}
|
||||
|
||||
if(!result)
|
||||
if (!result)
|
||||
return 0;
|
||||
|
||||
if (mkdir(dirnoslash, 0777) == -1)
|
||||
{
|
||||
if (mkdir(dirnoslash, 0777) == -1) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -6,6 +6,7 @@ extern "C" {
|
||||
#endif
|
||||
|
||||
#include <gctypes.h>
|
||||
#include "../common/fs_defs.h"
|
||||
|
||||
int MountFS(void *pClient, void *pCmd, char **mount_path);
|
||||
int UmountFS(void *pClient, void *pCmd, const char *mountPath);
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -23,6 +23,7 @@
|
||||
#include "patcher/function_patcher_gx2.h"
|
||||
#include "system/raw_assembly_cheats.h"
|
||||
#include "fs/fs_utils.h"
|
||||
#include "fs/sd_fat_devoptab.h"
|
||||
|
||||
void *client;
|
||||
void *commandBlock;
|
||||
@ -1485,27 +1486,56 @@ static int runTCPGeckoServer(int argc, void *argv) {
|
||||
#define TITLE_ID_LENGTH 16
|
||||
#define CODES_FILE_PATH_SIZE (SD_FILE_PATH_HEADER_LENGTH + TITLE_ID_LENGTH + EXTENSION_SIZE)
|
||||
|
||||
void applyCheatCodes() {
|
||||
unsigned char filePath[CODES_FILE_PATH_SIZE];
|
||||
memset(filePath, '0', sizeof(filePath));
|
||||
memcpy(filePath, "sd:/codes/", SD_FILE_PATH_HEADER_LENGTH); // File path header
|
||||
u64 titleID = OSGetTitleID();
|
||||
char asciiTitleID[TITLE_ID_LENGTH];
|
||||
snprintf(asciiTitleID, TITLE_ID_LENGTH, "%llX", titleID);
|
||||
memcpy(filePath + SD_FILE_PATH_HEADER_LENGTH + TITLE_ID_LEADING_ZEROS, asciiTitleID, TITLE_ID_LENGTH); // Title ID
|
||||
memcpy(filePath + SD_FILE_PATH_HEADER_LENGTH + TITLE_ID_LENGTH, ".gctu", EXTENSION_SIZE); // Extension
|
||||
filePath[CODES_FILE_PATH_SIZE - 1] = '\0'; // Null-terminated
|
||||
u64 cachedTitleID = 0;
|
||||
|
||||
unsigned char *codes = NULL;
|
||||
unsigned int codesSize = 0;
|
||||
int result = LoadFileToMem((const char *) filePath, &codes, &codesSize);
|
||||
void considerApplyingSDCheats() {
|
||||
u64 currentTitleID = OSGetTitleID();
|
||||
|
||||
if (result < 0) {
|
||||
// Error, we won't write any codes
|
||||
return;
|
||||
if (cachedTitleID == currentTitleID) {
|
||||
// log_print("Title ID NOT changed\n");
|
||||
} else {
|
||||
log_print("Title ID changed\n");
|
||||
cachedTitleID = currentTitleID;
|
||||
int result = mount_sd_fat("sd");
|
||||
|
||||
if (result < 0) {
|
||||
log_printf("Mounting error: %i\n", result);
|
||||
return;
|
||||
}
|
||||
|
||||
unsigned char filePath[CODES_FILE_PATH_SIZE];
|
||||
memset(filePath, '0', sizeof(filePath));
|
||||
memcpy(filePath, "sd:/codes/", SD_FILE_PATH_HEADER_LENGTH); // File path header
|
||||
log_printf("Title ID: %lu\n", currentTitleID);
|
||||
char asciiTitleID[TITLE_ID_LENGTH];
|
||||
snprintf(asciiTitleID, TITLE_ID_LENGTH, "%llX", currentTitleID);
|
||||
memcpy(filePath + SD_FILE_PATH_HEADER_LENGTH + TITLE_ID_LEADING_ZEROS, asciiTitleID,
|
||||
TITLE_ID_LENGTH); // Title ID
|
||||
memcpy(filePath + SD_FILE_PATH_HEADER_LENGTH + TITLE_ID_LENGTH, ".gctu", EXTENSION_SIZE); // Extension
|
||||
filePath[CODES_FILE_PATH_SIZE - 1] = '\0'; // Null-terminated
|
||||
log_printf("File Path: %s\n", filePath);
|
||||
|
||||
unsigned char *codes = NULL;
|
||||
unsigned int codesSize = 0;
|
||||
result = LoadFileToMem((const char *) filePath, &codes, &codesSize);
|
||||
|
||||
if (result < 0) {
|
||||
log_printf("Reading error: %i\n", result);
|
||||
// Error, we won't write any codes
|
||||
goto CLEANUP;
|
||||
}
|
||||
|
||||
kernelCopyData((unsigned char *) 0x01133000, codes, codesSize);
|
||||
log_print("Copied!\n");
|
||||
|
||||
CLEANUP:
|
||||
|
||||
result = unmount_sd_fat("sd");
|
||||
|
||||
if (result < 0) {
|
||||
log_printf("Unmounting error: %i\n", result);
|
||||
}
|
||||
}
|
||||
|
||||
kernelCopyData((unsigned char *) 0x01133000, codes, codesSize);
|
||||
}
|
||||
|
||||
static int startTCPGeckoThread(int argc, void *argv) {
|
||||
@ -1538,7 +1568,7 @@ static int startTCPGeckoThread(int argc, void *argv) {
|
||||
while (true) {
|
||||
usleep(9000);
|
||||
|
||||
applyCheatCodes();
|
||||
considerApplyingSDCheats();
|
||||
// log_print("Running code handler...\n");
|
||||
codeHandlerFunction();
|
||||
|
||||
|
BIN
tcpgecko.elf
BIN
tcpgecko.elf
Binary file not shown.
Loading…
Reference in New Issue
Block a user