emulate firmware command 0x9F (read ID) and update test

This commit is contained in:
zeromus 2010-08-30 06:30:57 +00:00
parent e1901a2f08
commit a199a91f47
5 changed files with 230 additions and 161 deletions

View File

@ -1,6 +1,6 @@
/* Copyright (C) 2006 thoduv /* Copyright (C) 2006 thoduv
Copyright (C) 2006-2007 Theo Berkau Copyright (C) 2006-2007 Theo Berkau
Copyright (C) 2008-2009 DeSmuME team Copyright (C) 2008-2010 DeSmuME team
This file is part of DeSmuME This file is part of DeSmuME
@ -35,21 +35,22 @@
#include <xtl.h> // it`s really need? #include <xtl.h> // it`s really need?
#endif #endif
#define FW_CMD_READ 0x3 #define FW_CMD_READ 0x03
#define FW_CMD_WRITEDISABLE 0x4 #define FW_CMD_WRITEDISABLE 0x04
#define FW_CMD_READSTATUS 0x5 #define FW_CMD_READSTATUS 0x05
#define FW_CMD_WRITEENABLE 0x6 #define FW_CMD_WRITEENABLE 0x06
#define FW_CMD_PAGEWRITE 0xA #define FW_CMD_PAGEWRITE 0x0A
#define FW_CMD_READ_ID 0x9F
#define BM_CMD_AUTODETECT 0xFF #define BM_CMD_AUTODETECT 0xFF
#define BM_CMD_WRITESTATUS 0x1 #define BM_CMD_WRITESTATUS 0x01
#define BM_CMD_WRITELOW 0x2 #define BM_CMD_WRITELOW 0x02
#define BM_CMD_READLOW 0x3 #define BM_CMD_READLOW 0x03
#define BM_CMD_WRITEDISABLE 0x4 #define BM_CMD_WRITEDISABLE 0x04
#define BM_CMD_READSTATUS 0x5 #define BM_CMD_READSTATUS 0x05
#define BM_CMD_WRITEENABLE 0x6 #define BM_CMD_WRITEENABLE 0x06
#define BM_CMD_WRITEHIGH 0xA #define BM_CMD_WRITEHIGH 0x0A
#define BM_CMD_READHIGH 0xB #define BM_CMD_READHIGH 0x0B
/* FLASH*/ /* FLASH*/
#define COMM_PAGE_WRITE 0x0A #define COMM_PAGE_WRITE 0x0A
@ -228,31 +229,57 @@ u8 fw_transfer(memory_chip_t *mc, u8 data)
} }
} }
else if(mc->com == FW_CMD_READ_ID)
{
switch(mc->addr)
{
//here is an ID string measured from an old ds fat: 62 16 00 (0x62=sanyo)
//but we chose to use an ST from martin's ds fat string so programs might have a clue as to the firmware size:
//20 40 12
case 0:
data = 0x20;
mc->addr=1;
break;
case 1:
data = 0x40; //according to gbatek this is the device ID for the flash on someone's ds fat
mc->addr=2;
break;
case 2:
data = 0x12;
mc->addr = 0;
break;
}
}
else if(mc->com == FW_CMD_READSTATUS) else if(mc->com == FW_CMD_READSTATUS)
{ {
return (mc->write_enable ? 0x02 : 0x00); return (mc->write_enable ? 0x02 : 0x00);
} }
else /* finally, check if it's a new command */ else //finally, check if it's a new command
{ {
switch(data) switch(data)
{ {
case 0: break; /* nothing */ case 0: break; //nothing
case FW_CMD_READ: /* read command */ case FW_CMD_READ_ID:
mc->addr = 0;
mc->com = FW_CMD_READ_ID;
break;
case FW_CMD_READ: //read command
mc->addr = 0; mc->addr = 0;
mc->addr_shift = 3; mc->addr_shift = 3;
mc->com = FW_CMD_READ; mc->com = FW_CMD_READ;
break; break;
case FW_CMD_WRITEENABLE: /* enable writing */ case FW_CMD_WRITEENABLE: //enable writing
if(mc->writeable_buffer) { mc->write_enable = TRUE; } if(mc->writeable_buffer) { mc->write_enable = TRUE; }
break; break;
case FW_CMD_WRITEDISABLE: /* disable writing */ case FW_CMD_WRITEDISABLE: //disable writing
mc->write_enable = FALSE; mc->write_enable = FALSE;
break; break;
case FW_CMD_PAGEWRITE: /* write command */ case FW_CMD_PAGEWRITE: //write command
if(mc->write_enable) if(mc->write_enable)
{ {
mc->addr = 0; mc->addr = 0;
@ -262,7 +289,7 @@ u8 fw_transfer(memory_chip_t *mc, u8 data)
else { data = 0; } else { data = 0; }
break; break;
case FW_CMD_READSTATUS: /* status register command */ case FW_CMD_READSTATUS: //status register command
mc->com = FW_CMD_READSTATUS; mc->com = FW_CMD_READSTATUS;
break; break;

View File

@ -1,6 +1,6 @@
/* Copyright (C) 2006 thoduv /* Copyright (C) 2006 thoduv
Copyright (C) 2006 Theo Berkau Copyright (C) 2006 Theo Berkau
Copyright (C) 2008-2009 DeSmuME team Copyright (C) 2008-2010 DeSmuME team
This file is part of DeSmuME This file is part of DeSmuME
@ -50,24 +50,24 @@
#define MC_SIZE_256MBITS 0x2000000 #define MC_SIZE_256MBITS 0x2000000
#define MC_SIZE_512MBITS 0x4000000 #define MC_SIZE_512MBITS 0x4000000
typedef struct struct memory_chip_t
{ {
u8 com; /* persistent command actually handled */ u8 com; //persistent command actually handled
u32 addr; /* current address for reading/writing */ u32 addr; //current address for reading/writing
u8 addr_shift; /* shift for address (since addresses are transfered by 3 bytes units) */ u8 addr_shift; //shift for address (since addresses are transfered by 3 bytes units)
u8 addr_size; /* size of addr when writing/reading */ u8 addr_size; //size of addr when writing/reading
BOOL write_enable; /* is write enabled ? */ BOOL write_enable; //is write enabled ?
u8 *data; /* memory data */ u8 *data; //memory data
u32 size; /* memory size */ u32 size; //memory size
BOOL writeable_buffer; /* is "data" writeable ? */ BOOL writeable_buffer; //is "data" writeable ?
int type; /* type of Memory */ int type; //type of Memory
char *filename; char *filename;
FILE *fp; FILE *fp;
u8 autodetectbuf[32768]; u8 autodetectbuf[32768];
int autodetectsize; int autodetectsize;
} memory_chip_t; };
//the new backup system by zeromus //the new backup system by zeromus
class BackupDevice class BackupDevice

View File

@ -29,6 +29,7 @@ distribution.
#include <dswifi7.h> #include <dswifi7.h>
#include <maxmod7.h> #include <maxmod7.h>
#include "../../regstest.h" #include "../../regstest.h"
#include <nds/arm7/serial.h>
arm7comm_t *arm7comm; arm7comm_t *arm7comm;
@ -44,6 +45,45 @@ void VblankHandler(void) {
Wifi_Update(); Wifi_Update();
} }
//modified from: http://www.bottledlight.com/ds/index.php/Main/Firmware
#define FW_READ_ID 0x9F
#define FW_READ 0x03
#define FW_READ_STATUS 0x05
u32 getFirmwareType()
{
u32 result;
// Get ID
while (REG_SPICNT & SPI_BUSY);
REG_SPICNT = SPI_ENABLE | SPI_CONTINUOUS | SPI_DEVICE_FIRMWARE;
REG_SPIDATA = FW_READ_ID;
while (REG_SPICNT & SPI_BUSY);
result = 0;
for (int i = 0; i < 3; i++) {
REG_SPIDATA = 0;
while (REG_SPICNT & SPI_BUSY);
result = (REG_SPIDATA & 0xFF) | (result<<8);
}
// Get status
//zeromus note: this is broken. not only does it put the byte in a different spot than the docs said it does,
//it is coded otherwise glitchily and just returns bytes of the 3-Byte flash ID
//(desmume shows five reads during the ID command; apparently this code fails to reset correctly)
while (REG_SPICNT & SPI_BUSY);
REG_SPICNT = SPI_ENABLE | SPI_CONTINUOUS | SPI_DEVICE_FIRMWARE;
REG_SPIDATA = FW_READ_STATUS;
while (REG_SPICNT & SPI_BUSY);
REG_SPIDATA = 0;
while (REG_SPICNT & SPI_BUSY);
result = ((REG_SPIDATA & 0xFF) << 24) | result;
return result;
}
void pokeMessage(const char* msg) void pokeMessage(const char* msg)
{ {
const char* cp = msg; const char* cp = msg;
@ -113,7 +153,7 @@ int main() {
if(*reg != 0x00000000) fail("spu length reg is not readable!",*reg); if(*reg != 0x00000000) fail("spu length reg is not readable!",*reg);
} }
arm7comm->firmwareId = getFirmwareType();
arm7comm->code = 2; arm7comm->code = 2;
fifoSendValue32(FIFO_USER_01,0); fifoSendValue32(FIFO_USER_01,0);
while (1) swiWaitForVBlank(); while (1) swiWaitForVBlank();

View File

@ -90,6 +90,7 @@ int main(void) {
swiWaitForVBlank(); swiWaitForVBlank();
} }
iprintf("firmwareID: %08X\n",arm7comm.firmwareId);
iprintf("arm7 finish code: %d\n",arm7comm.code); iprintf("arm7 finish code: %d\n",arm7comm.code);
if(arm7comm.code == 1) if(arm7comm.code == 1)

View File

@ -1,8 +1,9 @@
typedef struct _arm7comm_t struct arm7comm_t
{ {
int code; int code;
u32 offender; u32 offender;
char message[1024]; char message[1024];
} arm7comm_t; u32 firmwareId;
};
//#define arm7comm ( (arm7comm_t*)0x02200000 ) //#define arm7comm ( (arm7comm_t*)0x02200000 )