www.pudn.com > potemkin_sourceforPSP.rar > ARM.h
#pragma once
#include "../../Globals.h"
#include "../CPU.h"
#include "BlockCache.h"
#define S_FLAG(x) (x&(1<<20))
/*
#ifdef _MSC_VER
#define ALIGN16 __declspec(align(16))
#else
#define ALIGN16
#endif
*/
enum
{
COND_EQ = 0,
COND_NE,
COND_CS,
COND_CC,
COND_MI,
COND_PL,
COND_VS,
COND_VC,
COND_HI,
COND_LS,
COND_GE,
COND_LT,
COND_GT,
COND_LE,
COND_AL,
COND_ERR
};
enum
{
ARM_SCRATCH_1=0,
ARM_SCRATCH_2=1,
ARM_REG_SP=13,
ARM_REG_LR=14,
ARM_REG_PC=15
};
enum
{
ARM_F_MASK = (1<<6),
ARM_I_MASK = (1<<7)
};
enum ARMMode
{
ARMMODE_USER = 0x10,
ARMMODE_FIQ = 0x11,
ARMMODE_IRQ = 0x12,
ARMMODE_SUPER = 0x13,
ARMMODE_ABORT = 0x17,
ARMMODE_UNDEF = 0x1b,
ARMMODE_SYSTEM = 0x1f,
};
enum
{
ARMTYPE_ARM7TDMI = 7,
ARMTYPE_ARM9 = 9
};
class ALIGN16 ARMState : public CPU
{
private:
u32 cpsr; // do not read directly
public:
ARMState(int _type)
{
blockCache.armState = this;
type=_type;
}
~ARMState() {}
void Reset();
u32 ALIGN16 r[20]; //space for temp regs
u32 r13_usr,r14_usr;
u32 r13_svc,r14_svc;
u32 r13_abt,r14_abt;
u32 r13_und,r14_und;
u32 r13_irq,r14_irq;
u32 r8_14_fiq[6];
bool n,z,c,v;
//todo : join n,z into flags
bool thumb;
u32 spsr;
u32 spsr_svc;
u32 spsr_abt;
u32 spsr_und;
u32 spsr_irq;
u32 spsr_fiq;
bool highVectors;
bool fakeBios;
bool enabled;
BlockCache blockCache;
u32 GetCPSR();
void SetCPSR(u32 ncpsr);
ARMMode GetMode();
void ModeSwitch(ARMMode mode, bool saveState=false);
bool EvaluateCondition(int cc);
bool IRQEnabled() { return (cpsr & ARM_I_MASK) ? false : true;}
bool FIRQEnabled() { return (cpsr & ARM_F_MASK) ? false : true;}
void Irq();
void FIrq();
void SWI();
void Abort();
void UndefInstr();
int type; //7 or 9
//overridden functions
TCHAR *GetName();
int GetNumGPRs() { return 16; }
int GetGPRSize() { return GPR_SIZE_32;}
u32 GetGPR32Value(int reg) {return r[reg];}
u32 GetPC() {return r[ARM_REG_PC];}
u32 GetLR() {return r[ARM_REG_LR];}
int GetInstructionSize() {return thumb?2:4;}
void SetPC(u32 _pc) {r[15]=_pc;}
CPUType GetType() {return type == 7 ? CPUTYPE_ARM7 : CPUTYPE_ARM9;}
const TCHAR *GetCategoryName(int cat)
{
const TCHAR *names[2] = {_T("GPR"),_T("SPECIAL")};
return names[cat];
}
int GetNumCategories() { return 2; }
int GetNumRegsInCategory(int cat)
{
int r[2] = {17,1};
return r[cat];
}
const TCHAR *GetRegName(int cat, int index)
{
const TCHAR *regName[17] = {
_T("R0"),
"R1", "R2", "R3", "R4",
"R5", "R6", "R7", "R8",
"R9", "R10", "R11", "R12",
"R13", "R14", "R15 PC", "CPSR",
};
if (cat==0)
return regName[index];
else
return "boo";
}
u32 GetRegValue(int cat, int index)
{
switch(index) {
case 16:
return GetCPSR();
default:
return r[index];
}
}
void SetRegValue(int cat, int index, u32 value)
{
if (index<16)
r[index] = value;
}
};
extern ARMState arm7;
extern ARMState arm9;
inline u32 SEX24(u32 i)
{
return (i&0x800000) ? (i|0xFF000000) : (i&0x7FFFFF);
}
inline u32 SEX11(u32 i)
{
return (i&0x400) ? (i|0xFFFFF800) : (i&0x3FF);
}
void ARM_Init();
void ARM_Shutdown();
void ARM_Irq();
void ARM_Firq();
void ARM_SWI();