mirror of
https://gitlab.com/Nanolx/homebrewfilter.git
synced 2024-11-24 10:09:21 +01:00
support for SD-Gecko and neek2o in HBF booter (obcd)
This commit is contained in:
parent
7546e1e22b
commit
5ebe1f801b
119
boot/source/gecko.c
Normal file
119
boot/source/gecko.c
Normal file
@ -0,0 +1,119 @@
|
||||
#include <gccore.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <malloc.h>
|
||||
#include <sys/iosupport.h>
|
||||
|
||||
/* init-globals */
|
||||
static bool geckoinit = false;
|
||||
|
||||
#ifndef NO_DEBUG
|
||||
#include <stdarg.h>
|
||||
|
||||
void gprintf(const char *format, ...)
|
||||
{
|
||||
if (!geckoinit)
|
||||
return;
|
||||
|
||||
char * tmp = NULL;
|
||||
va_list va;
|
||||
va_start(va, format);
|
||||
if((vasprintf(&tmp, format, va) >= 0) && tmp)
|
||||
{
|
||||
usb_sendbuffer(1, tmp, strlen(tmp));
|
||||
}
|
||||
va_end(va);
|
||||
|
||||
if(tmp)
|
||||
free(tmp);
|
||||
}
|
||||
|
||||
bool InitGecko()
|
||||
{
|
||||
u32 geckoattached = usb_isgeckoalive(EXI_CHANNEL_1);
|
||||
if (geckoattached)
|
||||
{
|
||||
usb_flush(EXI_CHANNEL_1);
|
||||
geckoinit = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
char ascii(char s)
|
||||
{
|
||||
if (s < 0x20) return '.';
|
||||
if (s > 0x7E) return '.';
|
||||
return s;
|
||||
}
|
||||
|
||||
void hexdump(void *d, int len)
|
||||
{
|
||||
u8 *data;
|
||||
int i, off;
|
||||
data = (u8*) d;
|
||||
|
||||
gprintf("\n 0 1 2 3 4 5 6 7 8 9 A B C D E F 0123456789ABCDEF");
|
||||
gprintf("\n==== =============================================== ================\n");
|
||||
|
||||
for (off = 0; off < len; off += 16)
|
||||
{
|
||||
gprintf("%04x ", off);
|
||||
for (i = 0; i < 16; i++)
|
||||
if ((i + off) >= len)
|
||||
gprintf(" ");
|
||||
else gprintf("%02x ", data[off + i]);
|
||||
|
||||
gprintf(" ");
|
||||
for (i = 0; i < 16; i++)
|
||||
if ((i + off) >= len)
|
||||
gprintf(" ");
|
||||
else gprintf("%c", ascii(data[off + i]));
|
||||
gprintf("\n");
|
||||
}
|
||||
}
|
||||
|
||||
static ssize_t __out_write(struct _reent *r, int fd, const char *ptr, size_t len)
|
||||
{
|
||||
if(geckoinit && ptr)
|
||||
usb_sendbuffer(1, ptr, len);
|
||||
|
||||
return len;
|
||||
}
|
||||
|
||||
static const devoptab_t gecko_out = {
|
||||
"stdout", // device name
|
||||
0, // size of file structure
|
||||
NULL, // device open
|
||||
NULL, // device close
|
||||
__out_write,// device write
|
||||
NULL, // device read
|
||||
NULL, // device seek
|
||||
NULL, // device fstat
|
||||
NULL, // device stat
|
||||
NULL, // device link
|
||||
NULL, // device unlink
|
||||
NULL, // device chdir
|
||||
NULL, // device rename
|
||||
NULL, // device mkdir
|
||||
0, // dirStateSize
|
||||
NULL, // device diropen_r
|
||||
NULL, // device dirreset_r
|
||||
NULL, // device dirnext_r
|
||||
NULL, // device dirclose_r
|
||||
NULL, // device statvfs_r
|
||||
NULL, // device ftruncate_r
|
||||
NULL, // device fsync_r
|
||||
NULL, // device deviceData
|
||||
NULL, // device chmod_r
|
||||
NULL, // device fchmod_r
|
||||
};
|
||||
|
||||
void USBGeckoOutput()
|
||||
{
|
||||
devoptab_list[STD_OUT] = &gecko_out;
|
||||
devoptab_list[STD_ERR] = &gecko_out;
|
||||
}
|
||||
|
||||
#endif /* NO_DEBUG */
|
@ -2,14 +2,21 @@
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <gccore.h>
|
||||
#include <unistd.h>
|
||||
#include <ogc/machine/processor.h>
|
||||
#include <ogc/irq.h>
|
||||
#include "uneek_fs.h"
|
||||
|
||||
extern void __exception_closeall();
|
||||
/* Video variables */
|
||||
static void *framebuffer = NULL;
|
||||
static GXRModeObj *vmode = NULL;
|
||||
|
||||
extern void __exception_closeall();
|
||||
typedef void (*entrypoint) (void);
|
||||
|
||||
static u8 *buffer = (u8 *) 0x92000000;
|
||||
static u8 *buffer = (u8 *) 0x92000000;
|
||||
|
||||
extern u8 hbf_dol[];
|
||||
extern u8 hbf_dol[];
|
||||
extern u32 hbf_dol_size;
|
||||
|
||||
typedef struct _dolheader {
|
||||
@ -60,9 +67,56 @@ u32 load_dol_image(void *dolstart)
|
||||
return 0;
|
||||
}
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
memcpy(buffer, (void *) hbf_dol, hbf_dol_size);
|
||||
void Video_Clear(s32 color)
|
||||
{
|
||||
VIDEO_ClearFrameBuffer(vmode, framebuffer, color);
|
||||
}
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
|
||||
|
||||
/*
|
||||
raw_irq_handler_t irq_handler;
|
||||
|
||||
__IOS_ShutdownSubsystems();
|
||||
__ES_Init();
|
||||
|
||||
__ES_Reset();
|
||||
|
||||
// Mask IPC IRQ while we're busy reloading
|
||||
__MaskIrq(IRQ_PI_ACR);
|
||||
irq_handler = IRQ_Free(IRQ_PI_ACR);
|
||||
IRQ_Request(IRQ_PI_ACR, irq_handler, NULL);
|
||||
__UnmaskIrq(IRQ_PI_ACR);
|
||||
__IPC_Reinitialize();
|
||||
|
||||
__IOS_InitializeSubsystems();
|
||||
|
||||
*/
|
||||
VIDEO_Init();
|
||||
vmode = VIDEO_GetPreferredMode(NULL);
|
||||
|
||||
/* Allocate memory for the framebuffer */
|
||||
framebuffer = MEM_K0_TO_K1(SYS_AllocateFramebuffer(vmode));
|
||||
|
||||
/* Configure the video subsystem */
|
||||
VIDEO_Configure(vmode);
|
||||
|
||||
/* Setup video */
|
||||
VIDEO_SetNextFramebuffer(framebuffer);
|
||||
VIDEO_SetBlack(FALSE);
|
||||
VIDEO_Flush();
|
||||
VIDEO_WaitVSync();
|
||||
|
||||
if (vmode->viTVMode & VI_NON_INTERLACE)
|
||||
VIDEO_WaitVSync();
|
||||
|
||||
/* Clear the screen */
|
||||
Video_Clear(COLOR_BLACK);
|
||||
|
||||
|
||||
memcpy(buffer, (void *) hbf_dol, hbf_dol_size);
|
||||
|
||||
u32 exeEntryPointAddress = load_dol_image(buffer);
|
||||
entrypoint exeEntryPoint = (entrypoint) exeEntryPointAddress;
|
||||
u32 level;
|
||||
@ -71,7 +125,7 @@ int main(int argc, char **argv) {
|
||||
__exception_closeall();
|
||||
exeEntryPoint();
|
||||
_CPU_ISR_Restore(level);
|
||||
|
||||
|
||||
exit(0);
|
||||
}
|
||||
|
||||
|
652
boot/source/uneek_fs.c
Normal file
652
boot/source/uneek_fs.c
Normal file
@ -0,0 +1,652 @@
|
||||
/*-------------------------------------------------------------
|
||||
|
||||
uneek_fs.c -- USB mass storage support, using a modified uneek fs-usb
|
||||
|
||||
rev. 1.00 first draft
|
||||
|
||||
rev. 1.01 second draft
|
||||
added detection and support for SDHC access in SNEEK
|
||||
added check_uneek_fs_type function to see if it's sneek or uneek
|
||||
|
||||
rev. 1.02 third draft
|
||||
added the UNEEK_FS_BOTH option to the init_uneek_fs function.
|
||||
when the parameter is set, both sd and usb access are rerouted to the sd card.
|
||||
it can only be used with sneek and could serve programs like Joyflow on a sd only
|
||||
setup.
|
||||
the exit_uneek_fs function needs to be called when that setup is used.
|
||||
since I can't disable usb, not knowing if sd access is still needed, and
|
||||
I can't disable sd if usb access if sd is still needed.
|
||||
It's probably exceptional that one will be shutdown and the other still used,
|
||||
but it's better to stay on the safe area.
|
||||
|
||||
rev. 1.04 fourth draft.
|
||||
shutdown function is now a stub as some programs call it before they end to force a remount
|
||||
exit_uneek_fs added to properly shutdown the uneek_usb_fs file system.
|
||||
max_write_sectors increased to speedup things. Transfer speed from wiixplorer gone up
|
||||
from 20KB/s to 265KB/s.
|
||||
|
||||
rev. 1.05 fifth draft
|
||||
added "is_uneek" function
|
||||
|
||||
rev. 1.06 sixth draft
|
||||
added "is_neek2" and "is_neek3" functions
|
||||
Crediar changed the boot2 version back from 5 to 4.
|
||||
The is_uneek function will not detect those neek versions anymore.
|
||||
Stfour created the is_neek2 method to detect if neek is running.
|
||||
JoostinOnline and GiantPune created the is_neek3 which is a little less code.
|
||||
So, you should use either is_neek2 or is_neek3
|
||||
|
||||
rev. 1.07 seventh draft
|
||||
added "is_neek4" function
|
||||
Dj_Skual created the is_neek4 method to detect if neek is running.
|
||||
|
||||
added WII_launch_Channel. It's not really uneek_fs related, but it could be handy
|
||||
|
||||
|
||||
Copyright (C) 2011 Obcd
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any
|
||||
damages arising from the use of this software.
|
||||
|
||||
Permission is granted to anyone to use this software for any
|
||||
purpose, including commercial applications, and to alter it and
|
||||
redistribute it freely, subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you
|
||||
must not claim that you wrote the original software. If you use
|
||||
this software in a product, an acknowledgment in the product
|
||||
documentation would be appreciated but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and
|
||||
must not be misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source
|
||||
distribution.
|
||||
|
||||
-------------------------------------------------------------*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <ogcsys.h>
|
||||
#include <locale.h>
|
||||
#include <malloc.h>
|
||||
#include <ogc/isfs.h>
|
||||
//#include <sdcard/wiisd_io.h>
|
||||
//#include <gctypes.h>
|
||||
//#include <ogc/disc_io.h>
|
||||
|
||||
|
||||
//#define SHOW_GECKO_DEBUG 1
|
||||
|
||||
#ifdef SHOW_GECKO_DEBUG
|
||||
#include "gecko.h"
|
||||
#endif
|
||||
|
||||
#define MAX_READ_SECTORS 16 //yet to be determined how much is allowed?
|
||||
#define MAX_WRITE_SECTORS 16 //yet to be determined how much is allowed?
|
||||
#define CACHE_SECTOR_LOCATION 1 //not sure if it will improve speed much...
|
||||
|
||||
#define UNEEK_FS_NONE 0
|
||||
#define UNEEK_FS_USB 1
|
||||
#define UNEEK_FS_SD 2
|
||||
#define UNEEK_FS_BOTH 4
|
||||
|
||||
#define ISFS_OPEN_ALL 64
|
||||
|
||||
#define DEVICE_TYPE_WII_SD (('W'<<24)|('I'<<16)|('S'<<8)|'D')
|
||||
|
||||
|
||||
//Not yet implemented as most disk io buffers don't seem have proper alignment
|
||||
//It would require a more serious modification in the code (aligning those buffers)
|
||||
//#define USE_ORIGINAL_ALIGNED_BUF 0 //if the buffer is aligned already...why not?
|
||||
|
||||
|
||||
|
||||
//This one triggers the unique functions in the uneek fs
|
||||
//Don't try to change it.
|
||||
//If you really need to access that file with ISFS, access it in read/write mode
|
||||
//As only read mode will trigger uneek fs
|
||||
|
||||
static char _dev_obcd[] ATTRIBUTE_ALIGN(32) = "/sneek/obcd.txt";
|
||||
|
||||
static s32 fu = -1;
|
||||
// static bool uneek_fs_ok = false;
|
||||
static s32 uneek_fs_type = UNEEK_FS_NONE;
|
||||
|
||||
s32 confirm_neek1 = 5;
|
||||
s32 confirm_neek2 = 5;
|
||||
s32 confirm_neek3 = 5;
|
||||
s32 confirm_neek4 = 5;
|
||||
|
||||
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
static u32 seek_cache;
|
||||
#endif
|
||||
|
||||
// DISC_INTERFACE __io_usbstorage;
|
||||
DISC_INTERFACE __io_wiisd;
|
||||
extern DISC_INTERFACE __io_usbstorage;
|
||||
//extern DISC_INTERFACE __io_usb2storage;
|
||||
|
||||
// DISC_INTERFACE methods
|
||||
|
||||
static bool __io_uns_IsInserted(void)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool __io_uns_Startup(void)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
int usb_verbose = 0;
|
||||
|
||||
bool __io_uns_ReadSectors(u32 sector, u32 count, void *buffer)
|
||||
{
|
||||
|
||||
u8* buf;
|
||||
s32 whence;
|
||||
u32 done;
|
||||
u32 sec;
|
||||
u32 amount;
|
||||
u8* resultbuf;
|
||||
|
||||
done = 0;
|
||||
sec = sector;
|
||||
if (count <= MAX_READ_SECTORS)
|
||||
{
|
||||
amount = count;
|
||||
}
|
||||
else
|
||||
{
|
||||
amount = MAX_READ_SECTORS;
|
||||
}
|
||||
// buf = (u8 *)memalign(32, 512 * amount);
|
||||
// sdhc aligns it's buffers on 64 byte boundaries
|
||||
buf = (u8 *)memalign(64, 512 * amount);
|
||||
|
||||
while(done < count)
|
||||
{
|
||||
whence = 0;
|
||||
if ((sec & 0x80000000)!= 0)
|
||||
{
|
||||
sec &= 0x7fffffff;
|
||||
whence = 1;
|
||||
}
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
if ((sector + done) != seek_cache)
|
||||
{
|
||||
#endif
|
||||
ISFS_Seek(fu,sec,whence);
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
seek_cache = sector + done;
|
||||
}
|
||||
#endif
|
||||
s32 ret = ISFS_Read(fu,buf,512*amount);
|
||||
if (ret == (s32)(512*amount))
|
||||
{
|
||||
resultbuf = (u8*)buffer + (done * 512);
|
||||
memcpy(resultbuf,buf,512*amount);
|
||||
done+=amount;
|
||||
sec = sector + done;
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
seek_cache = sector + done;
|
||||
#endif
|
||||
if((count-done)<=MAX_READ_SECTORS)
|
||||
{
|
||||
amount = count - done;
|
||||
}
|
||||
else
|
||||
{
|
||||
amount = MAX_READ_SECTORS;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
seek_cache = 0xfffffff8;
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
}
|
||||
free(buf);
|
||||
if (usb_verbose) {
|
||||
printf("usb-r: %x [%d]\n", sector, count);
|
||||
//sleep(1);
|
||||
}
|
||||
//printf("ret = %x\n",ret);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool __io_uns_WriteSectors(u32 sector, u32 count, void *buffer)
|
||||
{
|
||||
|
||||
u8* buf;
|
||||
s32 whence;
|
||||
u32 done;
|
||||
u32 sec;
|
||||
u32 amount;
|
||||
u8* resultbuf;
|
||||
|
||||
done = 0;
|
||||
sec = sector;
|
||||
if (count <= MAX_WRITE_SECTORS)
|
||||
{
|
||||
amount = count;
|
||||
}
|
||||
else
|
||||
{
|
||||
amount = MAX_WRITE_SECTORS;
|
||||
}
|
||||
// buf = (u8 *)memalign(32, 512 * amount);
|
||||
// sdhc aligns it's buffers on 64 byte boundaries
|
||||
buf = (u8 *)memalign(64, 512 * amount);
|
||||
|
||||
while(done < count)
|
||||
{
|
||||
whence = 0;
|
||||
if ((sec & 0x80000000)!= 0)
|
||||
{
|
||||
sec &= 0x7fffffff;
|
||||
whence = 1;
|
||||
}
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
if ((sector + done) != seek_cache)
|
||||
{
|
||||
#endif
|
||||
ISFS_Seek(fu,sec,whence);
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
seek_cache = sector + done;
|
||||
}
|
||||
#endif
|
||||
resultbuf = (u8*)buffer + (done * 512);
|
||||
memcpy(buf,resultbuf,512*amount);
|
||||
s32 ret = ISFS_Write(fu,buf,512*amount);
|
||||
if (ret == (s32)(512*amount))
|
||||
{
|
||||
done+=amount;
|
||||
sec = sector + done;
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
seek_cache = sector + done;
|
||||
#endif
|
||||
if((count-done)<=MAX_WRITE_SECTORS)
|
||||
{
|
||||
amount = count - done;
|
||||
}
|
||||
else
|
||||
{
|
||||
amount = MAX_WRITE_SECTORS;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
seek_cache = 0xfffffff8;
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
free(buf);
|
||||
if (usb_verbose) {
|
||||
printf("usb-r: %x [%d]\n", sector, count);
|
||||
//sleep(1);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool __io_uns_ClearStatus(void)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
static bool __io_uns_Shutdown(void)
|
||||
{
|
||||
|
||||
return true;
|
||||
/*
|
||||
if ((uneek_fs_type != UNEEK_FS_NONE)&&(uneek_fs_type != UNEEK_FS_BOTH))
|
||||
{
|
||||
ISFS_Close(fu);
|
||||
ISFS_Deinitialize();
|
||||
uneek_fs_type = UNEEK_FS_NONE;
|
||||
}
|
||||
// do nothing
|
||||
return true;
|
||||
*/
|
||||
}
|
||||
|
||||
static bool __io_uns_NOP(void)
|
||||
{
|
||||
// do nothing
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
|
||||
bool init_uneek_fs(u32 mode)
|
||||
{
|
||||
|
||||
u8* buf = NULL;
|
||||
struct _fstats* pstat = NULL;
|
||||
//struct _fstats stat;
|
||||
|
||||
if (uneek_fs_type == UNEEK_FS_NONE){
|
||||
ISFS_Initialize();
|
||||
fu = ISFS_Open(_dev_obcd, ISFS_OPEN_READ);
|
||||
buf = (u8*)memalign(32, sizeof(struct _fstats));
|
||||
pstat = (struct _fstats*)buf;
|
||||
pstat->file_length = 0;
|
||||
pstat->file_pos = 0;
|
||||
if(fu >= 0)
|
||||
{
|
||||
ISFS_GetFileStats(fu,pstat);
|
||||
//printf("Filestat length returned %x\n",pstat->file_length);
|
||||
//printf("Filestat pos returned %x\n",pstat->file_pos);
|
||||
}
|
||||
if ((pstat->file_length == 0xfffffff0)&&(pstat->file_pos == 0xfffffff8)&&(fu>=0))
|
||||
{
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
seek_cache = 0xfffffff8;
|
||||
#endif
|
||||
if (mode & ISFS_OPEN_WRITE)
|
||||
{
|
||||
__io_usbstorage.ioType = DEVICE_TYPE_WII_USB;
|
||||
__io_usbstorage.features = FEATURE_MEDIUM_CANREAD | FEATURE_MEDIUM_CANWRITE | FEATURE_WII_USB;
|
||||
__io_usbstorage.startup = (FN_MEDIUM_STARTUP)&__io_uns_Startup;
|
||||
__io_usbstorage.isInserted = (FN_MEDIUM_ISINSERTED)&__io_uns_IsInserted;
|
||||
__io_usbstorage.readSectors = (FN_MEDIUM_READSECTORS)&__io_uns_ReadSectors;
|
||||
__io_usbstorage.writeSectors = (FN_MEDIUM_WRITESECTORS)&__io_uns_WriteSectors;
|
||||
__io_usbstorage.clearStatus = (FN_MEDIUM_CLEARSTATUS)&__io_uns_ClearStatus;
|
||||
__io_usbstorage.shutdown = (FN_MEDIUM_SHUTDOWN)&__io_uns_Shutdown;
|
||||
}
|
||||
else
|
||||
{
|
||||
__io_usbstorage.ioType = DEVICE_TYPE_WII_USB;
|
||||
__io_usbstorage.features = FEATURE_MEDIUM_CANREAD | FEATURE_WII_USB;
|
||||
__io_usbstorage.startup = (FN_MEDIUM_STARTUP)&__io_uns_Startup;
|
||||
__io_usbstorage.isInserted = (FN_MEDIUM_ISINSERTED)&__io_uns_IsInserted;
|
||||
__io_usbstorage.readSectors = (FN_MEDIUM_READSECTORS)&__io_uns_ReadSectors;
|
||||
__io_usbstorage.writeSectors = (FN_MEDIUM_WRITESECTORS)&__io_uns_NOP; //&__io_uns_WriteSectors
|
||||
__io_usbstorage.clearStatus = (FN_MEDIUM_CLEARSTATUS)&__io_uns_ClearStatus;
|
||||
__io_usbstorage.shutdown = (FN_MEDIUM_SHUTDOWN)&__io_uns_Shutdown;
|
||||
}
|
||||
|
||||
uneek_fs_type = UNEEK_FS_USB;
|
||||
free (buf);
|
||||
return true;
|
||||
}
|
||||
//sneek
|
||||
else if ((pstat->file_length == 0xfffffff1)&&(pstat->file_pos == 0xfffffff8)&&(fu>=0))
|
||||
{
|
||||
#ifdef CACHE_SECTOR_LOCATION
|
||||
seek_cache = 0xfffffff8;
|
||||
#endif
|
||||
uneek_fs_type = UNEEK_FS_SD;
|
||||
if (mode & ISFS_OPEN_WRITE)
|
||||
{
|
||||
__io_wiisd.ioType = DEVICE_TYPE_WII_SD;
|
||||
__io_wiisd.features = FEATURE_MEDIUM_CANREAD | FEATURE_MEDIUM_CANWRITE | FEATURE_WII_SD;
|
||||
__io_wiisd.startup = (FN_MEDIUM_STARTUP)&__io_uns_Startup;
|
||||
__io_wiisd.isInserted = (FN_MEDIUM_ISINSERTED)&__io_uns_IsInserted;
|
||||
__io_wiisd.readSectors = (FN_MEDIUM_READSECTORS)&__io_uns_ReadSectors;
|
||||
__io_wiisd.writeSectors = (FN_MEDIUM_WRITESECTORS)&__io_uns_WriteSectors;
|
||||
__io_wiisd.clearStatus = (FN_MEDIUM_CLEARSTATUS)&__io_uns_ClearStatus;
|
||||
__io_wiisd.shutdown = (FN_MEDIUM_SHUTDOWN)&__io_uns_Shutdown;
|
||||
|
||||
//usb and sd will be treated equally
|
||||
//needed for joyflow with the sd only setup
|
||||
|
||||
if (mode & ISFS_OPEN_ALL)
|
||||
{
|
||||
__io_usbstorage.ioType = DEVICE_TYPE_WII_USB;
|
||||
__io_usbstorage.features = FEATURE_MEDIUM_CANREAD | FEATURE_MEDIUM_CANWRITE | FEATURE_WII_USB;
|
||||
__io_usbstorage.startup = (FN_MEDIUM_STARTUP)&__io_uns_Startup;
|
||||
__io_usbstorage.isInserted = (FN_MEDIUM_ISINSERTED)&__io_uns_IsInserted;
|
||||
__io_usbstorage.readSectors = (FN_MEDIUM_READSECTORS)&__io_uns_ReadSectors;
|
||||
__io_usbstorage.writeSectors = (FN_MEDIUM_WRITESECTORS)&__io_uns_WriteSectors;
|
||||
__io_usbstorage.clearStatus = (FN_MEDIUM_CLEARSTATUS)&__io_uns_ClearStatus;
|
||||
__io_usbstorage.shutdown = (FN_MEDIUM_SHUTDOWN)&__io_uns_Shutdown;
|
||||
uneek_fs_type = UNEEK_FS_BOTH;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
__io_wiisd.ioType = DEVICE_TYPE_WII_SD;
|
||||
__io_wiisd.features = FEATURE_MEDIUM_CANREAD | FEATURE_WII_SD;
|
||||
__io_wiisd.startup = (FN_MEDIUM_STARTUP)&__io_uns_Startup;
|
||||
__io_wiisd.isInserted = (FN_MEDIUM_ISINSERTED)&__io_uns_IsInserted;
|
||||
__io_wiisd.readSectors = (FN_MEDIUM_READSECTORS)&__io_uns_ReadSectors;
|
||||
__io_wiisd.writeSectors = (FN_MEDIUM_WRITESECTORS)&__io_uns_NOP; //&__io_uns_WriteSectors
|
||||
__io_wiisd.clearStatus = (FN_MEDIUM_CLEARSTATUS)&__io_uns_ClearStatus;
|
||||
__io_wiisd.shutdown = (FN_MEDIUM_SHUTDOWN)&__io_uns_Shutdown;
|
||||
if(mode & ISFS_OPEN_ALL)
|
||||
{
|
||||
__io_usbstorage.ioType = DEVICE_TYPE_WII_USB;
|
||||
__io_usbstorage.features = FEATURE_MEDIUM_CANREAD | FEATURE_WII_USB;
|
||||
__io_usbstorage.startup = (FN_MEDIUM_STARTUP)&__io_uns_Startup;
|
||||
__io_usbstorage.isInserted = (FN_MEDIUM_ISINSERTED)&__io_uns_IsInserted;
|
||||
__io_usbstorage.readSectors = (FN_MEDIUM_READSECTORS)&__io_uns_ReadSectors;
|
||||
__io_usbstorage.writeSectors = (FN_MEDIUM_WRITESECTORS)&__io_uns_NOP; //&__io_uns_WriteSectors
|
||||
__io_usbstorage.clearStatus = (FN_MEDIUM_CLEARSTATUS)&__io_uns_ClearStatus;
|
||||
__io_usbstorage.shutdown = (FN_MEDIUM_SHUTDOWN)&__io_uns_Shutdown;
|
||||
uneek_fs_type = UNEEK_FS_BOTH;
|
||||
}
|
||||
}
|
||||
free (buf);
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* these should be initialised right in the ogc library */
|
||||
/* so we will ignore those for the moment */
|
||||
/*
|
||||
__io_usbstorage.ioType = DEVICE_TYPE_WII_USB;
|
||||
__io_usbstorage.features = FEATURE_MEDIUM_CANREAD | FEATURE_MEDIUM_CANWRITE | FEATURE_WII_USB;
|
||||
__io_usbstorage.startup = (FN_MEDIUM_STARTUP)&__io_usb_Startup;
|
||||
__io_usbstorage.isInserted = (FN_MEDIUM_ISINSERTED)&__io_usb_IsInserted;
|
||||
__io_usbstorage.readSectors = (FN_MEDIUM_READSECTORS)&__io_usb_ReadSectors;
|
||||
__io_usbstorage.writeSectors = (FN_MEDIUM_WRITESECTORS)&__io_usb_WriteSectors;
|
||||
__io_usbstorage.clearStatus = (FN_MEDIUM_CLEARSTATUS)&__io_usb_ClearStatus;
|
||||
__io_usbstorage.shutdown = (FN_MEDIUM_SHUTDOWN)&__io_usb_Shutdown;
|
||||
*/
|
||||
|
||||
uneek_fs_type = UNEEK_FS_NONE;
|
||||
free(buf);
|
||||
ISFS_Close(fu);
|
||||
ISFS_Deinitialize();
|
||||
return false;
|
||||
}
|
||||
}
|
||||
else //was already initialised
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* stay compatible with previous versions */
|
||||
bool check_uneek_fs(void)
|
||||
{
|
||||
if(uneek_fs_type != UNEEK_FS_NONE)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
s32 check_uneek_fs_type(void)
|
||||
{
|
||||
return uneek_fs_type;
|
||||
}
|
||||
|
||||
bool exit_uneek_fs(void)
|
||||
{
|
||||
if (uneek_fs_type != UNEEK_FS_NONE)
|
||||
{
|
||||
ISFS_Close(fu);
|
||||
ISFS_Deinitialize();
|
||||
uneek_fs_type = UNEEK_FS_NONE;
|
||||
}
|
||||
// do nothing
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
bool SenseSneek (bool isfsinit)
|
||||
{
|
||||
bool ret = true;
|
||||
char path[ISFS_MAXPATH] ATTRIBUTE_ALIGN(32);
|
||||
|
||||
strcpy (path, "/SNEEK/kernel.bin");
|
||||
|
||||
if (isfsinit) ISFS_Initialize ();
|
||||
|
||||
s32 fd = ISFS_Open(path, ISFS_OPEN_READ);
|
||||
if (fd < 0)
|
||||
ret = false;
|
||||
else
|
||||
ISFS_Close (fd);
|
||||
|
||||
if (isfsinit) ISFS_Deinitialize();
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
|
||||
bool is_neek(void)
|
||||
{
|
||||
u32 boot2version;
|
||||
|
||||
if(confirm_neek1 == 5)
|
||||
{
|
||||
ES_GetBoot2Version(&boot2version);
|
||||
if(boot2version < 5)
|
||||
confirm_neek1 = false;
|
||||
else
|
||||
confirm_neek1 = true;
|
||||
}
|
||||
return confirm_neek1;
|
||||
}
|
||||
|
||||
|
||||
bool is_neek2 (bool isfsinit)
|
||||
{
|
||||
|
||||
char path[ISFS_MAXPATH] ATTRIBUTE_ALIGN(32);
|
||||
|
||||
if(confirm_neek2 == 5)
|
||||
{
|
||||
confirm_neek2 = true;
|
||||
strcpy (path, "/SNEEK/kernel.bin");
|
||||
|
||||
if (isfsinit) ISFS_Initialize ();
|
||||
|
||||
s32 fd = ISFS_Open(path, ISFS_OPEN_READ);
|
||||
if (fd < 0)
|
||||
confirm_neek2 = false;
|
||||
else
|
||||
ISFS_Close (fd);
|
||||
|
||||
if (isfsinit) ISFS_Deinitialize ();
|
||||
}
|
||||
return confirm_neek2;
|
||||
}
|
||||
|
||||
//! New method for determining if this is a real or emu nand.
|
||||
//! Works with new versions of classic Crediar NEEK
|
||||
bool is_neek3(bool isfsinit)
|
||||
{
|
||||
u32 num = 0;
|
||||
|
||||
//! Thanks goes to the almighty giantpune for this
|
||||
if(confirm_neek3 == 5)
|
||||
{
|
||||
if (isfsinit) ISFS_Initialize ();
|
||||
if(ISFS_ReadDir("/Sneek", NULL, &num)==0)
|
||||
confirm_neek3 = true;
|
||||
else
|
||||
confirm_neek3 = false;
|
||||
if (isfsinit) ISFS_Deinitialize ();
|
||||
}
|
||||
return confirm_neek3;
|
||||
}
|
||||
|
||||
bool is_neek4(bool isfsinit)
|
||||
{
|
||||
|
||||
u32 ownerID;
|
||||
u16 groupID;
|
||||
u8 attributes;
|
||||
u8 ownerperm;
|
||||
u8 groupperm;
|
||||
u8 otherperm;
|
||||
|
||||
if(confirm_neek4 == 5)
|
||||
{
|
||||
confirm_neek4 = false;
|
||||
if(isfsinit) ISFS_Initialize();
|
||||
ISFS_GetAttr("/shared1/00000000.app", &ownerID, &groupID, &attributes, &ownerperm, &groupperm, &otherperm);
|
||||
if(otherperm)
|
||||
confirm_neek4 = true;
|
||||
|
||||
if(isfsinit) ISFS_Deinitialize();
|
||||
}
|
||||
return confirm_neek4;
|
||||
}
|
||||
|
||||
bool WII_Launch_Channel(char* which)
|
||||
{
|
||||
#ifdef HW_RVL
|
||||
size_t wlen;
|
||||
u64 title_id;
|
||||
int titlemsb, titlelsb;
|
||||
char stitlexsb[16];
|
||||
union lsbstufftype
|
||||
{
|
||||
char titlename[4];
|
||||
u32 title_lsb;
|
||||
}lsbstuff;
|
||||
|
||||
|
||||
wlen = strlen(which);
|
||||
if ((wlen != 4) && (wlen != 16))
|
||||
{
|
||||
#ifdef SHOW_GECKO_DEBUG
|
||||
gprintf("Title %s has an invalid length\n",which);
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
if (wlen == 4)
|
||||
{
|
||||
titlemsb = 0x00010001;
|
||||
strncpy(lsbstuff.titlename,which,4);
|
||||
titlelsb = lsbstuff.title_lsb;
|
||||
}
|
||||
else
|
||||
{
|
||||
strncpy(stitlexsb,which,8);
|
||||
stitlexsb[8]=0;
|
||||
sscanf(stitlexsb,"%x",&titlemsb);
|
||||
strncpy(stitlexsb,which+8,8);
|
||||
stitlexsb[8]=0;
|
||||
sscanf(stitlexsb,"%x",&titlelsb);
|
||||
}
|
||||
title_id = (u64)(titlemsb) << 32;
|
||||
title_id = title_id + (u64)(titlelsb);
|
||||
#ifdef SHOW_GECKO_DEBUG
|
||||
gprintf( "titleid = %08x %08x\r\n", (u32)((title_id)>>32), (u32)(title_id) );
|
||||
s32 lret = WII_LaunchTitle(title_id);
|
||||
gprintf("WII_LaunchTitle returned %d\r\n",lret);
|
||||
#else
|
||||
WII_LaunchTitle(title_id);
|
||||
#endif
|
||||
// basically, it shouldn't get here I assume
|
||||
#endif //HW_RVL
|
||||
return false;
|
||||
}
|
96
boot/source/uneek_fs.h
Normal file
96
boot/source/uneek_fs.h
Normal file
@ -0,0 +1,96 @@
|
||||
/*-------------------------------------------------------------
|
||||
|
||||
uneek_fs.H -- USB mass storage support, using a modified uneek fs-usb
|
||||
|
||||
rev. 1.00 first draft
|
||||
|
||||
rev. 1.01 second draft
|
||||
added detection and support for SDHC access in SNEEK
|
||||
added check_uneek_fs_type function to see if it's sneek or uneek
|
||||
|
||||
rev. 1.02 third draft
|
||||
added the UNEEK_FS_BOTH option to the init_uneek_fs function.
|
||||
when the parameter is set, both sd and usb access are rerouted to the sd card.
|
||||
it can only be used with sneek.
|
||||
the exit_uneek_fs function needs to be called when that setup is used.
|
||||
since I can't disable usb, not knowing if sd access is still needed, and
|
||||
I can't disable sd if usb access if sd is still needed.
|
||||
It's probably exceptional that one will be shutdown and the other still used,
|
||||
but it's better to stay on the safe area.
|
||||
|
||||
rev. 1.05 fifth draft
|
||||
added "is_uneek" function
|
||||
|
||||
rev. 1.06 sixth draft
|
||||
added "is_neek2" and "is_neek3" functions
|
||||
Crediar changed the boot2 version back from 5 to 4.
|
||||
The is_uneek function will not detect those neek versions anymore.
|
||||
Stfour created the is_neek2 method to detect if neek is running.
|
||||
JoostinOnline and GiantPune created the is_neek3 which is a little less code.
|
||||
So, you should use either is_neek2 or is_neek3
|
||||
|
||||
rev. 1.07 seventh draft
|
||||
added "is_neek4" function
|
||||
Dj_Skual created the is_neek4 method to detect if neek is running.
|
||||
|
||||
added WII_launch_Channel. It's not really uneek_fs related, but it could be handy
|
||||
|
||||
|
||||
Copyright (C) 2011 Obcd
|
||||
|
||||
This software is provided 'as-is', without any express or implied
|
||||
warranty. In no event will the authors be held liable for any
|
||||
damages arising from the use of this software.
|
||||
|
||||
Permission is granted to anyone to use this software for any
|
||||
purpose, including commercial applications, and to alter it and
|
||||
redistribute it freely, subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you
|
||||
must not claim that you wrote the original software. If you use
|
||||
this software in a product, an acknowledgment in the product
|
||||
documentation would be appreciated but is not required.
|
||||
|
||||
2. Altered source versions must be plainly marked as such, and
|
||||
must not be misrepresented as being the original software.
|
||||
|
||||
3. This notice may not be removed or altered from any source
|
||||
distribution.
|
||||
|
||||
-------------------------------------------------------------*/
|
||||
|
||||
#ifndef _UNEEK_FS_H_
|
||||
#define _UNEEK_FS_H_
|
||||
|
||||
#include <ogcsys.h>
|
||||
#include <ogc/isfs.h>
|
||||
|
||||
|
||||
#define UNEEK_FS_NONE 0
|
||||
#define UNEEK_FS_USB 1
|
||||
#define UNEEK_FS_SD 2
|
||||
#define UNEEK_FS_BOTH 4
|
||||
|
||||
#define ISFS_OPEN_ALL 64
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif //__cplusplus
|
||||
bool init_uneek_fs(u32 mode);
|
||||
bool check_uneek_fs(void);
|
||||
s32 check_uneek_fs_type(void);
|
||||
bool exit_uneek_fs(void);
|
||||
bool is_neek(void);
|
||||
bool is_neek2 (bool isfsinit);
|
||||
bool is_neek3 (bool isfsinit);
|
||||
bool is_neek4 (bool isfsinit);
|
||||
bool WII_Launch_Channel(char* which);
|
||||
|
||||
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif //__cplusplus
|
||||
|
||||
#endif
|
Loading…
Reference in New Issue
Block a user