Added ARM CPU to memory system interface.

This commit is contained in:
masscat 2007-06-07 09:56:12 +00:00
parent 6886803593
commit 35168b3e01
8 changed files with 1721 additions and 969 deletions

View File

@ -39,6 +39,15 @@
#define ROM_MASK 3
/*
*
*/
//#define PROFILE_MEMORY_ACCESS 1
#define EARLY_MEMORY_ACCESS 1
#define INTERNAL_DTCM_READ 1
#define INTERNAL_DTCM_WRITE 1
//#define LOG_CARD
//#define LOG_GPU
//#define LOG_DMA
@ -551,10 +560,12 @@ char txt[80];
u8 FASTCALL MMU_read8(u32 proc, u32 adr)
{
#ifdef INTERNAL_DTCM_READ
if((proc==ARMCPU_ARM9)&((adr&(~0x3FFF))==MMU.DTCMRegion))
{
return ARM9Mem.ARM9_DTCM[adr&0x3FFF];
}
#endif
// CFlash reading, Mic
if ((adr>=0x9000000)&&(adr<0x9900000))
@ -578,11 +589,13 @@ u8 FASTCALL MMU_read8(u32 proc, u32 adr)
u16 FASTCALL MMU_read16(u32 proc, u32 adr)
{
#ifdef INTERNAL_DTCM_READ
if((proc == ARMCPU_ARM9) && ((adr & ~0x3FFF) == MMU.DTCMRegion))
{
/* Returns data from DTCM (ARM9 only) */
return T1ReadWord(ARM9Mem.ARM9_DTCM, adr & 0x3FFF);
}
#endif
// CFlash reading, Mic
if ((adr>=0x08800000)&&(adr<0x09900000))
@ -646,11 +659,13 @@ u16 FASTCALL MMU_read16(u32 proc, u32 adr)
u32 FASTCALL MMU_read32(u32 proc, u32 adr)
{
#ifdef INTERNAL_DTCM_READ
if((proc == ARMCPU_ARM9) && ((adr & ~0x3FFF) == MMU.DTCMRegion))
{
/* Returns data from DTCM (ARM9 only) */
return T1ReadLong(ARM9Mem.ARM9_DTCM, adr & 0x3FFF);
}
#endif
// CFlash reading, Mic
if ((adr>=0x9000000)&&(adr<0x9900000))
@ -806,12 +821,14 @@ u32 FASTCALL MMU_read32(u32 proc, u32 adr)
void FASTCALL MMU_write8(u32 proc, u32 adr, u8 val)
{
#ifdef INTERNAL_DTCM_WRITE
if((proc == ARMCPU_ARM9) && ((adr & ~0x3FFF) == MMU.DTCMRegion))
{
/* Writes data in DTCM (ARM9 only) */
ARM9Mem.ARM9_DTCM[adr&0x3FFF] = val;
return ;
}
#endif
// CFlash writing, Mic
if ((adr>=0x9000000)&&(adr<0x9900000)) {
@ -1178,12 +1195,14 @@ u16 partie = 1;
void FASTCALL MMU_write16(u32 proc, u32 adr, u16 val)
{
#ifdef INTERNAL_DTCM_WRITE
if((proc == ARMCPU_ARM9) && ((adr & ~0x3FFF) == MMU.DTCMRegion))
{
/* Writes in DTCM (ARM9 only) */
T1WriteWord(ARM9Mem.ARM9_DTCM, adr & 0x3FFF, val);
return;
}
#endif
// CFlash writing, Mic
if ((adr>=0x08800000)&&(adr<0x09900000))
@ -1797,11 +1816,13 @@ void FASTCALL MMU_write16(u32 proc, u32 adr, u16 val)
void FASTCALL MMU_write32(u32 proc, u32 adr, u32 val)
{
#ifdef INTERNAL_DTCM_WRITE
if((proc==ARMCPU_ARM9)&((adr&(~0x3FFF))==MMU.DTCMRegion))
{
T1WriteLong(ARM9Mem.ARM9_DTCM, adr & 0x3FFF, val);
return ;
}
#endif
// CFlash writing, Mic
if ((adr>=0x9000000)&&(adr<0x9900000)) {
@ -2974,3 +2995,493 @@ void FASTCALL MMU_write32_acl(u32 proc, u32 adr, u32 val)
}
#endif
#ifdef PROFILE_MEMORY_ACCESS
#define PROFILE_PREFETCH 0
#define PROFILE_READ 1
#define PROFILE_WRITE 2
struct mem_access_profile {
u64 num_accesses;
u32 address_mask;
u32 masked_value;
};
#define PROFILE_NUM_MEM_ACCESS_PROFILES 4
static u64 profile_num_accesses[2][3];
static u64 profile_unknown_addresses[2][3];
static struct mem_access_profile
profile_memory_accesses[2][3][PROFILE_NUM_MEM_ACCESS_PROFILES];
static void
setup_profiling( void) {
int i;
for ( i = 0; i < 2; i++) {
int access_type;
for ( access_type = 0; access_type < 3; access_type++) {
profile_num_accesses[i][access_type] = 0;
profile_unknown_addresses[i][access_type] = 0;
/*
* Setup the access testing structures
*/
profile_memory_accesses[i][access_type][0].address_mask = 0x0e000000;
profile_memory_accesses[i][access_type][0].masked_value = 0x00000000;
profile_memory_accesses[i][access_type][0].num_accesses = 0;
/* main memory */
profile_memory_accesses[i][access_type][1].address_mask = 0x0f000000;
profile_memory_accesses[i][access_type][1].masked_value = 0x02000000;
profile_memory_accesses[i][access_type][1].num_accesses = 0;
/* shared memory */
profile_memory_accesses[i][access_type][2].address_mask = 0x0f800000;
profile_memory_accesses[i][access_type][2].masked_value = 0x03000000;
profile_memory_accesses[i][access_type][2].num_accesses = 0;
/* arm7 memory */
profile_memory_accesses[i][access_type][3].address_mask = 0x0f800000;
profile_memory_accesses[i][access_type][3].masked_value = 0x03800000;
profile_memory_accesses[i][access_type][3].num_accesses = 0;
}
}
}
static void
profile_memory_access( int arm9, u32 adr, int access_type) {
static int first = 1;
int mem_profile;
int address_found = 0;
if ( first) {
setup_profiling();
first = 0;
}
profile_num_accesses[arm9][access_type] += 1;
for ( mem_profile = 0;
mem_profile < PROFILE_NUM_MEM_ACCESS_PROFILES &&
!address_found;
mem_profile++) {
if ( (adr & profile_memory_accesses[arm9][access_type][mem_profile].address_mask) ==
profile_memory_accesses[arm9][access_type][mem_profile].masked_value) {
/*printf( "adr %08x mask %08x res %08x expected %08x\n",
adr,
profile_memory_accesses[arm9][access_type][mem_profile].address_mask,
adr & profile_memory_accesses[arm9][access_type][mem_profile].address_mask,
profile_memory_accesses[arm9][access_type][mem_profile].masked_value);*/
address_found = 1;
profile_memory_accesses[arm9][access_type][mem_profile].num_accesses += 1;
}
}
if ( !address_found) {
profile_unknown_addresses[arm9][access_type] += 1;
}
}
static const char *access_type_strings[] = {
"prefetch",
"read ",
"write "
};
void
print_memory_profiling( void) {
int arm;
printf("------ Memory access profile ------\n");
for ( arm = 0; arm < 2; arm++) {
int access_type;
for ( access_type = 0; access_type < 3; access_type++) {
int mem_profile;
printf("ARM%c: num of %s %lld\n",
arm ? '9' : '7',
access_type_strings[access_type],
profile_num_accesses[arm][access_type]);
for ( mem_profile = 0;
mem_profile < PROFILE_NUM_MEM_ACCESS_PROFILES;
mem_profile++) {
printf( "address %08x: %lld\n",
profile_memory_accesses[arm][access_type][mem_profile].masked_value,
profile_memory_accesses[arm][access_type][mem_profile].num_accesses);
}
printf( "unknown addresses %lld\n",
profile_unknown_addresses[arm][access_type]);
printf( "\n");
}
}
printf("------ End of Memory access profile ------\n\n");
}
#else
void
print_memory_profiling( void) {
}
#endif /* End of PROFILE_MEMORY_ACCESS area */
static u16 FASTCALL
arm9_prefetch16( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 1, adr, PROFILE_PREFETCH);
#endif
#ifdef EARLY_MEMORY_ACCESS
if((adr & ~0x3FFF) == MMU.DTCMRegion)
{
/* Returns data from DTCM (ARM9 only) */
return T1ReadWord(ARM9Mem.ARM9_DTCM, adr & 0x3FFF);
}
/* access to main memory */
if ( (adr & 0x0f000000) == 0x02000000) {
return T1ReadWord( MMU.MMU_MEM[ARMCPU_ARM9][(adr >> 20) & 0xFF],
adr & MMU.MMU_MASK[ARMCPU_ARM9][(adr >> 20) & 0xFF]);
}
#endif
return MMU_read16( ARMCPU_ARM9, adr);
}
static u32 FASTCALL
arm9_prefetch32( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 1, adr, PROFILE_PREFETCH);
#endif
#ifdef EARLY_MEMORY_ACCESS
if((adr & ~0x3FFF) == MMU.DTCMRegion)
{
/* Returns data from DTCM (ARM9 only) */
return T1ReadLong(ARM9Mem.ARM9_DTCM, adr & 0x3FFF);
}
/* access to main memory */
if ( (adr & 0x0f000000) == 0x02000000) {
return T1ReadLong( MMU.MMU_MEM[ARMCPU_ARM9][(adr >> 20) & 0xFF],
adr & MMU.MMU_MASK[ARMCPU_ARM9][(adr >> 20) & 0xFF]);
}
#endif
return MMU_read32( ARMCPU_ARM9, adr);
}
static u8 FASTCALL
arm9_read8( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 1, adr, PROFILE_READ);
#endif
#ifdef EARLY_MEMORY_ACCESS
if( (adr&(~0x3FFF)) == MMU.DTCMRegion)
{
return ARM9Mem.ARM9_DTCM[adr&0x3FFF];
}
/* access to main memory */
if ( (adr & 0x0f000000) == 0x02000000) {
return MMU.MMU_MEM[ARMCPU_ARM9][(adr >> 20) & 0xFF]
[adr & MMU.MMU_MASK[ARMCPU_ARM9][(adr >> 20) & 0xFF]];
}
#endif
return MMU_read8( ARMCPU_ARM9, adr);
}
static u16 FASTCALL
arm9_read16( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 1, adr, PROFILE_READ);
#endif
#ifdef EARLY_MEMORY_ACCESS
if((adr & ~0x3FFF) == MMU.DTCMRegion)
{
/* Returns data from DTCM (ARM9 only) */
return T1ReadWord(ARM9Mem.ARM9_DTCM, adr & 0x3FFF);
}
/* access to main memory */
if ( (adr & 0x0f000000) == 0x02000000) {
return T1ReadWord( MMU.MMU_MEM[ARMCPU_ARM9][(adr >> 20) & 0xFF],
adr & MMU.MMU_MASK[ARMCPU_ARM9][(adr >> 20) & 0xFF]);
}
#endif
return MMU_read16( ARMCPU_ARM9, adr);
}
static u32 FASTCALL
arm9_read32( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 1, adr, PROFILE_READ);
#endif
#ifdef EARLY_MEMORY_ACCESS
if((adr & ~0x3FFF) == MMU.DTCMRegion)
{
/* Returns data from DTCM (ARM9 only) */
return T1ReadLong(ARM9Mem.ARM9_DTCM, adr & 0x3FFF);
}
/* access to main memory */
if ( (adr & 0x0f000000) == 0x02000000) {
return T1ReadLong( MMU.MMU_MEM[ARMCPU_ARM9][(adr >> 20) & 0xFF],
adr & MMU.MMU_MASK[ARMCPU_ARM9][(adr >> 20) & 0xFF]);
}
#endif
return MMU_read32( ARMCPU_ARM9, adr);
}
static void FASTCALL
arm9_write8(void *data, u32 adr, u8 val) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 1, adr, PROFILE_WRITE);
#endif
#ifdef EARLY_MEMORY_ACCESS
if( (adr & ~0x3FFF) == MMU.DTCMRegion)
{
/* Writes data in DTCM (ARM9 only) */
ARM9Mem.ARM9_DTCM[adr&0x3FFF] = val;
return ;
}
/* main memory */
if ( (adr & 0x0f000000) == 0x02000000) {
MMU.MMU_MEM[ARMCPU_ARM9][(adr>>20)&0xFF]
[adr&MMU.MMU_MASK[ARMCPU_ARM9][(adr>>20)&0xFF]] = val;
return;
}
#endif
MMU_write8( ARMCPU_ARM9, adr, val);
}
static void FASTCALL
arm9_write16(void *data, u32 adr, u16 val) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 1, adr, PROFILE_WRITE);
#endif
#ifdef EARLY_MEMORY_ACCESS
if((adr & ~0x3FFF) == MMU.DTCMRegion)
{
/* Writes in DTCM (ARM9 only) */
T1WriteWord(ARM9Mem.ARM9_DTCM, adr & 0x3FFF, val);
return;
}
/* main memory */
if ( (adr & 0x0f000000) == 0x02000000) {
T1WriteWord( MMU.MMU_MEM[ARMCPU_ARM9][(adr>>20)&0xFF],
adr&MMU.MMU_MASK[ARMCPU_ARM9][(adr>>20)&0xFF], val);
return;
}
#endif
MMU_write16( ARMCPU_ARM9, adr, val);
}
static void FASTCALL
arm9_write32(void *data, u32 adr, u32 val) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 1, adr, PROFILE_WRITE);
#endif
#ifdef EARLY_MEMORY_ACCESS
if((adr & ~0x3FFF) == MMU.DTCMRegion)
{
/* Writes in DTCM (ARM9 only) */
T1WriteLong(ARM9Mem.ARM9_DTCM, adr & 0x3FFF, val);
return;
}
/* main memory */
if ( (adr & 0x0f000000) == 0x02000000) {
T1WriteLong( MMU.MMU_MEM[ARMCPU_ARM9][(adr>>20)&0xFF],
adr&MMU.MMU_MASK[ARMCPU_ARM9][(adr>>20)&0xFF], val);
return;
}
#endif
MMU_write32( ARMCPU_ARM9, adr, val);
}
static u16 FASTCALL
arm7_prefetch16( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 0, adr, PROFILE_PREFETCH);
#endif
#ifdef EARLY_MEMORY_ACCESS
/* ARM7 private memory */
if ( (adr & 0x0f800000) == 0x03800000) {
T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM7][(adr >> 20) & 0xFF],
adr & MMU.MMU_MASK[ARMCPU_ARM7][(adr >> 20) & 0xFF]);
}
#endif
return MMU_read16( ARMCPU_ARM7, adr);
}
static u32 FASTCALL
arm7_prefetch32( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 0, adr, PROFILE_PREFETCH);
#endif
#ifdef EARLY_MEMORY_ACCESS
/* ARM7 private memory */
if ( (adr & 0x0f800000) == 0x03800000) {
T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM7][(adr >> 20) & 0xFF],
adr & MMU.MMU_MASK[ARMCPU_ARM7][(adr >> 20) & 0xFF]);
}
#endif
return MMU_read32( ARMCPU_ARM7, adr);
}
static u8 FASTCALL
arm7_read8( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 0, adr, PROFILE_READ);
#endif
return MMU_read8( ARMCPU_ARM7, adr);
}
static u16 FASTCALL
arm7_read16( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 0, adr, PROFILE_READ);
#endif
return MMU_read16( ARMCPU_ARM7, adr);
}
static u32 FASTCALL
arm7_read32( void *data, u32 adr) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 0, adr, PROFILE_READ);
#endif
return MMU_read32( ARMCPU_ARM7, adr);
}
static void FASTCALL
arm7_write8(void *data, u32 adr, u8 val) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 0, adr, PROFILE_WRITE);
#endif
MMU_write8( ARMCPU_ARM7, adr, val);
}
static void FASTCALL
arm7_write16(void *data, u32 adr, u16 val) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 0, adr, PROFILE_WRITE);
#endif
MMU_write16( ARMCPU_ARM7, adr, val);
}
static void FASTCALL
arm7_write32(void *data, u32 adr, u32 val) {
#ifdef PROFILE_MEMORY_ACCESS
profile_memory_access( 0, adr, PROFILE_WRITE);
#endif
MMU_write32( ARMCPU_ARM7, adr, val);
}
/*
* the base memory interfaces
*/
struct armcpu_memory_iface arm9_base_memory_iface = {
#ifdef __GNUC__
.prefetch32 = arm9_prefetch32,
.prefetch16 = arm9_prefetch16,
.read8 = arm9_read8,
.read16 = arm9_read16,
.read32 = arm9_read32,
.write8 = arm9_write8,
.write16 = arm9_write16,
.write32 = arm9_write32
#else
arm9_prefetch32,
arm9_prefetch16,
arm9_read8,
arm9_read16,
arm9_read32,
arm9_write8,
arm9_write16,
arm9_write32
#endif
};
struct armcpu_memory_iface arm7_base_memory_iface = {
#ifdef __GNUC__
.prefetch32 = arm7_prefetch32,
.prefetch16 = arm7_prefetch16,
.read8 = arm7_read8,
.read16 = arm7_read16,
.read32 = arm7_read32,
.write8 = arm7_write8,
.write16 = arm7_write16,
.write32 = arm7_write32
#else
arm7_prefetch32,
arm7_prefetch16,
arm7_read8,
arm7_read16,
arm7_read32,
arm7_write8,
arm7_write16,
arm7_write32
#endif
};
/*
* The direct memory interface for the ARM9.
* This avoids the ARM9 protection unit when accessing
* memory.
*/
struct armcpu_memory_iface arm9_direct_memory_iface = {
#ifdef __GNUC__
/* the prefetch is not used */
.prefetch32 = NULL,
.prefetch16 = NULL,
.read8 = arm9_read8,
.read16 = arm9_read16,
.read32 = arm9_read32,
.write8 = arm9_write8,
.write16 = arm9_write16,
.write32 = arm9_write32
#else
NULL,
NULL,
arm9_read8,
arm9_read16,
arm9_read32,
arm9_write8,
arm9_write16,
arm9_write32
#endif
};

View File

@ -104,6 +104,32 @@ typedef struct {
extern MMU_struct MMU;
struct armcpu_memory_iface {
/** the 32 bit instruction prefetch */
u32 FASTCALL (*prefetch32)( void *data, u32 adr);
/** the 16 bit instruction prefetch */
u16 FASTCALL (*prefetch16)( void *data, u32 adr);
/** read 8 bit data value */
u8 FASTCALL (*read8)( void *data, u32 adr);
/** read 16 bit data value */
u16 FASTCALL (*read16)( void *data, u32 adr);
/** read 32 bit data value */
u32 FASTCALL (*read32)( void *data, u32 adr);
/** write 8 bit data value */
void FASTCALL (*write8)( void *data, u32 adr, u8 val);
/** write 16 bit data value */
void FASTCALL (*write16)( void *data, u32 adr, u16 val);
/** write 32 bit data value */
void FASTCALL (*write32)( void *data, u32 adr, u32 val);
void *data;
};
static void mmu_select_savetype(int type, int *bmemtype, u32 *bmemsize) {
if (type<0 || type > 5) return;
*bmemtype=save_types[type][0];
@ -164,6 +190,15 @@ void FASTCALL MMU_writeXX(u32 proc, u32 adr, u32 val, u8 nbbytes);
void FASTCALL MMU_doDMA(u32 proc, u32 num);
/*
* The base ARM memory interfaces
*/
extern struct armcpu_memory_iface arm9_base_memory_iface;
extern struct armcpu_memory_iface arm7_base_memory_iface;
extern struct armcpu_memory_iface arm9_direct_memory_iface;
#ifdef __cplusplus
}
#endif

View File

@ -26,6 +26,8 @@
#include "MMU.h"
#include "cflash.h"
#include "MMU.h"
#include "cflash.h"
#include "ROMReader.h"
NDSSystem nds;
@ -56,7 +58,10 @@ calc_CRC16( u32 start, u8 *data, int count) {
return crc;
}
int NDS_Init(void) {
int NDS_Init( struct armcpu_memory_iface *arm9_mem_if,
struct armcpu_ctrl_iface **arm9_ctrl_iface,
struct armcpu_memory_iface *arm7_mem_if,
struct armcpu_ctrl_iface **arm7_ctrl_iface) {
nds.ARM9Cycle = 0;
nds.ARM7Cycle = 0;
nds.cycles = 0;
@ -68,8 +73,8 @@ int NDS_Init(void) {
if (Screen_Init(GFXCORE_DUMMY) != 0)
return -1;
armcpu_new(&NDS_ARM7,1);
armcpu_new(&NDS_ARM9,0);
armcpu_new(&NDS_ARM7,1, arm7_mem_if, arm7_ctrl_iface);
armcpu_new(&NDS_ARM9,0, arm9_mem_if, arm9_ctrl_iface);
if (SPU_Init(SNDCORE_DUMMY, 735) != 0)
return -1;
@ -212,7 +217,8 @@ enum
ROM_DSGBA
};
int NDS_LoadROM(const char *filename, int bmtype, u32 bmsize)
int NDS_LoadROM( const char *filename, int bmtype, u32 bmsize,
const char *cflash_disk_image_file)
{
int i;
int type;
@ -283,7 +289,7 @@ int NDS_LoadROM(const char *filename, int bmtype, u32 bmsize)
* so the current one should be ok */
strncpy(szRomPath, ".", 512); /* "." is shorter then 512, yet strcpy should be avoided */
cflash_close();
cflash_init();
cflash_init( cflash_disk_image_file);
strncpy(szRomBaseName, filename,512);
@ -742,3 +748,656 @@ int NDS_LoadFirmware(const char *filename)
return i;
}
#define INDEX(i) ((((i)>>16)&0xFF0)|(((i)>>4)&0xF))
u32
NDS_exec(s32 nb, BOOL force)
{
nb += nds.cycles;//(nds.cycles>>26)<<26;
for(; (nb >= nds.cycles) && ((force)||(execute)); )
{
if(nds.ARM9Cycle<=nds.cycles)
{
#ifdef LOG_ARM9
if(logcount==3){
if(NDS_ARM9.CPSR.bits.T)
des_thumb_instructions_set[(NDS_ARM9.instruction)>>6](NDS_ARM9.instruct_adr, NDS_ARM9.instruction, logbuf);
else
des_arm_instructions_set[INDEX(NDS_ARM9.instruction)](NDS_ARM9.instruct_adr, NDS_ARM9.instruction, logbuf);
sprintf(logbuf, "%s\t%08X\n\t R00: %08X, R01: %08X, R02: %08X, R03: %08X, R04: %08X, R05: %08X, R06: %08X, R07: %08X,\n\t R08: %08X, R09: %08X, R10: %08X, R11: %08X, R12: %08X, R13: %08X, R14: %08X, R15: %08X,\n\t CPSR: %08X , SPSR: %08X",
logbuf, NDS_ARM9.instruction, NDS_ARM9.R[0], NDS_ARM9.R[1], NDS_ARM9.R[2], NDS_ARM9.R[3], NDS_ARM9.R[4], NDS_ARM9.R[5], NDS_ARM9.R[6], NDS_ARM9.R[7],
NDS_ARM9.R[8], NDS_ARM9.R[9], NDS_ARM9.R[10], NDS_ARM9.R[11], NDS_ARM9.R[12], NDS_ARM9.R[13], NDS_ARM9.R[14], NDS_ARM9.R[15],
NDS_ARM9.CPSR, NDS_ARM9.SPSR);
LOG(logbuf);
}
#endif
if(NDS_ARM9.waitIRQ)
nds.ARM9Cycle += 100;
else
//nds.ARM9Cycle += NDS_ARM9.exec();
nds.ARM9Cycle += armcpu_exec(&NDS_ARM9);
}
#ifdef EXPERIMENTAL_WIFI
if((nds.ARM7Cycle % 0x3F03) == 0)
{
/* 3F03 arm7 cyles = ~1usec */
WIFI_usTrigger(&wifiMac) ;
}
#endif
if(nds.ARM7Cycle<=nds.cycles)
{
#ifdef LOG_ARM7
if(logcount==1){
if(NDS_ARM7.CPSR.bits.T)
des_thumb_instructions_set[(NDS_ARM7.instruction)>>6](NDS_ARM7.instruct_adr, NDS_ARM7.instruction, logbuf);
else
des_arm_instructions_set[INDEX(NDS_ARM7.instruction)](NDS_ARM7.instruct_adr, NDS_ARM7.instruction, logbuf);
sprintf(logbuf, "%s\n\t R00: %08X, R01: %08X, R02: %08X, R03: %08X, R04: %08X, R05: %08X, R06: %08X, R07: %08X,\n\t R08: %08X, R09: %08X, R10: %08X, R11: %08X, R12: %08X, R13: %08X, R14: %08X, R15: %08X,\n\t CPSR: %08X , SPSR: %08X",
logbuf, NDS_ARM7.R[0], NDS_ARM7.R[1], NDS_ARM7.R[2], NDS_ARM7.R[3], NDS_ARM7.R[4], NDS_ARM7.R[5], NDS_ARM7.R[6], NDS_ARM7.R[7],
NDS_ARM7.R[8], NDS_ARM7.R[9], NDS_ARM7.R[10], NDS_ARM7.R[11], NDS_ARM7.R[12], NDS_ARM7.R[13], NDS_ARM7.R[14], NDS_ARM7.R[15],
NDS_ARM7.CPSR, NDS_ARM7.SPSR);
LOG(logbuf);
}
#endif
if(NDS_ARM7.waitIRQ)
nds.ARM7Cycle += 100;
else
//nds.ARM7Cycle += (NDS_ARM7.exec()<<1);
nds.ARM7Cycle += (armcpu_exec(&NDS_ARM7)<<1);
}
nds.cycles = (nds.ARM9Cycle<nds.ARM7Cycle)?nds.ARM9Cycle : nds.ARM7Cycle;
//debug();
if(nds.cycles>=nds.nextHBlank)
{
if(!nds.lignerendu)
{
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) | 2);
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) | 2);
NDS_ARM9HBlankInt();
NDS_ARM7HBlankInt();
if(nds.VCount<192)
{
GPU_ligne(&MainScreen, nds.VCount);
GPU_ligne(&SubScreen, nds.VCount);
if(MMU.DMAStartTime[0][0] == 2)
MMU_doDMA(0, 0);
if(MMU.DMAStartTime[0][1] == 2)
MMU_doDMA(0, 1);
if(MMU.DMAStartTime[0][2] == 2)
MMU_doDMA(0, 2);
if(MMU.DMAStartTime[0][3] == 2)
MMU_doDMA(0, 3);
}
nds.lignerendu = TRUE;
}
if(nds.cycles>=nds.nextHBlank+1092)
{
u32 vmatch;
++nds.VCount;
nds.nextHBlank += 4260;
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) & 0xFFFD);
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) & 0xFFFD);
if(MMU.DMAStartTime[0][0] == 3)
MMU_doDMA(0, 0);
if(MMU.DMAStartTime[0][1] == 3)
MMU_doDMA(0, 1);
if(MMU.DMAStartTime[0][2] == 3)
MMU_doDMA(0, 2);
if(MMU.DMAStartTime[0][3] == 3)
MMU_doDMA(0, 3);
// Main memory display
if(MMU.DMAStartTime[0][0] == 4)
{
MMU_doDMA(0, 0);
MMU.DMAStartTime[0][0] = 0;
}
if(MMU.DMAStartTime[0][1] == 4)
{
MMU_doDMA(0, 1);
MMU.DMAStartTime[0][1] = 0;
}
if(MMU.DMAStartTime[0][2] == 4)
{
MMU_doDMA(0, 2);
MMU.DMAStartTime[0][2] = 0;
}
if(MMU.DMAStartTime[0][3] == 4)
{
MMU_doDMA(0, 3);
MMU.DMAStartTime[0][3] = 0;
}
if(MMU.DMAStartTime[1][0] == 4)
{
MMU_doDMA(1, 0);
MMU.DMAStartTime[1][0] = 0;
}
if(MMU.DMAStartTime[1][1] == 4)
{
MMU_doDMA(1, 1);
MMU.DMAStartTime[0][1] = 0;
}
if(MMU.DMAStartTime[1][2] == 4)
{
MMU_doDMA(1, 2);
MMU.DMAStartTime[1][2] = 0;
}
if(MMU.DMAStartTime[1][3] == 4)
{
MMU_doDMA(1, 3);
MMU.DMAStartTime[1][3] = 0;
}
nds.lignerendu = FALSE;
if(nds.VCount==192)
{
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) | 1);
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) | 1);
NDS_ARM9VBlankInt();
NDS_ARM7VBlankInt();
if(MMU.DMAStartTime[0][0] == 1)
MMU_doDMA(0, 0);
if(MMU.DMAStartTime[0][1] == 1)
MMU_doDMA(0, 1);
if(MMU.DMAStartTime[0][2] == 1)
MMU_doDMA(0, 2);
if(MMU.DMAStartTime[0][3] == 1)
MMU_doDMA(0, 3);
if(MMU.DMAStartTime[1][0] == 1)
MMU_doDMA(1, 0);
if(MMU.DMAStartTime[1][1] == 1)
MMU_doDMA(1, 1);
if(MMU.DMAStartTime[1][2] == 1)
MMU_doDMA(1, 2);
if(MMU.DMAStartTime[1][3] == 1)
MMU_doDMA(1, 3);
}
else
if(nds.VCount==263)
{
nds.nextHBlank = 3168;
nds.VCount = 0;
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) & 0xFFFE);
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) & 0xFFFE);
nds.cycles -= (560190<<1);
nds.ARM9Cycle -= (560190<<1);
nds.ARM7Cycle -= (560190<<1);
nb -= (560190<<1);
if(MMU.timerON[0][0])
nds.timerCycle[0][0] -= (560190<<1);
if(MMU.timerON[0][1])
nds.timerCycle[0][1] -= (560190<<1);
if(MMU.timerON[0][2])
nds.timerCycle[0][2] -= (560190<<1);
if(MMU.timerON[0][3])
nds.timerCycle[0][3] -= (560190<<1);
if(MMU.timerON[1][0])
nds.timerCycle[1][0] -= (560190<<1);
if(MMU.timerON[1][1])
nds.timerCycle[1][1] -= (560190<<1);
if(MMU.timerON[1][2])
nds.timerCycle[1][2] -= (560190<<1);
if(MMU.timerON[1][3])
nds.timerCycle[1][3] -= (560190<<1);
if(MMU.DMAing[0][0])
MMU.DMACycle[0][0] -= (560190<<1);
if(MMU.DMAing[0][1])
MMU.DMACycle[0][1] -= (560190<<1);
if(MMU.DMAing[0][2])
MMU.DMACycle[0][2] -= (560190<<1);
if(MMU.DMAing[0][3])
MMU.DMACycle[0][3] -= (560190<<1);
if(MMU.DMAing[1][0])
MMU.DMACycle[1][0] -= (560190<<1);
if(MMU.DMAing[1][1])
MMU.DMACycle[1][1] -= (560190<<1);
if(MMU.DMAing[1][2])
MMU.DMACycle[1][2] -= (560190<<1);
if(MMU.DMAing[1][3])
MMU.DMACycle[1][3] -= (560190<<1);
}
T1WriteWord(ARM9Mem.ARM9_REG, 6, nds.VCount);
T1WriteWord(MMU.ARM7_REG, 6, nds.VCount);
vmatch = T1ReadWord(ARM9Mem.ARM9_REG, 4);
if((nds.VCount==(vmatch>>8)|((vmatch<<1)&(1<<8))))
{
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) | 4);
if(T1ReadWord(ARM9Mem.ARM9_REG, 4) & 32)
NDS_makeARM9Int(2);
}
else
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) & 0xFFFB);
vmatch = T1ReadWord(MMU.ARM7_REG, 4);
if((nds.VCount==(vmatch>>8)|((vmatch<<1)&(1<<8))))
{
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) | 4);
if(T1ReadWord(MMU.ARM7_REG, 4) & 32)
NDS_makeARM7Int(2);
}
else
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) & 0xFFFB);
}
}
/* assume the timers have not expired */
nds.timerOver[0][0] = 0;
nds.timerOver[0][1] = 0;
nds.timerOver[0][2] = 0;
nds.timerOver[0][3] = 0;
nds.timerOver[1][0] = 0;
nds.timerOver[1][1] = 0;
nds.timerOver[1][2] = 0;
nds.timerOver[1][3] = 0;
if(MMU.timerON[0][0])
{
if(MMU.timerRUN[0][0])
{
switch(MMU.timerMODE[0][0])
{
case 0xFFFF :
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[0][0])>>MMU.timerMODE[0][0];
nds.old = MMU.timer[0][0];
MMU.timer[0][0] += nds.diff;
nds.timerCycle[0][0] += (nds.diff << MMU.timerMODE[0][0]);
nds.timerOver[0][0] = nds.old>MMU.timer[0][0];
if(nds.timerOver[0][0])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x102) & 0x40)
NDS_makeARM9Int(3);
MMU.timer[0][0] = MMU.timerReload[0][0];
}
}
break;
}
}
else
{
MMU.timerRUN[0][0] = TRUE;
nds.timerCycle[0][0] = nds.cycles;
}
}
if(MMU.timerON[0][1])
{
if(MMU.timerRUN[0][1])
{
switch(MMU.timerMODE[0][1])
{
case 0xFFFF :
if(nds.timerOver[0][0])
{
++(MMU.timer[0][1]);
nds.timerOver[0][1] = !MMU.timer[0][1];
if (nds.timerOver[0][1])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x106) & 0x40)
NDS_makeARM9Int(4);
MMU.timer[0][1] = MMU.timerReload[0][1];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[0][1])>>MMU.timerMODE[0][1];
nds.old = MMU.timer[0][1];
MMU.timer[0][1] += nds.diff;
nds.timerCycle[0][1] += nds.diff << MMU.timerMODE[0][1];
nds.timerOver[0][1] = nds.old>MMU.timer[0][1];
if(nds.timerOver[0][1])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x106) & 0x40)
NDS_makeARM9Int(4);
MMU.timer[0][1] = MMU.timerReload[0][1];
}
}
break;
}
}
else
{
MMU.timerRUN[0][1] = TRUE;
nds.timerCycle[0][1] = nds.cycles;
}
}
if(MMU.timerON[0][2])
{
if(MMU.timerRUN[0][2])
{
switch(MMU.timerMODE[0][2])
{
case 0xFFFF :
if(nds.timerOver[0][1])
{
++(MMU.timer[0][2]);
nds.timerOver[0][2] = !MMU.timer[0][2];
if (nds.timerOver[0][2])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x10A) & 0x40)
NDS_makeARM9Int(5);
MMU.timer[0][2] = MMU.timerReload[0][2];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[0][2])>>MMU.timerMODE[0][2];
nds.old = MMU.timer[0][2];
MMU.timer[0][2] += nds.diff;
nds.timerCycle[0][2] += nds.diff << MMU.timerMODE[0][2];
nds.timerOver[0][2] = nds.old>MMU.timer[0][2];
if(nds.timerOver[0][2])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x10A) & 0x40)
NDS_makeARM9Int(5);
MMU.timer[0][2] = MMU.timerReload[0][2];
}
}
break;
}
}
else
{
MMU.timerRUN[0][2] = TRUE;
nds.timerCycle[0][2] = nds.cycles;
}
}
if(MMU.timerON[0][3])
{
if(MMU.timerRUN[0][3])
{
switch(MMU.timerMODE[0][3])
{
case 0xFFFF :
if(nds.timerOver[0][2])
{
++(MMU.timer[0][3]);
nds.timerOver[0][3] = !MMU.timer[0][3];
if (nds.timerOver[0][3])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x10E) & 0x40)
NDS_makeARM9Int(6);
MMU.timer[0][3] = MMU.timerReload[0][3];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[0][3])>>MMU.timerMODE[0][3];
nds.old = MMU.timer[0][3];
MMU.timer[0][3] += nds.diff;
nds.timerCycle[0][3] += nds.diff << MMU.timerMODE[0][3];
nds.timerOver[0][3] = nds.old>MMU.timer[0][3];
if(nds.timerOver[0][3])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x10E) & 0x40)
NDS_makeARM9Int(6);
MMU.timer[0][3] = MMU.timerReload[0][3];
}
}
break;
}
}
else
{
MMU.timerRUN[0][3] = TRUE;
nds.timerCycle[0][3] = nds.cycles;
}
}
if(MMU.timerON[1][0])
{
if(MMU.timerRUN[1][0])
{
switch(MMU.timerMODE[1][0])
{
case 0xFFFF :
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[1][0])>>MMU.timerMODE[1][0];
nds.old = MMU.timer[1][0];
MMU.timer[1][0] += nds.diff;
nds.timerCycle[1][0] += nds.diff << MMU.timerMODE[1][0];
nds.timerOver[1][0] = nds.old>MMU.timer[1][0];
if(nds.timerOver[1][0])
{
if(T1ReadWord(MMU.ARM7_REG, 0x102) & 0x40)
NDS_makeARM7Int(3);
MMU.timer[1][0] = MMU.timerReload[1][0];
}
}
break;
}
}
else
{
MMU.timerRUN[1][0] = TRUE;
nds.timerCycle[1][0] = nds.cycles;
}
}
if(MMU.timerON[1][1])
{
if(MMU.timerRUN[1][1])
{
switch(MMU.timerMODE[1][1])
{
case 0xFFFF :
if(nds.timerOver[1][0])
{
++(MMU.timer[1][1]);
nds.timerOver[1][1] = !MMU.timer[1][1];
if (nds.timerOver[1][1])
{
if(T1ReadWord(MMU.ARM7_REG, 0x106) & 0x40)
NDS_makeARM7Int(4);
MMU.timer[1][1] = MMU.timerReload[1][1];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[1][1])>>MMU.timerMODE[1][1];
nds.old = MMU.timer[1][1];
MMU.timer[1][1] += nds.diff;
nds.timerCycle[1][1] += nds.diff << MMU.timerMODE[1][1];
nds.timerOver[1][1] = nds.old>MMU.timer[1][1];
if(nds.timerOver[1][1])
{
if(T1ReadWord(MMU.ARM7_REG, 0x106) & 0x40)
NDS_makeARM7Int(4);
MMU.timer[1][1] = MMU.timerReload[1][1];
}
}
break;
}
}
else
{
MMU.timerRUN[1][1] = TRUE;
nds.timerCycle[1][1] = nds.cycles;
}
}
if(MMU.timerON[1][2])
{
if(MMU.timerRUN[1][2])
{
switch(MMU.timerMODE[1][2])
{
case 0xFFFF :
if(nds.timerOver[1][1])
{
++(MMU.timer[1][2]);
nds.timerOver[1][2] = !MMU.timer[1][2];
if (nds.timerOver[1][2])
{
if(T1ReadWord(MMU.ARM7_REG, 0x10A) & 0x40)
NDS_makeARM7Int(5);
MMU.timer[1][2] = MMU.timerReload[1][2];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[1][2])>>MMU.timerMODE[1][2];
nds.old = MMU.timer[1][2];
MMU.timer[1][2] += nds.diff;
nds.timerCycle[1][2] += nds.diff << MMU.timerMODE[1][2];
nds.timerOver[1][2] = nds.old>MMU.timer[1][2];
if(nds.timerOver[1][2])
{
if(T1ReadWord(MMU.ARM7_REG, 0x10A) & 0x40)
NDS_makeARM7Int(5);
MMU.timer[1][2] = MMU.timerReload[1][2];
}
}
break;
}
}
else
{
MMU.timerRUN[1][2] = TRUE;
nds.timerCycle[1][2] = nds.cycles;
}
}
if(MMU.timerON[1][3])
{
if(MMU.timerRUN[1][3])
{
switch(MMU.timerMODE[1][3])
{
case 0xFFFF :
if(nds.timerOver[1][2])
{
++(MMU.timer[1][3]);
nds.timerOver[1][3] = !MMU.timer[1][3];
if (nds.timerOver[1][3])
{
if(T1ReadWord(MMU.ARM7_REG, 0x10E) & 0x40)
NDS_makeARM7Int(6);
MMU.timer[1][3] += MMU.timerReload[1][3];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[1][3])>>MMU.timerMODE[1][3];
nds.old = MMU.timer[1][3];
MMU.timer[1][3] += nds.diff;
nds.timerCycle[1][3] += nds.diff << MMU.timerMODE[1][3];
nds.timerOver[1][3] = nds.old>MMU.timer[1][3];
if(nds.timerOver[1][3])
{
if(T1ReadWord(MMU.ARM7_REG, 0x10E) & 0x40)
NDS_makeARM7Int(6);
MMU.timer[1][3] += MMU.timerReload[1][3];
}
}
break;
}
}
else
{
MMU.timerRUN[1][3] = TRUE;
nds.timerCycle[1][3] = nds.cycles;
}
}
if((MMU.DMAing[0][0])&&(MMU.DMACycle[0][0]<=nds.cycles))
{
T1WriteLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*0), T1ReadLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*0)) & 0x7FFFFFFF);
if((MMU.DMACrt[0][0])&(1<<30)) NDS_makeARM9Int(8);
MMU.DMAing[0][0] = FALSE;
}
if((MMU.DMAing[0][1])&&(MMU.DMACycle[0][1]<=nds.cycles))
{
T1WriteLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*1), T1ReadLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*1)) & 0x7FFFFFFF);
if((MMU.DMACrt[0][1])&(1<<30)) NDS_makeARM9Int(9);
MMU.DMAing[0][1] = FALSE;
}
if((MMU.DMAing[0][2])&&(MMU.DMACycle[0][2]<=nds.cycles))
{
T1WriteLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*2), T1ReadLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*2)) & 0x7FFFFFFF);
if((MMU.DMACrt[0][2])&(1<<30)) NDS_makeARM9Int(10);
MMU.DMAing[0][2] = FALSE;
}
if((MMU.DMAing[0][3])&&(MMU.DMACycle[0][3]<=nds.cycles))
{
T1WriteLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*3), T1ReadLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*3)) & 0x7FFFFFFF);
if((MMU.DMACrt[0][3])&(1<<30)) NDS_makeARM9Int(11);
MMU.DMAing[0][3] = FALSE;
}
if((MMU.DMAing[1][0])&&(MMU.DMACycle[1][0]<=nds.cycles))
{
T1WriteLong(MMU.ARM7_REG, 0xB8 + (0xC*0), T1ReadLong(MMU.ARM7_REG, 0xB8 + (0xC*0)) & 0x7FFFFFFF);
if((MMU.DMACrt[1][0])&(1<<30)) NDS_makeARM7Int(8);
MMU.DMAing[1][0] = FALSE;
}
if((MMU.DMAing[1][1])&&(MMU.DMACycle[1][1]<=nds.cycles))
{
T1WriteLong(MMU.ARM7_REG, 0xB8 + (0xC*1), T1ReadLong(MMU.ARM7_REG, 0xB8 + (0xC*1)) & 0x7FFFFFFF);
if((MMU.DMACrt[1][1])&(1<<30)) NDS_makeARM7Int(9);
MMU.DMAing[1][1] = FALSE;
}
if((MMU.DMAing[1][2])&&(MMU.DMACycle[1][2]<=nds.cycles))
{
T1WriteLong(MMU.ARM7_REG, 0xB8 + (0xC*2), T1ReadLong(MMU.ARM7_REG, 0xB8 + (0xC*2)) & 0x7FFFFFFF);
if((MMU.DMACrt[1][2])&(1<<30)) NDS_makeARM7Int(10);
MMU.DMAing[1][2] = FALSE;
}
if((MMU.DMAing[1][3])&&(MMU.DMACycle[1][3]<=nds.cycles))
{
T1WriteLong(MMU.ARM7_REG, 0xB8 + (0xC*3), T1ReadLong(MMU.ARM7_REG, 0xB8 + (0xC*3)) & 0x7FFFFFFF);
if((MMU.DMACrt[1][3])&(1<<30)) NDS_makeARM7Int(11);
MMU.DMAing[1][3] = FALSE;
}
if((MMU.reg_IF[0]&MMU.reg_IE[0]) && (MMU.reg_IME[0]))
//if(NDS_ARM9.irqExeption())
if ( armcpu_flagIrq( &NDS_ARM9)) {
nds.ARM9Cycle = nds.cycles;
}
/*
if(armcpu_irqExeption(&NDS_ARM9))
{
nds.ARM9Cycle = nds.cycles;
}
*/
if((MMU.reg_IF[1]&MMU.reg_IE[1]) && (MMU.reg_IME[1]))
if ( armcpu_flagIrq( &NDS_ARM7)) {
nds.ARM7Cycle = nds.cycles;
}
/*
if (armcpu_irqExeption(&NDS_ARM7))
nds.ARM7Cycle = nds.cycles;
*/
}
return nds.cycles;
}

View File

@ -127,8 +127,11 @@ typedef struct
extern NDSSystem nds;
extern NDSFirmware firmware;
int NDSInit(void);
void NDSDeInit(void);
int NDS_Init( struct armcpu_memory_iface *arm9_mem_if,
struct armcpu_ctrl_iface **arm9_ctrl_iface,
struct armcpu_memory_iface *arm7_mem_if,
struct armcpu_ctrl_iface **arm7_ctrl_iface);
void NDS_DeInit(void);
BOOL NDS_SetROM(u8 * rom, u32 mask);
NDS_header * NDS_getROMHeader(void);
@ -136,7 +139,8 @@ NDS_header * NDS_getROMHeader(void);
void NDS_setTouchPos(u16 x, u16 y);
void NDS_releasTouch(void);
int NDS_LoadROM(const char *filename, int bmtype, u32 bmsize);
int NDS_LoadROM(const char *filename, int bmtype, u32 bmsize,
const char *cflash_disk_image_file);
void NDS_FreeROM(void);
void NDS_Reset(void);
int NDS_ImportSave(const char *filename);
@ -144,6 +148,8 @@ int NDS_ImportSave(const char *filename);
int NDS_WriteBMP(const char *filename);
int NDS_LoadFirmware(const char *filename);
int NDS_CreateDummyFirmware(void);
u32
NDS_exec(s32 nb, BOOL force);
static INLINE void NDS_ARM9HBlankInt(void)
{
@ -189,648 +195,7 @@ int NDS_CreateDummyFirmware(void);
SubScreen.offset = tmp;
}
#define INDEX(i) ((((i)>>16)&0xFF0)|(((i)>>4)&0xF))
static INLINE u32 NDS_exec(s32 nb, BOOL force)
{
nb += nds.cycles;//(nds.cycles>>26)<<26;
for(; (nb >= nds.cycles) && ((force)||(execute)); )
{
if(nds.ARM9Cycle<=nds.cycles)
{
#ifdef LOG_ARM9
if(logcount==3){
if(NDS_ARM9.CPSR.bits.T)
des_thumb_instructions_set[(NDS_ARM9.instruction)>>6](NDS_ARM9.instruct_adr, NDS_ARM9.instruction, logbuf);
else
des_arm_instructions_set[INDEX(NDS_ARM9.instruction)](NDS_ARM9.instruct_adr, NDS_ARM9.instruction, logbuf);
sprintf(logbuf, "%s\t%08X\n\t R00: %08X, R01: %08X, R02: %08X, R03: %08X, R04: %08X, R05: %08X, R06: %08X, R07: %08X,\n\t R08: %08X, R09: %08X, R10: %08X, R11: %08X, R12: %08X, R13: %08X, R14: %08X, R15: %08X,\n\t CPSR: %08X , SPSR: %08X",
logbuf, NDS_ARM9.instruction, NDS_ARM9.R[0], NDS_ARM9.R[1], NDS_ARM9.R[2], NDS_ARM9.R[3], NDS_ARM9.R[4], NDS_ARM9.R[5], NDS_ARM9.R[6], NDS_ARM9.R[7],
NDS_ARM9.R[8], NDS_ARM9.R[9], NDS_ARM9.R[10], NDS_ARM9.R[11], NDS_ARM9.R[12], NDS_ARM9.R[13], NDS_ARM9.R[14], NDS_ARM9.R[15],
NDS_ARM9.CPSR, NDS_ARM9.SPSR);
LOG(logbuf);
}
#endif
if(NDS_ARM9.waitIRQ)
nds.ARM9Cycle += 100;
else
//nds.ARM9Cycle += NDS_ARM9.exec();
nds.ARM9Cycle += armcpu_exec(&NDS_ARM9);
}
#ifdef EXPERIMENTAL_WIFI
if((nds.ARM7Cycle % 0x3F03) == 0)
{
/* 3F03 arm7 cyles = ~1usec */
WIFI_usTrigger(&wifiMac) ;
}
#endif
if(nds.ARM7Cycle<=nds.cycles)
{
#ifdef LOG_ARM7
if(logcount==1){
if(NDS_ARM7.CPSR.bits.T)
des_thumb_instructions_set[(NDS_ARM7.instruction)>>6](NDS_ARM7.instruct_adr, NDS_ARM7.instruction, logbuf);
else
des_arm_instructions_set[INDEX(NDS_ARM7.instruction)](NDS_ARM7.instruct_adr, NDS_ARM7.instruction, logbuf);
sprintf(logbuf, "%s\n\t R00: %08X, R01: %08X, R02: %08X, R03: %08X, R04: %08X, R05: %08X, R06: %08X, R07: %08X,\n\t R08: %08X, R09: %08X, R10: %08X, R11: %08X, R12: %08X, R13: %08X, R14: %08X, R15: %08X,\n\t CPSR: %08X , SPSR: %08X",
logbuf, NDS_ARM7.R[0], NDS_ARM7.R[1], NDS_ARM7.R[2], NDS_ARM7.R[3], NDS_ARM7.R[4], NDS_ARM7.R[5], NDS_ARM7.R[6], NDS_ARM7.R[7],
NDS_ARM7.R[8], NDS_ARM7.R[9], NDS_ARM7.R[10], NDS_ARM7.R[11], NDS_ARM7.R[12], NDS_ARM7.R[13], NDS_ARM7.R[14], NDS_ARM7.R[15],
NDS_ARM7.CPSR, NDS_ARM7.SPSR);
LOG(logbuf);
}
#endif
if(NDS_ARM7.waitIRQ)
nds.ARM7Cycle += 100;
else
//nds.ARM7Cycle += (NDS_ARM7.exec()<<1);
nds.ARM7Cycle += (armcpu_exec(&NDS_ARM7)<<1);
}
nds.cycles = (nds.ARM9Cycle<nds.ARM7Cycle)?nds.ARM9Cycle : nds.ARM7Cycle;
debug();
if(nds.cycles>=nds.nextHBlank)
{
if(!nds.lignerendu)
{
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) | 2);
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) | 2);
NDS_ARM9HBlankInt();
NDS_ARM7HBlankInt();
if(nds.VCount<192)
{
GPU_ligne(&MainScreen, nds.VCount);
GPU_ligne(&SubScreen, nds.VCount);
if(MMU.DMAStartTime[0][0] == 2)
MMU_doDMA(0, 0);
if(MMU.DMAStartTime[0][1] == 2)
MMU_doDMA(0, 1);
if(MMU.DMAStartTime[0][2] == 2)
MMU_doDMA(0, 2);
if(MMU.DMAStartTime[0][3] == 2)
MMU_doDMA(0, 3);
}
nds.lignerendu = TRUE;
}
if(nds.cycles>=nds.nextHBlank+1092)
{
u32 vmatch;
++nds.VCount;
nds.nextHBlank += 4260;
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) & 0xFFFD);
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) & 0xFFFD);
if(MMU.DMAStartTime[0][0] == 3)
MMU_doDMA(0, 0);
if(MMU.DMAStartTime[0][1] == 3)
MMU_doDMA(0, 1);
if(MMU.DMAStartTime[0][2] == 3)
MMU_doDMA(0, 2);
if(MMU.DMAStartTime[0][3] == 3)
MMU_doDMA(0, 3);
// Main memory display
if(MMU.DMAStartTime[0][0] == 4)
{
MMU_doDMA(0, 0);
MMU.DMAStartTime[0][0] = 0;
}
if(MMU.DMAStartTime[0][1] == 4)
{
MMU_doDMA(0, 1);
MMU.DMAStartTime[0][1] = 0;
}
if(MMU.DMAStartTime[0][2] == 4)
{
MMU_doDMA(0, 2);
MMU.DMAStartTime[0][2] = 0;
}
if(MMU.DMAStartTime[0][3] == 4)
{
MMU_doDMA(0, 3);
MMU.DMAStartTime[0][3] = 0;
}
if(MMU.DMAStartTime[1][0] == 4)
{
MMU_doDMA(1, 0);
MMU.DMAStartTime[1][0] = 0;
}
if(MMU.DMAStartTime[1][1] == 4)
{
MMU_doDMA(1, 1);
MMU.DMAStartTime[0][1] = 0;
}
if(MMU.DMAStartTime[1][2] == 4)
{
MMU_doDMA(1, 2);
MMU.DMAStartTime[1][2] = 0;
}
if(MMU.DMAStartTime[1][3] == 4)
{
MMU_doDMA(1, 3);
MMU.DMAStartTime[1][3] = 0;
}
nds.lignerendu = FALSE;
if(nds.VCount==192)
{
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) | 1);
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) | 1);
NDS_ARM9VBlankInt();
NDS_ARM7VBlankInt();
if(MMU.DMAStartTime[0][0] == 1)
MMU_doDMA(0, 0);
if(MMU.DMAStartTime[0][1] == 1)
MMU_doDMA(0, 1);
if(MMU.DMAStartTime[0][2] == 1)
MMU_doDMA(0, 2);
if(MMU.DMAStartTime[0][3] == 1)
MMU_doDMA(0, 3);
if(MMU.DMAStartTime[1][0] == 1)
MMU_doDMA(1, 0);
if(MMU.DMAStartTime[1][1] == 1)
MMU_doDMA(1, 1);
if(MMU.DMAStartTime[1][2] == 1)
MMU_doDMA(1, 2);
if(MMU.DMAStartTime[1][3] == 1)
MMU_doDMA(1, 3);
}
else
if(nds.VCount==263)
{
nds.nextHBlank = 3168;
nds.VCount = 0;
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) & 0xFFFE);
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) & 0xFFFE);
nds.cycles -= (560190<<1);
nds.ARM9Cycle -= (560190<<1);
nds.ARM7Cycle -= (560190<<1);
nb -= (560190<<1);
if(MMU.timerON[0][0])
nds.timerCycle[0][0] -= (560190<<1);
if(MMU.timerON[0][1])
nds.timerCycle[0][1] -= (560190<<1);
if(MMU.timerON[0][2])
nds.timerCycle[0][2] -= (560190<<1);
if(MMU.timerON[0][3])
nds.timerCycle[0][3] -= (560190<<1);
if(MMU.timerON[1][0])
nds.timerCycle[1][0] -= (560190<<1);
if(MMU.timerON[1][1])
nds.timerCycle[1][1] -= (560190<<1);
if(MMU.timerON[1][2])
nds.timerCycle[1][2] -= (560190<<1);
if(MMU.timerON[1][3])
nds.timerCycle[1][3] -= (560190<<1);
if(MMU.DMAing[0][0])
MMU.DMACycle[0][0] -= (560190<<1);
if(MMU.DMAing[0][1])
MMU.DMACycle[0][1] -= (560190<<1);
if(MMU.DMAing[0][2])
MMU.DMACycle[0][2] -= (560190<<1);
if(MMU.DMAing[0][3])
MMU.DMACycle[0][3] -= (560190<<1);
if(MMU.DMAing[1][0])
MMU.DMACycle[1][0] -= (560190<<1);
if(MMU.DMAing[1][1])
MMU.DMACycle[1][1] -= (560190<<1);
if(MMU.DMAing[1][2])
MMU.DMACycle[1][2] -= (560190<<1);
if(MMU.DMAing[1][3])
MMU.DMACycle[1][3] -= (560190<<1);
}
T1WriteWord(ARM9Mem.ARM9_REG, 6, nds.VCount);
T1WriteWord(MMU.ARM7_REG, 6, nds.VCount);
vmatch = T1ReadWord(ARM9Mem.ARM9_REG, 4);
if((nds.VCount==(vmatch>>8)|((vmatch<<1)&(1<<8))))
{
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) | 4);
if(T1ReadWord(ARM9Mem.ARM9_REG, 4) & 32)
NDS_makeARM9Int(2);
}
else
T1WriteWord(ARM9Mem.ARM9_REG, 4, T1ReadWord(ARM9Mem.ARM9_REG, 4) & 0xFFFB);
vmatch = T1ReadWord(MMU.ARM7_REG, 4);
if((nds.VCount==(vmatch>>8)|((vmatch<<1)&(1<<8))))
{
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) | 4);
if(T1ReadWord(MMU.ARM7_REG, 4) & 32)
NDS_makeARM7Int(2);
}
else
T1WriteWord(MMU.ARM7_REG, 4, T1ReadWord(MMU.ARM7_REG, 4) & 0xFFFB);
}
}
/* assume the timers have not expired */
nds.timerOver[0][0] = 0;
nds.timerOver[0][1] = 0;
nds.timerOver[0][2] = 0;
nds.timerOver[0][3] = 0;
nds.timerOver[1][0] = 0;
nds.timerOver[1][1] = 0;
nds.timerOver[1][2] = 0;
nds.timerOver[1][3] = 0;
if(MMU.timerON[0][0])
{
if(MMU.timerRUN[0][0])
{
switch(MMU.timerMODE[0][0])
{
case 0xFFFF :
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[0][0])>>MMU.timerMODE[0][0];
nds.old = MMU.timer[0][0];
MMU.timer[0][0] += nds.diff;
nds.timerCycle[0][0] += (nds.diff << MMU.timerMODE[0][0]);
nds.timerOver[0][0] = nds.old>MMU.timer[0][0];
if(nds.timerOver[0][0])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x102) & 0x40)
NDS_makeARM9Int(3);
MMU.timer[0][0] = MMU.timerReload[0][0];
}
}
break;
}
}
else
{
MMU.timerRUN[0][0] = TRUE;
nds.timerCycle[0][0] = nds.cycles;
}
}
if(MMU.timerON[0][1])
{
if(MMU.timerRUN[0][1])
{
switch(MMU.timerMODE[0][1])
{
case 0xFFFF :
if(nds.timerOver[0][0])
{
++(MMU.timer[0][1]);
nds.timerOver[0][1] = !MMU.timer[0][1];
if (nds.timerOver[0][1])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x106) & 0x40)
NDS_makeARM9Int(4);
MMU.timer[0][1] = MMU.timerReload[0][1];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[0][1])>>MMU.timerMODE[0][1];
nds.old = MMU.timer[0][1];
MMU.timer[0][1] += nds.diff;
nds.timerCycle[0][1] += nds.diff << MMU.timerMODE[0][1];
nds.timerOver[0][1] = nds.old>MMU.timer[0][1];
if(nds.timerOver[0][1])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x106) & 0x40)
NDS_makeARM9Int(4);
MMU.timer[0][1] = MMU.timerReload[0][1];
}
}
break;
}
}
else
{
MMU.timerRUN[0][1] = TRUE;
nds.timerCycle[0][1] = nds.cycles;
}
}
if(MMU.timerON[0][2])
{
if(MMU.timerRUN[0][2])
{
switch(MMU.timerMODE[0][2])
{
case 0xFFFF :
if(nds.timerOver[0][1])
{
++(MMU.timer[0][2]);
nds.timerOver[0][2] = !MMU.timer[0][2];
if (nds.timerOver[0][2])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x10A) & 0x40)
NDS_makeARM9Int(5);
MMU.timer[0][2] = MMU.timerReload[0][2];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[0][2])>>MMU.timerMODE[0][2];
nds.old = MMU.timer[0][2];
MMU.timer[0][2] += nds.diff;
nds.timerCycle[0][2] += nds.diff << MMU.timerMODE[0][2];
nds.timerOver[0][2] = nds.old>MMU.timer[0][2];
if(nds.timerOver[0][2])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x10A) & 0x40)
NDS_makeARM9Int(5);
MMU.timer[0][2] = MMU.timerReload[0][2];
}
}
break;
}
}
else
{
MMU.timerRUN[0][2] = TRUE;
nds.timerCycle[0][2] = nds.cycles;
}
}
if(MMU.timerON[0][3])
{
if(MMU.timerRUN[0][3])
{
switch(MMU.timerMODE[0][3])
{
case 0xFFFF :
if(nds.timerOver[0][2])
{
++(MMU.timer[0][3]);
nds.timerOver[0][3] = !MMU.timer[0][3];
if (nds.timerOver[0][3])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x10E) & 0x40)
NDS_makeARM9Int(6);
MMU.timer[0][3] = MMU.timerReload[0][3];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[0][3])>>MMU.timerMODE[0][3];
nds.old = MMU.timer[0][3];
MMU.timer[0][3] += nds.diff;
nds.timerCycle[0][3] += nds.diff << MMU.timerMODE[0][3];
nds.timerOver[0][3] = nds.old>MMU.timer[0][3];
if(nds.timerOver[0][3])
{
if(T1ReadWord(ARM9Mem.ARM9_REG, 0x10E) & 0x40)
NDS_makeARM9Int(6);
MMU.timer[0][3] = MMU.timerReload[0][3];
}
}
break;
}
}
else
{
MMU.timerRUN[0][3] = TRUE;
nds.timerCycle[0][3] = nds.cycles;
}
}
if(MMU.timerON[1][0])
{
if(MMU.timerRUN[1][0])
{
switch(MMU.timerMODE[1][0])
{
case 0xFFFF :
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[1][0])>>MMU.timerMODE[1][0];
nds.old = MMU.timer[1][0];
MMU.timer[1][0] += nds.diff;
nds.timerCycle[1][0] += nds.diff << MMU.timerMODE[1][0];
nds.timerOver[1][0] = nds.old>MMU.timer[1][0];
if(nds.timerOver[1][0])
{
if(T1ReadWord(MMU.ARM7_REG, 0x102) & 0x40)
NDS_makeARM7Int(3);
MMU.timer[1][0] = MMU.timerReload[1][0];
}
}
break;
}
}
else
{
MMU.timerRUN[1][0] = TRUE;
nds.timerCycle[1][0] = nds.cycles;
}
}
if(MMU.timerON[1][1])
{
if(MMU.timerRUN[1][1])
{
switch(MMU.timerMODE[1][1])
{
case 0xFFFF :
if(nds.timerOver[1][0])
{
++(MMU.timer[1][1]);
nds.timerOver[1][1] = !MMU.timer[1][1];
if (nds.timerOver[1][1])
{
if(T1ReadWord(MMU.ARM7_REG, 0x106) & 0x40)
NDS_makeARM7Int(4);
MMU.timer[1][1] = MMU.timerReload[1][1];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[1][1])>>MMU.timerMODE[1][1];
nds.old = MMU.timer[1][1];
MMU.timer[1][1] += nds.diff;
nds.timerCycle[1][1] += nds.diff << MMU.timerMODE[1][1];
nds.timerOver[1][1] = nds.old>MMU.timer[1][1];
if(nds.timerOver[1][1])
{
if(T1ReadWord(MMU.ARM7_REG, 0x106) & 0x40)
NDS_makeARM7Int(4);
MMU.timer[1][1] = MMU.timerReload[1][1];
}
}
break;
}
}
else
{
MMU.timerRUN[1][1] = TRUE;
nds.timerCycle[1][1] = nds.cycles;
}
}
if(MMU.timerON[1][2])
{
if(MMU.timerRUN[1][2])
{
switch(MMU.timerMODE[1][2])
{
case 0xFFFF :
if(nds.timerOver[1][1])
{
++(MMU.timer[1][2]);
nds.timerOver[1][2] = !MMU.timer[1][2];
if (nds.timerOver[1][2])
{
if(T1ReadWord(MMU.ARM7_REG, 0x10A) & 0x40)
NDS_makeARM7Int(5);
MMU.timer[1][2] = MMU.timerReload[1][2];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[1][2])>>MMU.timerMODE[1][2];
nds.old = MMU.timer[1][2];
MMU.timer[1][2] += nds.diff;
nds.timerCycle[1][2] += nds.diff << MMU.timerMODE[1][2];
nds.timerOver[1][2] = nds.old>MMU.timer[1][2];
if(nds.timerOver[1][2])
{
if(T1ReadWord(MMU.ARM7_REG, 0x10A) & 0x40)
NDS_makeARM7Int(5);
MMU.timer[1][2] = MMU.timerReload[1][2];
}
}
break;
}
}
else
{
MMU.timerRUN[1][2] = TRUE;
nds.timerCycle[1][2] = nds.cycles;
}
}
if(MMU.timerON[1][3])
{
if(MMU.timerRUN[1][3])
{
switch(MMU.timerMODE[1][3])
{
case 0xFFFF :
if(nds.timerOver[1][2])
{
++(MMU.timer[1][3]);
nds.timerOver[1][3] = !MMU.timer[1][3];
if (nds.timerOver[1][3])
{
if(T1ReadWord(MMU.ARM7_REG, 0x10E) & 0x40)
NDS_makeARM7Int(6);
MMU.timer[1][3] += MMU.timerReload[1][3];
}
}
break;
default :
{
nds.diff = (nds.cycles - nds.timerCycle[1][3])>>MMU.timerMODE[1][3];
nds.old = MMU.timer[1][3];
MMU.timer[1][3] += nds.diff;
nds.timerCycle[1][3] += nds.diff << MMU.timerMODE[1][3];
nds.timerOver[1][3] = nds.old>MMU.timer[1][3];
if(nds.timerOver[1][3])
{
if(T1ReadWord(MMU.ARM7_REG, 0x10E) & 0x40)
NDS_makeARM7Int(6);
MMU.timer[1][3] += MMU.timerReload[1][3];
}
}
break;
}
}
else
{
MMU.timerRUN[1][3] = TRUE;
nds.timerCycle[1][3] = nds.cycles;
}
}
if((MMU.DMAing[0][0])&&(MMU.DMACycle[0][0]<=nds.cycles))
{
T1WriteLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*0), T1ReadLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*0)) & 0x7FFFFFFF);
if((MMU.DMACrt[0][0])&(1<<30)) NDS_makeARM9Int(8);
MMU.DMAing[0][0] = FALSE;
}
if((MMU.DMAing[0][1])&&(MMU.DMACycle[0][1]<=nds.cycles))
{
T1WriteLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*1), T1ReadLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*1)) & 0x7FFFFFFF);
if((MMU.DMACrt[0][1])&(1<<30)) NDS_makeARM9Int(9);
MMU.DMAing[0][1] = FALSE;
}
if((MMU.DMAing[0][2])&&(MMU.DMACycle[0][2]<=nds.cycles))
{
T1WriteLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*2), T1ReadLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*2)) & 0x7FFFFFFF);
if((MMU.DMACrt[0][2])&(1<<30)) NDS_makeARM9Int(10);
MMU.DMAing[0][2] = FALSE;
}
if((MMU.DMAing[0][3])&&(MMU.DMACycle[0][3]<=nds.cycles))
{
T1WriteLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*3), T1ReadLong(ARM9Mem.ARM9_REG, 0xB8 + (0xC*3)) & 0x7FFFFFFF);
if((MMU.DMACrt[0][3])&(1<<30)) NDS_makeARM9Int(11);
MMU.DMAing[0][3] = FALSE;
}
if((MMU.DMAing[1][0])&&(MMU.DMACycle[1][0]<=nds.cycles))
{
T1WriteLong(MMU.ARM7_REG, 0xB8 + (0xC*0), T1ReadLong(MMU.ARM7_REG, 0xB8 + (0xC*0)) & 0x7FFFFFFF);
if((MMU.DMACrt[1][0])&(1<<30)) NDS_makeARM7Int(8);
MMU.DMAing[1][0] = FALSE;
}
if((MMU.DMAing[1][1])&&(MMU.DMACycle[1][1]<=nds.cycles))
{
T1WriteLong(MMU.ARM7_REG, 0xB8 + (0xC*1), T1ReadLong(MMU.ARM7_REG, 0xB8 + (0xC*1)) & 0x7FFFFFFF);
if((MMU.DMACrt[1][1])&(1<<30)) NDS_makeARM7Int(9);
MMU.DMAing[1][1] = FALSE;
}
if((MMU.DMAing[1][2])&&(MMU.DMACycle[1][2]<=nds.cycles))
{
T1WriteLong(MMU.ARM7_REG, 0xB8 + (0xC*2), T1ReadLong(MMU.ARM7_REG, 0xB8 + (0xC*2)) & 0x7FFFFFFF);
if((MMU.DMACrt[1][2])&(1<<30)) NDS_makeARM7Int(10);
MMU.DMAing[1][2] = FALSE;
}
if((MMU.DMAing[1][3])&&(MMU.DMACycle[1][3]<=nds.cycles))
{
T1WriteLong(MMU.ARM7_REG, 0xB8 + (0xC*3), T1ReadLong(MMU.ARM7_REG, 0xB8 + (0xC*3)) & 0x7FFFFFFF);
if((MMU.DMACrt[1][3])&(1<<30)) NDS_makeARM7Int(11);
MMU.DMAing[1][3] = FALSE;
}
if((MMU.reg_IF[0]&MMU.reg_IE[0]) && (MMU.reg_IME[0]))
//if(NDS_ARM9.irqExeption())
if(armcpu_irqExeption(&NDS_ARM9))
{
nds.ARM9Cycle = nds.cycles;
}
if((MMU.reg_IF[1]&MMU.reg_IE[1]) && (MMU.reg_IME[1]))
if (armcpu_irqExeption(&NDS_ARM7))
nds.ARM7Cycle = nds.cycles;
}
return nds.cycles;
}
#ifdef __cplusplus
}
#endif

File diff suppressed because it is too large Load Diff

View File

@ -29,6 +29,8 @@
armcpu_t NDS_ARM7;
armcpu_t NDS_ARM9;
#define STALLED_CYCLE_COUNT 10
#define SWAP(a, b, c) do \
{ \
c=a; \
@ -36,14 +38,98 @@ armcpu_t NDS_ARM9;
b=c; \
} \
while(0)
static void
stall_cpu( void *instance) {
armcpu_t *armcpu = (armcpu_t *)instance;
armcpu->stalled = 1;
}
int armcpu_new(armcpu_t *armcpu, u32 id)
static void
unstall_cpu( void *instance) {
armcpu_t *armcpu = (armcpu_t *)instance;
armcpu->stalled = 0;
}
static void
install_post_exec_fn( void *instance,
void (*ex_fn)( void *, u32 adr, int thumb),
void *fn_data) {
armcpu_t *armcpu = (armcpu_t *)instance;
armcpu->post_ex_fn = ex_fn;
armcpu->post_ex_fn_data = fn_data;
}
static void
remove_post_exec_fn( void *instance) {
armcpu_t *armcpu = (armcpu_t *)instance;
armcpu->post_ex_fn = NULL;
}
static u32
read_cpu_reg( void *instance, u32 reg_num) {
armcpu_t *armcpu = (armcpu_t *)instance;
u32 reg_value = 0;
if ( reg_num <= 14) {
reg_value = armcpu->R[reg_num];
}
else if ( reg_num == 15) {
reg_value = armcpu->next_instruction;
}
else if ( reg_num == 16) {
/* CPSR */
reg_value = armcpu->CPSR.val;
}
return reg_value;
}
static void
set_cpu_reg( void *instance, u32 reg_num, u32 value) {
armcpu_t *armcpu = (armcpu_t *)instance;
if ( reg_num <= 14) {
armcpu->R[reg_num] = value;
}
else if ( reg_num == 15) {
armcpu->next_instruction = value;
}
else if ( reg_num == 16) {
/* FIXME: setting the CPSR */
}
}
int armcpu_new( armcpu_t *armcpu, u32 id,
struct armcpu_memory_iface *mem_if,
struct armcpu_ctrl_iface **ctrl_iface_ret)
{
armcpu->proc_ID = id;
if(id==0) armcpu->swi_tab = ARM9_swi_tab;
else armcpu->swi_tab = ARM7_swi_tab;
armcpu->mem_if = mem_if;
/* populate the control interface */
armcpu->ctrl_iface.stall = stall_cpu;
armcpu->ctrl_iface.unstall = unstall_cpu;
armcpu->ctrl_iface.read_reg = read_cpu_reg;
armcpu->ctrl_iface.set_reg = set_cpu_reg;
armcpu->ctrl_iface.install_post_ex_fn = install_post_exec_fn;
armcpu->ctrl_iface.remove_post_ex_fn = remove_post_exec_fn;
armcpu->ctrl_iface.data = armcpu;
*ctrl_iface_ret = &armcpu->ctrl_iface;
armcpu->stalled = 0;
armcpu->post_ex_fn = NULL;
armcpu_init(armcpu, 0);
@ -58,7 +144,8 @@ void armcpu_init(armcpu_t *armcpu, u32 adr)
armcpu->intVector = 0xFFFF0000 * (armcpu->proc_ID==0);
armcpu->waitIRQ = FALSE;
armcpu->wirq = FALSE;
armcpu->irq_flag = 0;
if(armcpu->coproc[15]) free(armcpu->coproc[15]);
for(i = 0; i < 15; ++i)
@ -77,11 +164,12 @@ void armcpu_init(armcpu_t *armcpu, u32 adr)
armcpu->R8_fiq = armcpu->R9_fiq = armcpu->R10_fiq = armcpu->R11_fiq = armcpu->R12_fiq = armcpu->R13_fiq = armcpu->R14_fiq = 0;
armcpu->SPSR_svc.val = armcpu->SPSR_abt.val = armcpu->SPSR_und.val = armcpu->SPSR_irq.val = armcpu->SPSR_fiq.val = 0;
armcpu->instruct_adr = adr;
armcpu->next_instruction = adr;
armcpu->R[15] = adr;
armcpu->R[15] = adr + 8;
armcpu->coproc[15] = (armcp_t*)armcp15_new(armcpu);
armcpu_prefetch(armcpu);
//armcpu_prefetch(armcpu);
}
u32 armcpu_switchMode(armcpu_t *armcpu, u8 mode)
@ -191,20 +279,34 @@ u32 armcpu_switchMode(armcpu_t *armcpu, u8 mode)
return oldmode;
}
u32 armcpu_prefetch(armcpu_t *armcpu)
static u32
armcpu_prefetch(armcpu_t *armcpu)
{
u32 temp_instruction;
if(armcpu->CPSR.bits.T == 0)
{
armcpu->instruction = MMU_readWordACL(armcpu->proc_ID, armcpu->next_instruction,CP15_ACCESS_EXECUTE);
armcpu->instruct_adr = armcpu->next_instruction;
armcpu->next_instruction += 4;
armcpu->R[15] = armcpu->next_instruction + 4;
return MMU.MMU_WAIT32[armcpu->proc_ID][(armcpu->instruct_adr>>24)&0xF];
temp_instruction =
armcpu->mem_if->prefetch32( armcpu->mem_if->data,
armcpu->next_instruction);
if ( !armcpu->stalled) {
armcpu->instruction = temp_instruction;
armcpu->instruct_adr = armcpu->next_instruction;
armcpu->next_instruction += 4;
armcpu->R[15] = armcpu->next_instruction + 4;
}
return MMU.MMU_WAIT32[armcpu->proc_ID][(armcpu->instruct_adr>>24)&0xF];
}
armcpu->instruction = MMU_readHWordACL(armcpu->proc_ID, armcpu->next_instruction,CP15_ACCESS_EXECUTE);
armcpu->instruct_adr = armcpu->next_instruction;
armcpu->next_instruction = armcpu->next_instruction + 2;
armcpu->R[15] = armcpu->next_instruction + 2;
temp_instruction =
armcpu->mem_if->prefetch16( armcpu->mem_if->data,
armcpu->next_instruction);
if ( !armcpu->stalled) {
armcpu->instruction = temp_instruction;
armcpu->instruct_adr = armcpu->next_instruction;
armcpu->next_instruction = armcpu->next_instruction + 2;
armcpu->R[15] = armcpu->next_instruction + 2;
}
return MMU.MMU_WAIT16[armcpu->proc_ID][(armcpu->instruct_adr>>24)&0xF];
}
@ -238,54 +340,89 @@ static BOOL (*FASTCALL test_conditions[])(Status_Reg CPSR)= {
#define TEST_COND2(cond, CPSR) \
(cond<15&&test_conditions[cond](CPSR))
u32 armcpu_exec(armcpu_t *armcpu)
{
u32 c = 1;
if(armcpu->CPSR.bits.T == 0)
{
if((TEST_COND(CONDITION(armcpu->instruction), armcpu->CPSR)) || ((CONDITION(armcpu->instruction)==0xF)&&(CODE(armcpu->instruction)==0x5)))
{
c = arm_instructions_set[INSTRUCTION_INDEX(armcpu->instruction)](armcpu);
}
c += armcpu_prefetch(armcpu);
return c;
}
c = thumb_instructions_set[armcpu->instruction>>6](armcpu);
c += armcpu_prefetch(armcpu);
return c;
}
BOOL armcpu_irqExeption(armcpu_t *armcpu)
static BOOL armcpu_irqExeption(armcpu_t *armcpu)
{
Status_Reg tmp;
if(armcpu->CPSR.bits.I) return FALSE;
armcpu->irq_flag = 0;
tmp = armcpu->CPSR;
armcpu_switchMode(armcpu, IRQ);
armcpu->R[14] = armcpu->instruct_adr + 4;
armcpu->R[14] = armcpu->next_instruction + 4;
armcpu->SPSR = tmp;
armcpu->CPSR.bits.T = 0;
armcpu->CPSR.bits.I = 1;
armcpu->next_instruction = armcpu->intVector + 0x18;
armcpu->R[15] = armcpu->next_instruction;
//armcpu->R[15] = armcpu->next_instruction + 8;
armcpu->waitIRQ = 0;
armcpu_prefetch(armcpu);
return TRUE;
}
BOOL armcpu_prefetchExeption(armcpu_t *armcpu)
static BOOL armcpu_prefetchExeption(armcpu_t *armcpu)
{
Status_Reg tmp;
if(armcpu->CPSR.bits.I) return FALSE;
tmp = armcpu->CPSR;
armcpu_switchMode(armcpu, ABT);
armcpu->R[14] = armcpu->instruct_adr + 4;
armcpu->R[14] = armcpu->next_instruction + 4;
armcpu->SPSR = tmp;
armcpu->CPSR.bits.T = 0;
armcpu->CPSR.bits.I = 1;
armcpu->next_instruction = armcpu->intVector + 0xC;
armcpu->R[15] = armcpu->next_instruction;
armcpu->R[15] = armcpu->next_instruction + 8;
armcpu->waitIRQ = 0;
armcpu_prefetch(armcpu);
return TRUE;
}
BOOL
armcpu_flagIrq( armcpu_t *armcpu) {
if(armcpu->CPSR.bits.I) return FALSE;
armcpu->waitIRQ = 0;
armcpu->irq_flag = 1;
return TRUE;
}
u32 armcpu_exec(armcpu_t *armcpu)
{
u32 c;
if ( armcpu->stalled)
return STALLED_CYCLE_COUNT;
/* check for interrupts */
if ( armcpu->irq_flag) {
armcpu_irqExeption( armcpu);
}
c = armcpu_prefetch(armcpu);
if ( armcpu->stalled) {
return c;
}
if(armcpu->CPSR.bits.T == 0)
{
if((TEST_COND(CONDITION(armcpu->instruction), armcpu->CPSR)) || ((CONDITION(armcpu->instruction)==0xF)&&(CODE(armcpu->instruction)==0x5)))
{
c += arm_instructions_set[INSTRUCTION_INDEX(armcpu->instruction)](armcpu);
}
if ( armcpu->post_ex_fn != NULL) {
/* call the external post execute function */
armcpu->post_ex_fn( armcpu->post_ex_fn_data,
armcpu->instruct_adr, 0);
}
return c;
}
c += thumb_instructions_set[armcpu->instruction>>6](armcpu);
if ( armcpu->post_ex_fn != NULL) {
/* call the external post execute function */
armcpu->post_ex_fn( armcpu->post_ex_fn_data, armcpu->instruct_adr, 1);
}
return c;
}

View File

@ -135,6 +135,35 @@ typedef union
} Status_Reg;
#endif
/**
* The control interface to a CPU
*/
struct armcpu_ctrl_iface {
/** stall the processor */
void (*stall)( void *instance);
/** unstall the processor */
void (*unstall)( void *instance);
/** read a register value */
u32 (*read_reg)( void *instance, u32 reg_num);
/** set a register value */
void (*set_reg)( void *instance, u32 reg_num, u32 value);
/** install the post execute function */
void (*install_post_ex_fn)( void *instance,
void (*fn)( void *, u32 adr, int thumb),
void *fn_data);
/** remove the post execute function */
void (*remove_post_ex_fn)( void *instance);
/** the private data passed to all interface functions */
void *data;
};
typedef void* armcp_t;
typedef struct armcpu_t
@ -164,18 +193,38 @@ typedef struct armcpu_t
BOOL wIRQ;
BOOL wirq;
u32 (* *swi_tab)(struct armcpu_t * cpu);
/** there is a pending irq for the cpu */
int irq_flag;
/** the post executed function (if installed) */
void (*post_ex_fn)( void *, u32 adr, int thumb);
/** data for the post executed function */
void *post_ex_fn_data;
/** flag indicating if the processor is stalled */
int stalled;
/** the memory interface */
struct armcpu_memory_iface *mem_if;
/** the ctrl interface */
struct armcpu_ctrl_iface ctrl_iface;
} armcpu_t;
int armcpu_new(armcpu_t *armcpu, u32 id);
int armcpu_new( armcpu_t *armcpu, u32 id, struct armcpu_memory_iface *mem_if,
struct armcpu_ctrl_iface **ctrl_iface_ret);
void armcpu_init(armcpu_t *armcpu, u32 adr);
u32 armcpu_switchMode(armcpu_t *armcpu, u8 mode);
u32 armcpu_prefetch(armcpu_t *armcpu);
//u32 armcpu_prefetch(armcpu_t *armcpu);
u32 armcpu_exec(armcpu_t *armcpu);
BOOL armcpu_irqExeption(armcpu_t *armcpu);
BOOL armcpu_prefetchExeption(armcpu_t *armcpu);
//BOOL armcpu_irqExeption(armcpu_t *armcpu);
//BOOL armcpu_prefetchExeption(armcpu_t *armcpu);
BOOL
armcpu_flagIrq( armcpu_t *armcpu);
extern armcpu_t NDS_ARM7;
extern armcpu_t NDS_ARM9;

View File

@ -538,7 +538,7 @@ static u32 FASTCALL OP_LDR_PCREL(armcpu_t *cpu)
{
u32 adr = (cpu->R[15]&0xFFFFFFFC) + ((cpu->instruction&0xFF)<<2);
cpu->R[REG_NUM(cpu->instruction, 8)] = MMU_readWord(cpu->proc_ID, adr);
cpu->R[REG_NUM(cpu->instruction, 8)] = cpu->mem_if->read32(cpu->mem_if->data, adr);
return 3 + MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
}
@ -547,7 +547,7 @@ static u32 FASTCALL OP_STR_REG_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 6)] + cpu->R[REG_NUM(i, 3)];
MMU_writeWord(cpu->proc_ID, adr, cpu->R[REG_NUM(i, 0)]);
cpu->mem_if->write32(cpu->mem_if->data, adr, cpu->R[REG_NUM(i, 0)]);
return 2 + MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
}
@ -556,7 +556,7 @@ static u32 FASTCALL OP_STRH_REG_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + cpu->R[REG_NUM(i, 6)];
MMU_writeHWord(cpu->proc_ID, adr, ((u16)cpu->R[REG_NUM(i, 0)]));
cpu->mem_if->write16(cpu->mem_if->data, adr, ((u16)cpu->R[REG_NUM(i, 0)]));
return 2 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -565,7 +565,7 @@ static u32 FASTCALL OP_STRB_REG_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + cpu->R[REG_NUM(i, 6)];
MMU_writeByte(cpu->proc_ID, adr, ((u8)cpu->R[REG_NUM(i, 0)]));
cpu->mem_if->write8(cpu->mem_if->data, adr, ((u8)cpu->R[REG_NUM(i, 0)]));
return 2 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -574,7 +574,7 @@ static u32 FASTCALL OP_LDRSB_REG_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + cpu->R[REG_NUM(i, 6)];
cpu->R[REG_NUM(i, 0)] = (s32)((s8)MMU_readByte(cpu->proc_ID, adr));
cpu->R[REG_NUM(i, 0)] = (s32)((s8)cpu->mem_if->read8(cpu->mem_if->data, adr));
return 3 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -583,7 +583,7 @@ static u32 FASTCALL OP_LDR_REG_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = (cpu->R[REG_NUM(i, 3)] + cpu->R[REG_NUM(i, 6)]);
u32 tempValue = MMU_readWord(cpu->proc_ID, adr&0xFFFFFFFC);
u32 tempValue = cpu->mem_if->read32(cpu->mem_if->data, adr&0xFFFFFFFC);
adr = (adr&3)*8;
tempValue = (tempValue>>adr) | (tempValue<<(32-adr));
@ -596,7 +596,7 @@ static u32 FASTCALL OP_LDRH_REG_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + cpu->R[REG_NUM(i, 6)];
cpu->R[REG_NUM(i, 0)] = (u32)MMU_readHWord(cpu->proc_ID, adr);
cpu->R[REG_NUM(i, 0)] = (u32)cpu->mem_if->read16(cpu->mem_if->data, adr);
return 3 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -605,7 +605,7 @@ static u32 FASTCALL OP_LDRB_REG_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + cpu->R[REG_NUM(i, 6)];
cpu->R[REG_NUM(i, 0)] = (u32)MMU_readByte(cpu->proc_ID, adr);
cpu->R[REG_NUM(i, 0)] = (u32)cpu->mem_if->read8(cpu->mem_if->data, adr);
return 3 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -614,7 +614,7 @@ static u32 FASTCALL OP_LDRSH_REG_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + cpu->R[REG_NUM(i, 6)];
cpu->R[REG_NUM(i, 0)] = (s32)((s16)MMU_readHWord(cpu->proc_ID, adr));
cpu->R[REG_NUM(i, 0)] = (s32)((s16)cpu->mem_if->read16(cpu->mem_if->data, adr));
return 3 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -623,7 +623,7 @@ static u32 FASTCALL OP_STR_IMM_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + ((i>>4)&0x7C);
MMU_writeWord(cpu->proc_ID, adr, cpu->R[REG_NUM(i, 0)]);
cpu->mem_if->write32(cpu->mem_if->data, adr, cpu->R[REG_NUM(i, 0)]);
return 2 + MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
}
@ -632,7 +632,7 @@ static u32 FASTCALL OP_LDR_IMM_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + ((i>>4)&0x7C);
u32 tempValue = MMU_readWord(cpu->proc_ID, adr&0xFFFFFFFC);
u32 tempValue = cpu->mem_if->read32(cpu->mem_if->data, adr&0xFFFFFFFC);
adr = (adr&3)*8;
tempValue = (tempValue>>adr) | (tempValue<<(32-adr));
cpu->R[REG_NUM(i, 0)] = tempValue;
@ -644,7 +644,7 @@ static u32 FASTCALL OP_STRB_IMM_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + ((i>>6)&0x1F);
MMU_writeByte(cpu->proc_ID, adr, (u8)cpu->R[REG_NUM(i, 0)]);
cpu->mem_if->write8(cpu->mem_if->data, adr, (u8)cpu->R[REG_NUM(i, 0)]);
return 2 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -653,7 +653,7 @@ static u32 FASTCALL OP_LDRB_IMM_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + ((i>>6)&0x1F);
cpu->R[REG_NUM(i, 0)] = MMU_readByte(cpu->proc_ID, adr);
cpu->R[REG_NUM(i, 0)] = cpu->mem_if->read8(cpu->mem_if->data, adr);
return 3 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -662,7 +662,7 @@ static u32 FASTCALL OP_STRH_IMM_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + ((i>>5)&0x3E);
MMU_writeHWord(cpu->proc_ID, adr, (u16)cpu->R[REG_NUM(i, 0)]);
cpu->mem_if->write16(cpu->mem_if->data, adr, (u16)cpu->R[REG_NUM(i, 0)]);
return 2 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -671,7 +671,7 @@ static u32 FASTCALL OP_LDRH_IMM_OFF(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[REG_NUM(i, 3)] + ((i>>5)&0x3E);
cpu->R[REG_NUM(i, 0)] = MMU_readHWord(cpu->proc_ID, adr);
cpu->R[REG_NUM(i, 0)] = cpu->mem_if->read16(cpu->mem_if->data, adr);
return 3 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -680,7 +680,7 @@ static u32 FASTCALL OP_STR_SPREL(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[13] + ((i&0xFF)<<2);
MMU_writeWord(cpu->proc_ID, adr, cpu->R[REG_NUM(i, 8)]);
cpu->mem_if->write32(cpu->mem_if->data, adr, cpu->R[REG_NUM(i, 8)]);
return 2 + MMU.MMU_WAIT16[cpu->proc_ID][(adr>>24)&0xF];
}
@ -689,7 +689,7 @@ static u32 FASTCALL OP_LDR_SPREL(armcpu_t *cpu)
{
u32 i = cpu->instruction;
u32 adr = cpu->R[13] + ((i&0xFF)<<2);
cpu->R[REG_NUM(i, 8)] = MMU_readWord(cpu->proc_ID, adr);
cpu->R[REG_NUM(i, 8)] = cpu->mem_if->read32(cpu->mem_if->data, adr);
return 3 + MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
}
@ -733,7 +733,7 @@ static u32 FASTCALL OP_PUSH(armcpu_t *cpu)
for(j = 0; j<8; ++j)
if(BIT_N(i, 7-j))
{
MMU_writeWord(cpu->proc_ID, adr, cpu->R[7-j]);
cpu->mem_if->write32(cpu->mem_if->data, adr, cpu->R[7-j]);
c += MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
adr -= 4;
}
@ -748,14 +748,14 @@ static u32 FASTCALL OP_PUSH_LR(armcpu_t *cpu)
u32 adr = cpu->R[13] - 4;
u32 c = 0, j;
MMU_writeWord(cpu->proc_ID, adr, cpu->R[14]);
cpu->mem_if->write32(cpu->mem_if->data, adr, cpu->R[14]);
c += MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
adr -= 4;
for(j = 0; j<8; ++j)
if(BIT_N(i, 7-j))
{
MMU_writeWord(cpu->proc_ID, adr, cpu->R[7-j]);
cpu->mem_if->write32(cpu->mem_if->data, adr, cpu->R[7-j]);
c += MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
adr -= 4;
}
@ -773,7 +773,7 @@ static u32 FASTCALL OP_POP(armcpu_t *cpu)
for(j = 0; j<8; ++j)
if(BIT_N(i, j))
{
cpu->R[j] = MMU_readWord(cpu->proc_ID, adr);
cpu->R[j] = cpu->mem_if->read32(cpu->mem_if->data, adr);
c += MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
adr += 4;
}
@ -792,12 +792,12 @@ static u32 FASTCALL OP_POP_PC(armcpu_t *cpu)
for(j = 0; j<8; ++j)
if(BIT_N(i, j))
{
cpu->R[j] = MMU_readWord(cpu->proc_ID, adr);
cpu->R[j] = cpu->mem_if->read32(cpu->mem_if->data, adr);
c += MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
adr += 4;
}
v = MMU_readWord(cpu->proc_ID, adr);
v = cpu->mem_if->read32(cpu->mem_if->data, adr);
c += MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
cpu->R[15] = v & 0xFFFFFFFE;
cpu->next_instruction = v & 0xFFFFFFFE;
@ -823,7 +823,7 @@ static u32 FASTCALL OP_STMIA_THUMB(armcpu_t *cpu)
for(j = 0; j<8; ++j)
if(BIT_N(i, j))
{
MMU_writeWord(cpu->proc_ID, adr, cpu->R[j]);
cpu->mem_if->write32(cpu->mem_if->data, adr, cpu->R[j]);
c += MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
adr += 4;
}
@ -840,7 +840,7 @@ static u32 FASTCALL OP_LDMIA_THUMB(armcpu_t *cpu)
for(j = 0; j<8; ++j)
if(BIT_N(i, j))
{
cpu->R[j] = MMU_readWord(cpu->proc_ID, adr);
cpu->R[j] = cpu->mem_if->read32(cpu->mem_if->data, adr);
c += MMU.MMU_WAIT32[cpu->proc_ID][(adr>>24)&0xF];
adr += 4;
}