/*---------------------------------------------------------------------------* Project: WPAD demo program File: memory.c Copyright (C) 2006 Nintendo. All rights reserved. These coded instructions, statements, and computer programs contain proprietary information of Nintendo of America Inc. and/or Nintendo Company Ltd., and are protected by Federal copyright law. They may not be disclosed to third parties or copied or duplicated in any form, in whole or in part, without the prior written consent of Nintendo. $Log: memory.c,v $ Revision 1.10.18.1 2008/08/27 04:50:20 tojo Modified the error handling of controller data. Revision 1.10 2007/04/23 09:02:52 tojo (none) Revision 1.9 2006/10/23 01:06:36 tojo Called WPADSetConnectCallback before initialization complete. Revision 1.8 2006/09/28 10:52:25 tojo (none) Revision 1.7 2006/09/23 07:13:15 tojo Changed api names Revision 1.6 2006/09/08 09:00:28 tojo (none) Revision 1.5 2006/09/05 11:30:09 tojo (none) Revision 1.4 2006/09/05 02:49:10 tojo (none) Revision 1.3 2006/09/05 02:38:35 tojo (none) Revision 1.2 2006/08/31 12:44:19 tojo (none) Revision 1.1 2006/08/16 05:05:30 tojo Initial check in. *---------------------------------------------------------------------------*/ #define DEMO_USE_MEMLIB = 1 #include #include #include #include #include #define WDATA 0 #define RDATA 1 u8 txBuf[WPAD_MAX_CONTROLLERS][WPAD_MEM_GAMEDATA_LEN]; u8 rxBuf[WPAD_MAX_CONTROLLERS][WPAD_MEM_GAMEDATA_LEN]; OSTime start[WPAD_MAX_CONTROLLERS]; OSTime end[WPAD_MAX_CONTROLLERS]; static void memory( s32 chan, u32 cmd, void *p_buf, u16 len ); /*---------------------------------------------------------------------------* * For WPAD testing *---------------------------------------------------------------------------*/ void *myAlloc( u32 size ); u8 myFree ( void *ptr ); /*---------------------------------------------------------------------------* * Name : myAlloc * Description : Callback needed by WPAD to allocate mem from MEM2 heap * Arguments : size of block, in bytes. * Returns : pointer to allocated block. *---------------------------------------------------------------------------*/ void *myAlloc( u32 size ) { void *ptr; ptr = MEMAllocFromAllocator(&DemoAllocator2, size); ASSERTMSG(ptr, "Memory allocation failed\n"); return(ptr); } /*---------------------------------------------------------------------------* * Name : myFree * Description : Callback needed by WPAD to free mem from MEM2 heap * Arguments : point to the block that should be freed. * Returns : Always 1. *---------------------------------------------------------------------------*/ u8 myFree( void *ptr ) { MEMFreeToAllocator(&DemoAllocator2, ptr); return(1); } /*---------------------------------------------------------------------------* * Name : ExtensionCallback * Description : Callback called when extension is installed/detached * Arguments : chan controller channel result device type * Returns : None. *---------------------------------------------------------------------------*/ static void ExtensionCallback( s32 chan, s32 result ) { const u32 dpd[] = {WPAD_DPD_EXP, WPAD_DPD_STD, WPAD_DPD_STD}; const u32 fmt[] = {WPAD_FMT_CORE_ACC_DPD, WPAD_FMT_FREESTYLE_ACC_DPD, WPAD_FMT_CLASSIC_ACC_DPD}; if (result == WPAD_DEV_CORE || result == WPAD_DEV_FREESTYLE || result == WPAD_DEV_CLASSIC) { WPADControlDpd (chan, dpd[result], NULL); WPADSetDataFormat(chan, fmt[result]); } } /*---------------------------------------------------------------------------* * Name : ConnectCallback * Description : Callback called when a controller connects/disconnects * Arguments : chan controller channel reason WPAD_ERR_NONE if open WPAD_ERR_NO_CONTROLLER if close * Returns : None. *---------------------------------------------------------------------------*/ static void ConnectCallback( s32 chan, s32 reason ) { OSReport("ConnectCallback(%d) : %s\n", chan, (reason < 0) ? "disconnect" : "connect"); if (reason == WPAD_ERR_NONE) { WPADSetExtensionCallback( chan, ExtensionCallback ); WPADControlDpd(chan, WPAD_DPD_EXP, NULL); WPADSetDataFormat(chan, WPAD_FMT_CORE_ACC_DPD); } } /*---------------------------------------------------------------------------* * Name : ReadCallback * Description : Callback called when reading is done. * Arguments : chan controller channel result result code * Returns : None. *---------------------------------------------------------------------------*/ static void ReadCallback( s32 chan, s32 result ) { u32 ms; OSTime t; OSCalendarTime ct; const u16 *p_name; u8 title[16]; s32 len = 16; end[chan] = OSGetTime(); ms = OSTicksToMilliseconds(OSDiffTick(end[chan], start[chan])); OSReport("chan[%d] result ==> err = %d, bytes: %d, time(ms): %d\n", chan, result, WPAD_MEM_GAMEDATA_LEN, ms); WPADGetGameTitleUtf16(chan, &p_name); WPADGetGameDataTimeStamp(chan, &t); ENCConvertStringUtf16ToUtf8(title, &len, p_name, &len); OSTicksToCalendarTime(t, &ct); OSReport("Title : %s, TimeStamp : %d/%d/%d %02d:%02d:%02d\n", title, ct.year, ct.mon+1, ct.mday, ct.hour, ct.min, ct.sec); if (!memcmp(txBuf[chan], rxBuf[chan], WPAD_MEM_GAMEDATA_LEN)) { OSReport("\n == OK == \n\n"); } else { OSReport("\n == NG == \n\n"); } } /*---------------------------------------------------------------------------* * Name : WriteCallback * Description : Callback called when writing is done. * Arguments : chan controller channel result result code * Returns : None. *---------------------------------------------------------------------------*/ static void WriteCallback( s32 chan, s32 result ) { u32 ms; end[chan] = OSGetTime(); ms = OSTicksToMilliseconds(OSDiffTick(end[chan], start[chan])); OSReport("chan[%d] result ==> err = %d, bytes: %d, time(ms): %d\n", chan, result, WPAD_MEM_GAMEDATA_LEN, ms); memory(chan, RDATA, rxBuf[chan], WPAD_MEM_GAMEDATA_LEN); } /*---------------------------------------------------------------------------* * Name : memory * Description : Performs reading/writing user data * Arguments : chan controller channel cmd read or write p_buf point to the data buffer len data length * Returns : None. *---------------------------------------------------------------------------*/ static void memory( s32 chan, u32 cmd, void *p_buf, u16 len ) { s32 result; const char *funcName[] = { "WPADWriteGameData", "WPADReadGameData", }; switch(cmd) { case WDATA: result = WPADWriteGameData(chan, p_buf, len, 0, WriteCallback); break; case RDATA: result = WPADReadGameData (chan, p_buf, len, 0, ReadCallback); break; } if (result == WPAD_ERR_NONE) { start[chan] = OSGetTime(); } OSReport("chan[%d] %s : %d\n", chan, funcName[cmd], result); } /*---------------------------------------------------------------------------* * Name : PrintIntro * Description : Print introduction * Arguments : None. * Returns : None. *---------------------------------------------------------------------------*/ static void PrintIntro( void ) { OSReport("+------------ WPADMEM Sample Demo Program ------------+\n"); OSReport(" This is a demo program to access embedded memory \n"); OSReport(" of Wii remote controller assigned to WPAD_CHAN0. \n"); OSReport("+-----------------------------------------------------+\n"); OSReport(" MENU: \n"); OSReport(" A button: Write game data to Wii remote controller\n"); OSReport(" B button: Read game data from Wii remote controller\n"); OSReport("+-----------------------------------------------------+\n"); } /*---------------------------------------------------------------------------* * Name : main * Description : * Arguments : None. * Returns : None. *---------------------------------------------------------------------------*/ void main( void ) { s32 bb_stat; u32 type; s32 chan; int i; u16 curr[WPAD_MAX_CONTROLLERS] = {0, 0, 0, 0}; u16 prev[WPAD_MAX_CONTROLLERS] = {0, 0, 0, 0}; WPADStatus status[WPAD_MAX_CONTROLLERS]; const char *utf8_title = { "Wii Sample Demo" }; // UTF-8 u16 utf16_title[16]; s32 len = (s32)strlen(utf8_title); OSInit(); DEMOInit( NULL ); // register allocator for stack before WPADInit(). WPADRegisterAllocator(myAlloc, myFree); // Initialize WPAD. WPADInit(); for(i=0;i