diff --git a/core/arm_emitter/E_Branches.h b/core/arm_emitter/E_Branches.h index 626ba54ac..71e545d87 100644 --- a/core/arm_emitter/E_Branches.h +++ b/core/arm_emitter/E_Branches.h @@ -64,12 +64,12 @@ namespace ARM // This encoding looks correct, but segfaults, the pc val is align(pc,4) but this should be right in ARM // #if defined(_DEVEL) - EAPI BLX(u32 sImm24) // Form I * H is derived so not needed, fixup sImm24 so one can just pass a real addr + EAPI BLX(u32 sImm24, bool toThumb) // Form I * H is derived so not needed, fixup sImm24 so one can just pass a real addr { DECL_Id(0xFA000000); - //if(sImm24&1) - // I |= 1<<24; // SET_H + if(toThumb) + I |= 1<<24; // SET_H I |= ((sImm24>>2)&0xFFFFFF); EMIT_I; diff --git a/core/arm_emitter/H_Branches.h b/core/arm_emitter/H_Branches.h index c99332010..0193a888f 100644 --- a/core/arm_emitter/H_Branches.h +++ b/core/arm_emitter/H_Branches.h @@ -22,6 +22,8 @@ namespace ARM EAPI CALL(unat FnAddr, ConditionCode CC=AL) { + bool isThumb = FnAddr & 1; + FnAddr &= ~1; snat lit = Literal(FnAddr); if(0==lit) { @@ -39,13 +41,22 @@ namespace ARM return; } - BL(lit,CC); + if (isThumb) { + verify (CC==CC_EQ); + BLX(lit, isThumb); + } else { + BL(lit,CC); + } } EAPI JUMP(unat FnAddr, ConditionCode CC=AL) { + bool isThumb = FnAddr & 1; + FnAddr &= ~1; + + verify(!isThumb); snat lit = Literal(FnAddr); /*if(0==lit) { @@ -62,8 +73,7 @@ namespace ARM BX(IP, CC); return; } - - B(lit,CC); // Note, wont work for THUMB*, have to use bx which is reg only ! + B(lit,CC); // Note, wont work for THUMB*, have to use bx which is reg only ! } diff --git a/core/arm_emitter/arm_emitter.h b/core/arm_emitter/arm_emitter.h index 25544261c..636cedf3d 100644 --- a/core/arm_emitter/arm_emitter.h +++ b/core/arm_emitter/arm_emitter.h @@ -34,7 +34,7 @@ namespace ARM #if defined(_DEBUG) || defined(DEBUG) - #define EAPI void + #define EAPI static void #define DECL_I \ u32 Instruction=0 diff --git a/core/build.h b/core/build.h index 45c83ed79..d495297d6 100755 --- a/core/build.h +++ b/core/build.h @@ -84,3 +84,8 @@ #error Invalid Target: TARGET_* not defined #endif +#ifdef HOST_NO_REC + #ifndef HOST_NO_AREC + #define HOST_NO_AREC 1 + #endif +#endif diff --git a/core/core.mk b/core/core.mk index b8fd49365..79b760bcc 100755 --- a/core/core.mk +++ b/core/core.mk @@ -29,6 +29,10 @@ ifndef NOT_ARM RZDCY_MODULES += rec-ARM/ endif +ifdef X86_REC + RZDCY_MODULES += rec-x86/ emitter/ +endif + ifndef NO_REND RZDCY_MODULES += rend/gles/ else diff --git a/core/deps/coreio/coreio.cpp b/core/deps/coreio/coreio.cpp index c9d0b351c..7b4a317af 100644 --- a/core/deps/coreio/coreio.cpp +++ b/core/deps/coreio/coreio.cpp @@ -18,7 +18,7 @@ #include #include -#if HOST_OS == OS_LINUX +#if HOST_OS == OS_LINUX || HOST_OS == OS_DARWIN #include #include #include diff --git a/core/emitter/types.h b/core/emitter/types.h index 2880a352c..a1277c121 100644 --- a/core/emitter/types.h +++ b/core/emitter/types.h @@ -1,9 +1,8 @@ #pragma once -#include "../types.h" - -/* - +#if 1 +#include "types.h" +#else //basic types typedef signed __int8 s8; typedef signed __int16 s16; @@ -54,4 +53,5 @@ using namespace std; #ifndef die #define die(reason) { printf("Fatal error : %s\n in %s -> %s : %d \n",reason,__FUNCTION__,__FILE__,__LINE__); dbgbreak;} -#endif \ No newline at end of file +#endif +#endif diff --git a/core/emitter/x86_emitter.cpp b/core/emitter/x86_emitter.cpp index 443b5dc30..5a2734854 100644 --- a/core/emitter/x86_emitter.cpp +++ b/core/emitter/x86_emitter.cpp @@ -3,6 +3,7 @@ #pragma warning(disable:4244) #pragma warning(disable:4245) +#include "../types.h" #include "x86_emitter.h" bool IsS8(u32 value) { @@ -183,6 +184,8 @@ x86_block_externs* x86_block::GetExterns() return rv; } + +#if 0 #include "windows.h" /*void x86_block::CopyTo(void* to) { @@ -194,6 +197,8 @@ x86_block_externs* x86_block::GetExterns() } */ +#endif + //wut ? void x86_block::ApplyPatches(u8* base) { @@ -409,7 +414,10 @@ void x86_block::Emit(x86_opcode_class op,x86_reg reg1,x86_reg reg2,u32 imm) //reg,mrm,imm, reg1 is written void x86_block::Emit(x86_opcode_class op,x86_reg reg,x86_ptr mem,u32 imm) { - ME_op_3_imm(op,reg,c_mrm(mem),imm); + //GCC bitches about using this directly. It doesn't complain for the other uses though + //go figure .... + x86_mrm_t mrm = c_mrm(mem); + ME_op_3_imm(op,reg,mrm,imm); } //reg,mrm,imm, reg1 is written @@ -449,19 +457,19 @@ u8 EncodeDisp(u32 disp,x86_mrm_t* to,u8 flags) verify(false); return 0; } -__declspec(dllexport) x86_mrm_t x86_mrm(x86_reg base) +/*__declspec(dllexport) */x86_mrm_t x86_mrm(x86_reg base) { return x86_mrm(base,NO_REG,sib_scale_1,0); } -__declspec(dllexport) x86_mrm_t x86_mrm(x86_reg base,x86_ptr disp) +/*__declspec(dllexport) */x86_mrm_t x86_mrm(x86_reg base,x86_ptr disp) { return x86_mrm(base,NO_REG,sib_scale_1,disp); } -__declspec(dllexport) x86_mrm_t x86_mrm(x86_reg index,x86_sib_scale scale,x86_ptr disp) +/*__declspec(dllexport) */x86_mrm_t x86_mrm(x86_reg index,x86_sib_scale scale,x86_ptr disp) { return x86_mrm(NO_REG,index,scale,disp); } -__declspec(dllexport) x86_mrm_t x86_mrm(x86_reg base,x86_reg index) +/*__declspec(dllexport) */x86_mrm_t x86_mrm(x86_reg base,x86_reg index) { return x86_mrm(base,index,sib_scale_1,0); } diff --git a/core/emitter/x86_emitter.h b/core/emitter/x86_emitter.h index 6e4d9b3f3..ecffcd327 100644 --- a/core/emitter/x86_emitter.h +++ b/core/emitter/x86_emitter.h @@ -193,7 +193,7 @@ typedef void* dyna_finalizeFP(void* ptr,u32 oldsize,u32 newsize); //define it here cus we use it on label type ;) class x86_block; // a label -struct __declspec(dllexport) x86_Label +struct /*__declspec(dllexport)*/ x86_Label { u32 target_opcode; u8 patch_sz; @@ -202,7 +202,7 @@ struct __declspec(dllexport) x86_Label void* GetPtr(); }; //An empty type that we will use as ptr type.This is ptr-reference -struct __declspec(dllexport) x86_ptr +struct /*__declspec(dllexport)*/ x86_ptr { union { @@ -216,7 +216,7 @@ struct __declspec(dllexport) x86_ptr } }; //This is ptr/imm (for call/jmp) -struct __declspec(dllexport) x86_ptr_imm +struct /*__declspec(dllexport)*/ x86_ptr_imm { union { @@ -255,11 +255,11 @@ struct x86_mrm_t u32 disp; }; -__declspec(dllexport) x86_mrm_t x86_mrm(x86_reg base); -__declspec(dllexport) x86_mrm_t x86_mrm(x86_reg base,x86_ptr disp); -__declspec(dllexport) x86_mrm_t x86_mrm(x86_reg base,x86_reg index); -__declspec(dllexport) x86_mrm_t x86_mrm(x86_reg index,x86_sib_scale scale,x86_ptr disp); -__declspec(dllexport) x86_mrm_t x86_mrm(x86_reg base,x86_reg index,x86_sib_scale scale,x86_ptr disp); +/*__declspec(dllexport)*/ x86_mrm_t x86_mrm(x86_reg base); +/*__declspec(dllexport)*/ x86_mrm_t x86_mrm(x86_reg base,x86_ptr disp); +/*__declspec(dllexport)*/ x86_mrm_t x86_mrm(x86_reg base,x86_reg index); +/*__declspec(dllexport)*/ x86_mrm_t x86_mrm(x86_reg index,x86_sib_scale scale,x86_ptr disp); +/*__declspec(dllexport)*/ x86_mrm_t x86_mrm(x86_reg base,x86_reg index,x86_sib_scale scale,x86_ptr disp); struct code_patch @@ -273,7 +273,7 @@ struct code_patch u32 offset; //offset in opcode stream :) }; -struct __declspec(dllexport) x86_block_externs +struct /*__declspec(dllexport)*/ x86_block_externs { void Apply(void* code_base); bool Modify(u32 offs,u8* dst); @@ -282,7 +282,7 @@ struct __declspec(dllexport) x86_block_externs }; //A block of x86 code :p -class __declspec(dllexport) x86_block +class /*__declspec(dllexport)*/ x86_block { private: void* _labels; @@ -303,9 +303,9 @@ public: ~x86_block(); void x86_buffer_ensure(u32 size); - void x86_block::write8(u32 value); - void x86_block::write16(u32 value); - void x86_block::write32(u32 value); + void write8(u32 value); + void write16(u32 value); + void write32(u32 value); //init things void Init(dyna_reallocFP* ral,dyna_finalizeFP* alf); @@ -332,45 +332,45 @@ public: //opcode Emitters //no param - void x86_block::Emit(x86_opcode_class op); + void Emit(x86_opcode_class op); //1 param //reg - void x86_block::Emit(x86_opcode_class op,x86_reg reg); + void Emit(x86_opcode_class op,x86_reg reg); //smrm - void x86_block::Emit(x86_opcode_class op,x86_ptr mem); + void Emit(x86_opcode_class op,x86_ptr mem); //mrm - void x86_block::Emit(x86_opcode_class op,x86_mrm_t mrm); + void Emit(x86_opcode_class op,x86_mrm_t mrm); //imm - void x86_block::Emit(x86_opcode_class op,u32 imm); + void Emit(x86_opcode_class op,u32 imm); //ptr_imm - void x86_block::Emit(x86_opcode_class op,x86_ptr_imm disp); + void Emit(x86_opcode_class op,x86_ptr_imm disp); //lbl - void x86_block::Emit(x86_opcode_class op,x86_Label* lbl); + void Emit(x86_opcode_class op,x86_Label* lbl); //2 param //reg,reg, reg1 is written - void x86_block::Emit(x86_opcode_class op,x86_reg reg1,x86_reg reg2); + void Emit(x86_opcode_class op,x86_reg reg1,x86_reg reg2); //reg,smrm, reg is written - void x86_block::Emit(x86_opcode_class op,x86_reg reg,x86_ptr mem); + void Emit(x86_opcode_class op,x86_reg reg,x86_ptr mem); //reg,mrm, reg is written - void x86_block::Emit(x86_opcode_class op,x86_reg reg1,x86_mrm_t mrm); + void Emit(x86_opcode_class op,x86_reg reg1,x86_mrm_t mrm); //reg,imm, reg is written - void x86_block::Emit(x86_opcode_class op,x86_reg reg,u32 imm); + void Emit(x86_opcode_class op,x86_reg reg,u32 imm); //smrm,reg, mem is written - void x86_block::Emit(x86_opcode_class op,x86_ptr mem,x86_reg reg); + void Emit(x86_opcode_class op,x86_ptr mem,x86_reg reg); //smrm,imm, mem is written - void x86_block::Emit(x86_opcode_class op,x86_ptr mem,u32 imm); + void Emit(x86_opcode_class op,x86_ptr mem,u32 imm); //mrm,reg, mrm is written - void x86_block::Emit(x86_opcode_class op,x86_mrm_t mrm,x86_reg reg); + void Emit(x86_opcode_class op,x86_mrm_t mrm,x86_reg reg); //mrm,imm, mrm is written - void x86_block::Emit(x86_opcode_class op,x86_mrm_t mrm,u32 imm); + void Emit(x86_opcode_class op,x86_mrm_t mrm,u32 imm); //3 param //reg,reg,imm, reg1 is written - void x86_block::Emit(x86_opcode_class op,x86_reg reg1,x86_reg reg2,u32 imm); + void Emit(x86_opcode_class op,x86_reg reg1,x86_reg reg2,u32 imm); //reg,mrm,imm, reg1 is written - void x86_block::Emit(x86_opcode_class op,x86_reg reg,x86_ptr mem,u32 imm); + void Emit(x86_opcode_class op,x86_reg reg,x86_ptr mem,u32 imm); //reg,mrm,imm, reg1 is written - void x86_block::Emit(x86_opcode_class op,x86_reg reg,x86_mrm_t mrm,u32 imm); + void Emit(x86_opcode_class op,x86_reg reg,x86_mrm_t mrm,u32 imm); }; diff --git a/core/emitter/x86_matcher.h b/core/emitter/x86_matcher.h index a1ec8bd41..9bcaa05fc 100644 --- a/core/emitter/x86_matcher.h +++ b/core/emitter/x86_matcher.h @@ -20,7 +20,7 @@ enum x86_op_params encoded_type pg_none = {pg_NONE}; -encoded_type __fastcall param_type(x86_Label* lbl) +encoded_type param_type(x86_Label* lbl) { encoded_type rv; //Return pg_MEM_Rel32/pg_MEM_Rel16/pg_MEM_Rel8 @@ -33,7 +33,7 @@ encoded_type __fastcall param_type(x86_Label* lbl) rv.ptr_type=1; return rv; } -encoded_type __fastcall param_type(x86_ptr_imm ptr) +encoded_type param_type(x86_ptr_imm ptr) { encoded_type rv; //Return pg_MEM_Rel32.Due to relocation we cant optimise to 16/8 in one pass ... @@ -43,7 +43,7 @@ encoded_type __fastcall param_type(x86_ptr_imm ptr) rv.ptr_type=0; return rv; } -encoded_type __fastcall param_type(x86_mrm_t& modrm) +encoded_type param_type(x86_mrm_t& modrm) { encoded_type rv; rv.modrm=modrm; @@ -51,7 +51,7 @@ encoded_type __fastcall param_type(x86_mrm_t& modrm) rv.type=pg_ModRM; return rv; } -encoded_type __fastcall param_type(x86_reg reg) +encoded_type param_type(x86_reg reg) { encoded_type rv; rv.reg=REG_ID(reg); @@ -65,7 +65,7 @@ encoded_type __fastcall param_type(x86_reg reg) return rv; } -encoded_type __fastcall param_type(u32 imm) +encoded_type param_type(u32 imm) { encoded_type rv; rv.imm=imm; @@ -82,7 +82,7 @@ encoded_type __fastcall param_type(u32 imm) return rv; } -void __fastcall Match_opcode(x86_block* block,const x86_opcode* ops,encoded_type pg1,encoded_type pg2,encoded_type pg3) +void Match_opcode(x86_block* block,const x86_opcode* ops,encoded_type pg1,encoded_type pg2,encoded_type pg3) { block->opcode_count++; const x86_opcode* match=0; diff --git a/core/emitter/x86_op_encoder.h b/core/emitter/x86_op_encoder.h index c77a1596b..0f3e9db9c 100644 --- a/core/emitter/x86_op_encoder.h +++ b/core/emitter/x86_op_encoder.h @@ -58,6 +58,11 @@ } */ +#include "build.h" + +#if BUILD_COMPILER == COMPILER_GCC + #define __fastcall BALLZZ!! +#endif enum enc_param @@ -168,7 +173,7 @@ struct encoded_type struct x86_opcode; -typedef void __fastcall x86_opcode_encoderFP(x86_block* block,const x86_opcode* op,encoded_type* p1,encoded_type* p2,u32 p3); +typedef void x86_opcode_encoderFP(x86_block* block,const x86_opcode* op,encoded_type* p1,encoded_type* p2,u32 p3); //enc_param_none is alower w/ params set to implicit registers (ie , mov eax,xxxx is enc_imm , pg1:pg_EAX , pg2:pg_imm @@ -185,7 +190,7 @@ struct x86_opcode }; //mod|reg|rm -void __fastcall encode_modrm(x86_block* block,encoded_type* mrm, u32 extra) +void encode_modrm(x86_block* block,encoded_type* mrm, u32 extra) { if (mrm->type != pg_ModRM) { @@ -208,7 +213,7 @@ void __fastcall encode_modrm(x86_block* block,encoded_type* mrm, u32 extra) } #ifdef X64 //x64 stuff -void __fastcall encode_rex(x86_block* block,encoded_type* mrm,u32 mrm_reg,u32 ofe=0) +void encode_rex(x86_block* block,encoded_type* mrm,u32 mrm_reg,u32 ofe=0) { u32 flags = (ofe>>3) & 1; //opcode field extension @@ -232,7 +237,7 @@ void __fastcall encode_rex(x86_block* block,encoded_type* mrm,u32 mrm_reg,u32 of //Encoding function (partially) specialised by templates to gain speed :) template < enc_param enc_1,enc_imm enc_2,u32 sz,x86_operand_size enc_op_size> -void __fastcall x86_encode_opcode_tmpl(x86_block* block, const x86_opcode* op, encoded_type* p1,encoded_type* p2,u32 p3) +void x86_encode_opcode_tmpl(x86_block* block, const x86_opcode* op, encoded_type* p1,encoded_type* p2,u32 p3) { //printf("Encoding : "); diff --git a/core/hw/aica/dsp.cpp b/core/hw/aica/dsp.cpp index 9d712876e..8d8be3814 100644 --- a/core/hw/aica/dsp.cpp +++ b/core/hw/aica/dsp.cpp @@ -20,7 +20,7 @@ See LICENSE & COPYRIGHT files further details */ -ALIGN(4096) dsp_t dsp; +DECL_ALIGN(4096) dsp_t dsp; #if HOST_OS==OS_WINDOWS && !defined(HOST_NO_REC) #include "emitter/x86_emitter.h" diff --git a/core/hw/aica/dsp.h b/core/hw/aica/dsp.h index ae007bfc5..e9e790d74 100644 --- a/core/hw/aica/dsp.h +++ b/core/hw/aica/dsp.h @@ -86,7 +86,7 @@ struct dsp_t bool dyndirty; }; -ALIGN(4096) +DECL_ALIGN(4096) extern dsp_t dsp; void dsp_init(); diff --git a/core/hw/arm7/arm7.cpp b/core/hw/arm7/arm7.cpp index 2ddb37c1d..228eb475c 100644 --- a/core/hw/arm7/arm7.cpp +++ b/core/hw/arm7/arm7.cpp @@ -121,7 +121,7 @@ typedef union //bool arm_FiqPending; -- not used , i use the input directly :) //bool arm_IrqPending; -ALIGN(8) reg_pair arm_Reg[RN_ARM_REG_COUNT]; +DECL_ALIGN(8) reg_pair arm_Reg[RN_ARM_REG_COUNT]; void CPUSwap(u32 *a, u32 *b) { @@ -188,7 +188,7 @@ void armt_init(); //void CreateTables(); void arm_Init() { -#if !defined(HOST_NO_REC) +#if !defined(HOST_NO_AREC) armt_init(); #endif //CreateTables(); @@ -398,7 +398,7 @@ void FlushCache(); void arm_Reset() { -#if !defined(HOST_NO_REC) +#if !defined(HOST_NO_AREC) FlushCache(); #endif Arm7Enabled = false; @@ -512,8 +512,16 @@ void update_armintc() reg[INTR_PEND].I=e68k_out && armFiqEnable; } -#ifdef HOST_NO_REC -void arm_Run(u32 CycleCount) { arm_Run_(CycleCount); } +void libAICA_TimeStep(); + +#ifdef HOST_NO_AREC +void arm_Run(u32 CycleCount) { + for (int i=0;i<32;i++) + { + arm_Run_(CycleCount/32); + libAICA_TimeStep(); + } +} #else extern "C" void CompileCode(); @@ -734,15 +742,16 @@ u8* icPtr; u8* ICache; const u32 ICacheSize=1024*1024; -#if HOST_OS != OS_LINUX +#if HOST_OS == OS_WINDOWS u8 ARM7_TCB[ICacheSize+4096]; #elif HOST_OS == OS_LINUX -u8 ARM7_TCB[ICacheSize+4096] -#ifndef DYNA_OPROF -__attribute__((section(".text"))) -#endif - ; +u8 ARM7_TCB[ICacheSize+4096] __attribute__((section(".text"))); + +#elif HOST_OS==OS_DARWIN +u8 ARM7_TCB[ICacheSize+4096] __attribute__((section("__TEXT, .text"))); +#else +#error ARM7_TCB ALLOC #endif #include "arm_emitter/arm_emitter.h" @@ -789,7 +798,7 @@ u32 DYNACALL DoMemOp(u32 addr,u32 data) { u32 rv=0; -#if HOST_CPU==CPU_X86 && !defined(HOST_NO_REC) +#if HOST_CPU==CPU_X86 && !defined(HOST_NO_AREC) addr=virt_arm_reg(0); data=virt_arm_reg(1); #endif @@ -809,7 +818,7 @@ u32 DYNACALL DoMemOp(u32 addr,u32 data) arm_WriteMem32(addr,data); } - #if HOST_CPU==CPU_X86 && !defined(HOST_NO_REC) + #if HOST_CPU==CPU_X86 && !defined(HOST_NO_AREC) virt_arm_reg(0)=rv; #endif @@ -1531,9 +1540,17 @@ void *armGetEmitPtr() return NULL; } +#if HOST_OS==OS_DARWIN +#include +extern "C" void armFlushICache(void *code, void *pEnd) { + sys_dcache_flush(code, (u8*)pEnd - (u8*)code + 1); + sys_icache_invalidate(code, (u8*)pEnd - (u8*)code + 1); +} +#else extern "C" void armFlushICache(void *bgn, void *end) { __clear_cache(bgn, end); } +#endif void armv_imm_to_reg(u32 regn, u32 imm) @@ -1594,7 +1611,6 @@ void armv_MOV32(eReg regn, u32 imm) #endif // HOST_CPU -void libAICA_TimeStep(); //Run a timeslice for ARMREC //CycleCount is pretty much fixed to (512*32) for now (might change to a diff constant, but will be constant) void arm_Run(u32 CycleCount) @@ -2121,10 +2137,16 @@ void armt_init() //align to next page .. ICache = (u8*)(((unat)ARM7_TCB+4095)& ~4095); + #if HOST_OS==OS_DARWIN + //Can't just mprotect on iOS + munmap(ICache, ICacheSize); + ICache = (u8*)mmap(ICache, ICacheSize, PROT_READ | PROT_WRITE | PROT_EXEC, MAP_FIXED | MAP_PRIVATE | MAP_ANON, 0, 0); + #endif + #if HOST_OS == OS_WINDOWS DWORD old; VirtualProtect(ICache,ICacheSize,PAGE_EXECUTE_READWRITE,&old); -#elif HOST_OS == OS_LINUX +#elif HOST_OS == OS_LINUX || HOST_OS == OS_DARWIN printf("\n\t ARM7_TCB addr: %p | from: %p | addr here: %p\n", ICache, ARM7_TCB, armt_init); diff --git a/core/hw/arm7/virt_arm.cpp b/core/hw/arm7/virt_arm.cpp index 857082603..f9aef686b 100644 --- a/core/hw/arm7/virt_arm.cpp +++ b/core/hw/arm7/virt_arm.cpp @@ -1,6 +1,6 @@ #include "virt_arm.h" -#if HOST_CPU==CPU_X86 && !defined(HOST_NO_REC) +#if HOST_CPU==CPU_X86 && !defined(HOST_NO_AREC) #define C_CORE @@ -311,7 +311,7 @@ void virt_arm_init() VARM::virt_arm_init(); } -u32 __fastcall virt_arm_op(u32 opcode) +u32 DYNACALL virt_arm_op(u32 opcode) { return VARM::virt_arm_op(opcode); } @@ -321,4 +321,4 @@ u32& virt_arm_reg(u32 id) return VARM::arm_Reg[id].I; } -#endif \ No newline at end of file +#endif diff --git a/core/hw/maple/maple_devs.cpp b/core/hw/maple/maple_devs.cpp index 2a2b6cf4b..3bfe9f531 100755 --- a/core/hw/maple/maple_devs.cpp +++ b/core/hw/maple/maple_devs.cpp @@ -547,7 +547,7 @@ struct maple_sega_vmu: maple_base } } config->SetImage(lcd_data_decoded); -#ifndef TARGET_PANDORA +#if !defined(TARGET_PANDORA) && HOST_OS != OS_DARWIN push_vmu_screen(lcd_data_decoded); #endif #if 0 diff --git a/core/hw/mem/_vmem.cpp b/core/hw/mem/_vmem.cpp index 32125ea42..61cfdb79a 100644 --- a/core/hw/mem/_vmem.cpp +++ b/core/hw/mem/_vmem.cpp @@ -546,7 +546,13 @@ error: void* _nvmem_alloc_mem() { -#ifndef _ANDROID + +#if HOST_OS == OS_DARWIN + string path = GetPath("/dcnzorz_mem"); + fd = open(path.c_str(),O_CREAT|O_RDWR|O_TRUNC,S_IRWXU|S_IRWXG|S_IRWXO); + unlink(path.c_str()); + verify(ftruncate(fd,RAM_SIZE + VRAM_SIZE +ARAM_SIZE)==0); +#elif !defined(_ANDROID) fd = shm_open("/dcnzorz_mem", O_CREAT | O_EXCL | O_RDWR,S_IREAD | S_IWRITE); shm_unlink("/dcnzorz_mem"); if (fd==-1) @@ -570,6 +576,7 @@ error: u32 sz= 512*1024*1024 + sizeof(Sh4RCB) + ARAM_SIZE + 0x10000; void* rv=mmap(0, sz, PROT_NONE, MAP_PRIVATE | MAP_ANON, -1, 0); + verify(rv != NULL); munmap(rv,sz); return (u8*)rv + 0x10000 - unat(rv)%0x10000;//align to 64 KB (Needed for linaro mmap not to extend to next region) } @@ -583,6 +590,11 @@ void _vmem_bm_pagefail(void** ptr,u32 PAGE_SZ); u32 pagecnt; void _vmem_bm_reset() { + #if HOST_OS == OS_DARWIN + //On iOS we allways allocate all of the mapping table + mprotect(p_sh4rcb, sizeof(p_sh4rcb->fpcb), PROT_READ | PROT_WRITE); + return; + #endif pagecnt=0; #if HOST_OS==OS_WINDOWS @@ -590,8 +602,12 @@ void _vmem_bm_reset() #else mprotect(p_sh4rcb, sizeof(p_sh4rcb->fpcb), PROT_NONE); madvise(p_sh4rcb,sizeof(p_sh4rcb->fpcb),MADV_DONTNEED); + #ifdef MADV_REMOVE madvise(p_sh4rcb,sizeof(p_sh4rcb->fpcb),MADV_REMOVE); - //madvise(p_sh4rcb,sizeof(p_sh4rcb->fpcb),MADV_FREE); + #else + //OSX, IOS + madvise(p_sh4rcb,sizeof(p_sh4rcb->fpcb),MADV_FREE); + #endif #endif printf("Freeing fpcb\n"); @@ -631,6 +647,10 @@ bool _vmem_reserve() verify((sizeof(Sh4RCB)%PAGE_SIZE)==0); virt_ram_base=(u8*)_nvmem_alloc_mem(); + + if (virt_ram_base==0) + return false; + p_sh4rcb=(Sh4RCB*)virt_ram_base; #if HOST_OS==OS_WINDOWS @@ -644,9 +664,6 @@ bool _vmem_reserve() #endif virt_ram_base+=sizeof(Sh4RCB); - if (virt_ram_base==0) - return false; - //Area 0 //[0x00000000 ,0x00800000) -> unused unused_buffer(0x00000000,0x00800000); diff --git a/core/hw/pvr/Renderer_if.cpp b/core/hw/pvr/Renderer_if.cpp index f10547b81..9f334d11c 100644 --- a/core/hw/pvr/Renderer_if.cpp +++ b/core/hw/pvr/Renderer_if.cpp @@ -178,6 +178,8 @@ TA_context* read_frame(const char* file, u8* vram_ref) { ctx->tad.thd_data += t; fclose(fw); + + return ctx; } bool rend_frame(TA_context* ctx, bool draw_osd) { @@ -244,7 +246,8 @@ void* rend_thread(void* p) if (!renderer->Init()) die("rend->init() failed\n"); - renderer->Resize(640, 480); + //we don't know if this is true, so let's not speculate here + //renderer->Resize(640, 480); for(;;) { @@ -258,6 +261,11 @@ cThread rthd(rend_thread,0); bool pend_rend = false; +void rend_resize(int width, int height) { + renderer->Resize(width, height); +} + + void rend_start_render() { pend_rend = false; @@ -311,7 +319,9 @@ void rend_end_render() { #if 1 //also disabled the printf, it takes quite some time ... #if HOST_OS!=OS_WINDOWS && !(defined(_ANDROID) || defined(TARGET_PANDORA)) - if (!re.state) printf("Render > Extended time slice ...\n"); + //too much console spam. + //TODO: how about a counter? + //if (!re.state) printf("Render > Extended time slice ...\n"); #endif #endif @@ -333,8 +343,8 @@ void rend_end_wait() bool rend_init() { -#if NO_REND - renderer = rend_norend(); +#ifdef NO_REND + renderer = rend_norend(); #else #if HOST_OS == OS_WINDOWS @@ -345,7 +355,7 @@ bool rend_init() #endif -#if !defined(_ANDROID) +#if !defined(_ANDROID) && HOST_OS != OS_DARWIN rthd.Start(); #endif diff --git a/core/hw/pvr/Renderer_if.h b/core/hw/pvr/Renderer_if.h index d95fcecb3..ea1ebda9e 100644 --- a/core/hw/pvr/Renderer_if.h +++ b/core/hw/pvr/Renderer_if.h @@ -14,9 +14,15 @@ void rend_end_render(); void rend_end_wait(); void rend_set_fb_scale(float x,float y); - +void rend_resize(int width, int height); void rend_text_invl(vram_block* bl); +#ifdef GLuint +GLuint +#else +u32 +#endif +GetTexture(TSP tsp,TCW tcw); /////// diff --git a/core/hw/pvr/ta_vtx.cpp b/core/hw/pvr/ta_vtx.cpp index e1e9594ce..a129752de 100644 --- a/core/hw/pvr/ta_vtx.cpp +++ b/core/hw/pvr/ta_vtx.cpp @@ -8,7 +8,6 @@ #include "ta.h" #include "ta_ctx.h" #include "pvr_mem.h" -#include "rend/gles/gles.h" #include "Renderer_if.h" u32 ta_type_lut[256]; @@ -84,10 +83,10 @@ PolyParam* CurrentPP=&nullPP; List* CurrentPPlist; //TA state vars -ALIGN(4) static u8 FaceBaseColor[4]; -ALIGN(4) static u8 FaceOffsColor[4]; -ALIGN(4) static u32 SFaceBaseColor; -ALIGN(4) static u32 SFaceOffsColor; +DECL_ALIGN(4) static u8 FaceBaseColor[4]; +DECL_ALIGN(4) static u8 FaceOffsColor[4]; +DECL_ALIGN(4) static u32 SFaceBaseColor; +DECL_ALIGN(4) static u32 SFaceOffsColor; diff --git a/core/hw/sh4/dyna/blockmanager.cpp b/core/hw/sh4/dyna/blockmanager.cpp index 2ed79ea73..ae8d40ca1 100644 --- a/core/hw/sh4/dyna/blockmanager.cpp +++ b/core/hw/sh4/dyna/blockmanager.cpp @@ -87,24 +87,24 @@ blkmap_t blkmap; u32 bm_gc_luc,bm_gcf_luc; -#define FPCA(x) ((DynarecCodeEntry*&)sh4rcb.fpcb[(x>>1)&(8*1024*1024-1)]) +#define FPCA(x) ((DynarecCodeEntryPtr&)sh4rcb.fpcb[(x>>1)&(8*1024*1024-1)]) -DynarecCodeEntry* DYNACALL bm_GetCode(u32 addr) +DynarecCodeEntryPtr DYNACALL bm_GetCode(u32 addr) { //rdv_FailedToFindBlock_pc=addr; - DynarecCodeEntry* rv=FPCA(addr); + DynarecCodeEntryPtr rv=(DynarecCodeEntryPtr)FPCA(addr); - return rv; + return (DynarecCodeEntryPtr)rv; } -DynarecCodeEntry* DYNACALL bm_GetCode2(u32 addr) +DynarecCodeEntryPtr DYNACALL bm_GetCode2(u32 addr) { - return bm_GetCode(addr); + return (DynarecCodeEntryPtr)bm_GetCode(addr); } RuntimeBlockInfo* DYNACALL bm_GetBlock(u32 addr) { - DynarecCodeEntry* cde=bm_GetCode(addr); + DynarecCodeEntryPtr cde=bm_GetCode(addr); if (cde==ngen_FailedToFindBlock) return 0; @@ -155,7 +155,7 @@ void bm_AddBlock(RuntimeBlockInfo* blk) blkmap.insert(blk); - verify(bm_GetCode(blk->addr)==ngen_FailedToFindBlock); + verify((void*)bm_GetCode(blk->addr)==(void*)ngen_FailedToFindBlock); FPCA(blk->addr)=blk->code; #ifdef DYNA_OPROF @@ -382,10 +382,13 @@ void bm_Reset() _vmem_bm_reset(); +#if HOST_OS == OS_DARWIN + //lazy allocation isn't working on iOS for (u32 i=0;i<(8*1024*1024);i++) { - //sh4rcb.fpcb[i]=(void*)ngen_FailedToFindBlock; + sh4rcb.fpcb[i]=(void*)ngen_FailedToFindBlock; } +#endif for (size_t i=0; icode; } -DynarecCodeEntry* DYNACALL rdv_FailedToFindBlock(u32 pc) +DynarecCodeEntryPtr DYNACALL rdv_FailedToFindBlock(u32 pc) { //printf("rdv_FailedToFindBlock ~ %08X\n",pc); next_pc=pc; @@ -269,25 +268,25 @@ u32 DYNACALL rdv_DoInterrupts(void* block_cpde) return next_pc; } -DynarecCodeEntry* DYNACALL rdv_BlockCheckFail(u32 pc) +DynarecCodeEntryPtr DYNACALL rdv_BlockCheckFail(u32 pc) { next_pc=pc; recSh4_ClearCache(); return rdv_CompilePC(); } -DynarecCodeEntry* rdv_FindCode() +DynarecCodeEntryPtr rdv_FindCode() { - DynarecCodeEntry* rv=bm_GetCode(next_pc); + DynarecCodeEntryPtr rv=bm_GetCode(next_pc); if (rv==ngen_FailedToFindBlock) return 0; return rv; } -DynarecCodeEntry* rdv_FindOrCompile() +DynarecCodeEntryPtr rdv_FindOrCompile() { - DynarecCodeEntry* rv=bm_GetCode(next_pc); + DynarecCodeEntryPtr rv=bm_GetCode(next_pc); if (rv==ngen_FailedToFindBlock) rv=rdv_CompilePC(); @@ -324,7 +323,7 @@ void* DYNACALL rdv_LinkBlock(u8* code,u32 dpc) next_pc=rbi->NextBlock; } - DynarecCodeEntry* rv=rdv_FindOrCompile(); + DynarecCodeEntryPtr rv=rdv_FindOrCompile(); bool do_link=bm_GetBlock(code)==rbi; @@ -388,6 +387,10 @@ void recSh4_Reset(bool Manual) Sh4_int_Reset(Manual); } +#if HOST_OS == OS_DARWIN +#include +#endif + void recSh4_Init() { printf("recSh4 Init\n"); @@ -407,14 +410,19 @@ void recSh4_Init() //align to next page .. CodeCache = (u8*)(((unat)SH4_TCB+4095)& ~4095); +#if HOST_OS == OS_DARWIN + munmap(CodeCache, CODE_SIZE*2); + CodeCache = (u8*)mmap(CodeCache, 2*CODE_SIZE, PROT_READ | PROT_WRITE | PROT_EXEC, MAP_FIXED | MAP_PRIVATE | MAP_ANON, 0, 0); +#endif + #if HOST_OS == OS_WINDOWS DWORD old; VirtualProtect(CodeCache,CODE_SIZE*2,PAGE_EXECUTE_READWRITE,&old); -#elif HOST_OS == OS_LINUX +#elif HOST_OS == OS_LINUX || HOST_OS == OS_DARWIN - printf("\n\t CodeCache addr: %p | from: %p | addr here: %p\n", CodeCache, SH4_TCB, recSh4_Init); + printf("\n\t CodeCache addr: %p | from: %p | addr here: %p\n", CodeCache, CodeCache, recSh4_Init); - if (mprotect(CodeCache, CODE_SIZE*2, PROT_EXEC|PROT_READ|PROT_WRITE)) + if (mprotect(CodeCache, CODE_SIZE*2, PROT_READ|PROT_WRITE|PROT_EXEC)) { perror("\n\tError,Couldn’t mprotect CodeCache!"); verify(false); diff --git a/core/hw/sh4/dyna/ngen.h b/core/hw/sh4/dyna/ngen.h index 1a7592fa8..0748e8ec0 100644 --- a/core/hw/sh4/dyna/ngen.h +++ b/core/hw/sh4/dyna/ngen.h @@ -49,13 +49,14 @@ #define CODE_SIZE (4*1024*1024) -#if HOST_OS==OS_LINUX -extern "C" { -#endif //alternative emit ptr, set to 0 to use the main buffer extern u32* emit_ptr; extern u8* CodeCache; +#if HOST_OS==OS_LINUX || HOST_OS==OS_DARWIN +extern "C" { +#endif + void emit_Write32(u32 data); void emit_Skip(u32 sz); u32 emit_FreeSpace(); @@ -63,15 +64,15 @@ void* emit_GetCCPtr(); void emit_SetBaseAddr(); //Called from ngen_FailedToFindBlock -DynarecCodeEntry* DYNACALL rdv_FailedToFindBlock(u32 pc); +DynarecCodeEntryPtr DYNACALL rdv_FailedToFindBlock(u32 pc); //Called when a block check failed, and the block needs to be invalidated -DynarecCodeEntry* DYNACALL rdv_BlockCheckFail(u32 pc); +DynarecCodeEntryPtr DYNACALL rdv_BlockCheckFail(u32 pc); //Called to compile code @pc -DynarecCodeEntry* rdv_CompilePC(); +DynarecCodeEntryPtr rdv_CompilePC(); //Returns 0 if there is no code @pc, code ptr otherwise -DynarecCodeEntry* rdv_FindCode(); +DynarecCodeEntryPtr rdv_FindCode(); //Finds or compiles code @pc -DynarecCodeEntry* rdv_FindOrCompile(); +DynarecCodeEntryPtr rdv_FindOrCompile(); //code -> pointer to code of block, dpc -> if dynamic block, pc. if cond, 0 for next, 1 for branch void* DYNACALL rdv_LinkBlock(u8* code,u32 dpc); @@ -120,6 +121,6 @@ void ngen_CC_Finish(shil_opcode* op); RuntimeBlockInfo* ngen_AllocateBlock(); -#if HOST_OS==OS_LINUX +#if HOST_OS==OS_LINUX || HOST_OS==OS_DARWIN } #endif diff --git a/core/hw/sh4/dyna/regalloc.h b/core/hw/sh4/dyna/regalloc.h index 7e0d32cd8..1affa2e1a 100644 --- a/core/hw/sh4/dyna/regalloc.h +++ b/core/hw/sh4/dyna/regalloc.h @@ -411,6 +411,8 @@ struct RegAlloc return all_spans[sid]; } } + die("Failed to find span"); + return NULL; } void flush_span(u32 sid) diff --git a/core/hw/sh4/dyna/shil.cpp b/core/hw/sh4/dyna/shil.cpp index f86ba267b..f1a7b058a 100644 --- a/core/hw/sh4/dyna/shil.cpp +++ b/core/hw/sh4/dyna/shil.cpp @@ -2,6 +2,8 @@ Some WIP optimisation stuff and maby helper functions for shil */ +#include + #include "types.h" #include "shil.h" #include "decoder.h" @@ -1020,8 +1022,6 @@ bool UpdateSR(); #include "shil_canonical.h" #endif -#include - string name_reg(u32 reg) { stringstream ss; diff --git a/core/hw/sh4/sh4_core.h b/core/hw/sh4/sh4_core.h index 0ca976877..1adfaeb9d 100644 --- a/core/hw/sh4/sh4_core.h +++ b/core/hw/sh4/sh4_core.h @@ -39,7 +39,7 @@ union DoubleReg f32 sgl[2]; }; -INLINE f64 GetDR(u32 n) +static INLINE f64 GetDR(u32 n) { #ifdef TRACE if (n>7) @@ -53,7 +53,7 @@ INLINE f64 GetDR(u32 n) return t.dbl; } -INLINE f64 GetXD(u32 n) +static INLINE f64 GetXD(u32 n) { #ifdef TRACE if (n>7) @@ -67,7 +67,7 @@ INLINE f64 GetXD(u32 n) return t.dbl; } -INLINE void SetDR(u32 n,f64 val) +static INLINE void SetDR(u32 n,f64 val) { #ifdef TRACE if (n>7) @@ -81,7 +81,7 @@ INLINE void SetDR(u32 n,f64 val) fr[(n<<1) | 0]=t.sgl[1]; } -INLINE void SetXD(u32 n,f64 val) +static INLINE void SetXD(u32 n,f64 val) { #ifdef TRACE if (n>7) diff --git a/core/hw/sh4/sh4_if.h b/core/hw/sh4/sh4_if.h index 8dddb8302..aaf61f04c 100644 --- a/core/hw/sh4/sh4_if.h +++ b/core/hw/sh4/sh4_if.h @@ -215,7 +215,7 @@ struct fpscr_t }; struct { - u32 nil : 2+1+1+1+1+4+8+1; + u32 _nil : 2+1+1+1+1+4+8+1; u32 PR_SZ : 2; u32 nilz : 11; }; diff --git a/core/hw/sh4/sh4_interpreter.h b/core/hw/sh4/sh4_interpreter.h index 0b8f4bd10..e66026457 100644 --- a/core/hw/sh4/sh4_interpreter.h +++ b/core/hw/sh4/sh4_interpreter.h @@ -52,13 +52,13 @@ void ExecuteDelayslot(); void ExecuteDelayslot_RTE(); -#if HOST_OS==OS_LINUX +#if HOST_OS==OS_LINUX || HOST_OS==OS_DARWIN extern "C" { #endif int UpdateSystem(); int UpdateSystem_INTC(); -#if HOST_OS==OS_LINUX +#if HOST_OS==OS_LINUX || HOST_OS==OS_DARWIN } #endif \ No newline at end of file diff --git a/core/hw/sh4/sh4_interrupts.cpp b/core/hw/sh4/sh4_interrupts.cpp index d8fe1584c..43b9cc9b1 100644 --- a/core/hw/sh4/sh4_interrupts.cpp +++ b/core/hw/sh4/sh4_interrupts.cpp @@ -42,11 +42,11 @@ struct InterptSourceList_Entry InterptSourceList_Entry InterruptSourceList[28]; //Maps siid -> EventID -ALIGN(64) u16 InterruptEnvId[32]= { 0 }; +DECL_ALIGN(64) u16 InterruptEnvId[32] = { 0 }; //Maps piid -> 1< #include #endif - + + #include + map x11_keymap; #endif -#if !defined(ANDROID) +#if !defined(ANDROID) && HOST_OS != OS_DARWIN #include #include #include @@ -140,6 +142,7 @@ void SetupInput() lt[port]=0; } +#if HOST_OS != OS_DARWIN if (true) { #ifdef TARGET_PANDORA const char* device = "/dev/input/event4"; @@ -160,10 +163,10 @@ void SetupInput() else perror("evdev open"); } - +#endif // Open joystick device JoyFD = open("/dev/input/js0",O_RDONLY); - +#if HOST_OS != OS_DARWIN if(JoyFD>=0) { int AxisCount,ButtonCount; @@ -187,13 +190,16 @@ void SetupInput() printf("Using Xbox 360 map\n"); } } +#endif } bool HandleKb(u32 port) { - struct input_event ie; +#if HOST_OS != OS_DARWIN if (kbfd < 0) return false; + input_event ie; + #if defined(TARGET_GCW0) #define KEY_A 0x1D @@ -284,17 +290,18 @@ bool HandleKb(u32 port) { printf("type %i key %i state %i\n", ie.type, ie.code, ie.value); } #endif - +#endif +return true; } bool HandleJoystick(u32 port) { - - struct js_event JE; // Joystick must be connected if(JoyFD<0) return false; +#if HOST_OS != OS_DARWIN + struct js_event JE; while(read(JoyFD,&JE,sizeof(JE))==sizeof(JE)) if (JE.number %d: %d\n",e.xkey.keycode, dc_key, x11_dc_buttons ); + } + break; + + + { + printf("KEYRELEASE\n"); + } + break; + + } + } + } + #endif } void os_SetWindowText(const char * text) @@ -472,7 +514,7 @@ void os_SetWindowText(const char * text) if (0==x11_win || 0==x11_disp || 1) printf("%s\n",text); #if defined(SUPPORT_X11) - else { + else if (x11_win) { XChangeProperty((Display*)x11_disp, (Window)x11_win, XInternAtom((Display*)x11_disp, "WM_NAME", False), //WM_NAME, XInternAtom((Display*)x11_disp, "UTF8_STRING", False), //UTF8_STRING, @@ -490,6 +532,7 @@ void os_CreateWindow() #if defined(SUPPORT_X11) if (cfgLoadInt("pvr","nox11",0)==0) { + XInitThreads(); // X11 variables Window x11Window = 0; Display* x11Display = 0; @@ -520,15 +563,51 @@ void os_CreateWindow() int depth = CopyFromParent; #if !defined(GLES) - int attr32[] = { GLX_RGBA, GLX_DEPTH_SIZE, 32, GLX_DOUBLEBUFFER, GLX_STENCIL_SIZE, 8, None }; - int attr24[] = { GLX_RGBA, GLX_DEPTH_SIZE, 24, GLX_DOUBLEBUFFER, GLX_STENCIL_SIZE, 8, None }; + // Get a matching FB config + static int visual_attribs[] = + { + GLX_X_RENDERABLE , True, + GLX_DRAWABLE_TYPE , GLX_WINDOW_BIT, + GLX_RENDER_TYPE , GLX_RGBA_BIT, + GLX_X_VISUAL_TYPE , GLX_TRUE_COLOR, + GLX_RED_SIZE , 8, + GLX_GREEN_SIZE , 8, + GLX_BLUE_SIZE , 8, + GLX_ALPHA_SIZE , 8, + GLX_DEPTH_SIZE , 24, + GLX_STENCIL_SIZE , 8, + GLX_DOUBLEBUFFER , True, + //GLX_SAMPLE_BUFFERS , 1, + //GLX_SAMPLES , 4, + None + }; + + int glx_major, glx_minor; + + // FBConfigs were added in GLX version 1.3. + if ( !glXQueryVersion( x11Display, &glx_major, &glx_minor ) || + ( ( glx_major == 1 ) && ( glx_minor < 3 ) ) || ( glx_major < 1 ) ) + { + printf("Invalid GLX version"); + exit(1); + } + + int fbcount; + GLXFBConfig* fbc = glXChooseFBConfig(x11Display, x11Screen, visual_attribs, &fbcount); + if (!fbc) + { + printf( "Failed to retrieve a framebuffer config\n" ); + exit(1); + } + printf( "Found %d matching FB configs.\n", fbcount ); + + GLXFBConfig bestFbc = fbc[ 0 ]; + XFree( fbc ); + + // Get a visual + XVisualInfo *vi = glXGetVisualFromFBConfig( x11Display, bestFbc ); + printf( "Chosen visual ID = 0x%x\n", vi->visualid ); - XVisualInfo* vi = glXChooseVisual(x11Display, 0, attr32); - if (!vi) - vi = glXChooseVisual(x11Display, 0, attr24); - - if (!vi) - die("Failed to glXChooseVisual"); depth = vi->depth; x11Visual = vi; @@ -580,8 +659,31 @@ void os_CreateWindow() XMapWindow(x11Display, x11Window); #if !defined(GLES) - x11_glc = glXCreateContext(x11Display, x11Visual, NULL, GL_TRUE); - //glXMakeCurrent(x11Display, x11Window, glc); + + #define GLX_CONTEXT_MAJOR_VERSION_ARB 0x2091 + #define GLX_CONTEXT_MINOR_VERSION_ARB 0x2092 + typedef GLXContext (*glXCreateContextAttribsARBProc)(Display*, GLXFBConfig, GLXContext, Bool, const int*); + + glXCreateContextAttribsARBProc glXCreateContextAttribsARB = 0; + glXCreateContextAttribsARB = (glXCreateContextAttribsARBProc) + glXGetProcAddressARB( (const GLubyte *) "glXCreateContextAttribsARB" ); + + verify( glXCreateContextAttribsARB != 0 ); + + int context_attribs[] = { + GLX_CONTEXT_MAJOR_VERSION_ARB, 3, + GLX_CONTEXT_MINOR_VERSION_ARB, 1, + GLX_CONTEXT_FLAGS_ARB, GLX_CONTEXT_DEBUG_BIT_ARB, + GLX_CONTEXT_PROFILE_MASK_ARB, GLX_CONTEXT_CORE_PROFILE_BIT_ARB, + None + }; + + x11_glc = glXCreateContextAttribsARB( x11Display, bestFbc, 0, True, context_attribs); + XSync( x11Display, False ); + + if (!x11_glc) { + die("Failed to create GL3.1 context\n"); + } #endif #endif XFlush(x11Display); @@ -681,8 +783,9 @@ void clean_exit(int sig_num) { void init_sound() { - if((audio_fd=open("/dev/dsp",O_WRONLY))<0) + if((audio_fd=open("/dev/dsp",O_WRONLY))<0) { printf("Couldn't open /dev/dsp.\n"); + } else { printf("sound enabled, dsp openned for write\n"); @@ -711,9 +814,12 @@ int main(int argc, wchar* argv[]) signal(SIGKILL, clean_exit); init_sound(); +#else + void os_InitAudio(); + os_InitAudio(); #endif -#if defined(USES_HOMEDIR) +#if defined(USES_HOMEDIR) && HOST_OS != OS_DARWIN string home = (string)getenv("HOME"); if(home.c_str()) { @@ -727,6 +833,27 @@ int main(int argc, wchar* argv[]) SetHomeDir("."); #endif + #if defined(SUPPORT_X11) + x11_keymap[113] = DPad_Left; + x11_keymap[114] = DPad_Right; + + x11_keymap[111] = DPad_Up; + x11_keymap[116] = DPad_Down; + + x11_keymap[52] = Btn_Y; + x11_keymap[53] = Btn_X; + x11_keymap[54] = Btn_B; + x11_keymap[55] = Btn_A; + + /* + //TODO: Fix sliders + x11_keymap[38] = DPad_Down; + x11_keymap[39] = DPad_Down; + */ + + x11_keymap[36] = Btn_Start; + #endif + printf("Home dir is: %s\n",GetPath("/").c_str()); common_linux_setup(); @@ -746,12 +873,20 @@ int main(int argc, wchar* argv[]) return 0; } +u32 alsa_Push(void* frame, u32 samples, bool wait); u32 os_Push(void* frame, u32 samples, bool wait) { -#ifdef TARGET_PANDORA - write(audio_fd, frame, samples*4); -#endif -return 1; + #ifndef TARGET_PANDORA + int audio_fd = -1; + #endif + + if (audio_fd > 0) { + write(audio_fd, frame, samples*4); + } else { + return alsa_Push(frame, samples, wait); + } + + return 1; } #endif diff --git a/core/linux/common.cpp b/core/linux/common.cpp index 68a061923..422689aa4 100644 --- a/core/linux/common.cpp +++ b/core/linux/common.cpp @@ -1,7 +1,11 @@ #include "types.h" #include "cfg/cfg.h" -#if HOST_OS==OS_LINUX +#if HOST_OS==OS_LINUX || HOST_OS == OS_DARWIN +#if HOST_OS == OS_DARWIN + #define _XOPEN_SOURCE 1 + #define __USE_GNU 1 +#endif #include #include //#include @@ -15,70 +19,74 @@ #include #include "hw/sh4/dyna/blockmanager.h" -#if defined(_ANDROID) -#include -#if 0 -typedef struct ucontext_t { -unsigned long uc_flags; -struct ucontext_t *uc_link; -struct { -void *p; -int flags; -size_t size; -} sstack_data; -struct sigcontext uc_mcontext; -/* some 2.6.x kernel has fp data here after a few other fields -* we don't use them for now... -*/ -} ucontext_t; -#endif -#endif - -#if HOST_CPU == CPU_ARM -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.arm_pc) -#elif HOST_CPU == CPU_MIPS -#if 0 && _ANDROID -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.sc_pc) -#else -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.pc) -#endif -#elif HOST_CPU == CPU_X86 -#if 0 && _ANDROID -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.eip) -#else -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.gregs[REG_EIP]) -#endif -#else -#error fix ->pc support -#endif +#include "linux/context.h" #include "hw/sh4/dyna/ngen.h" +bool ngen_Rewrite(unat& addr,unat retadr,unat acc); u32* ngen_readm_fail_v2(u32* ptr,u32* regs,u32 saddr); bool VramLockedWrite(u8* address); bool BM_LockedWrite(u8* address); -void fault_handler (int sn, siginfo_t * si, void *ctxr) -{ - bool dyna_cde=((u32)GET_PC_FROM_CONTEXT(ctxr)>(u32)CodeCache) && ((u32)GET_PC_FROM_CONTEXT(ctxr)<(u32)(CodeCache+CODE_SIZE)); +#if HOST_OS == OS_DARWIN +void sigill_handler(int sn, siginfo_t * si, void *segfault_ctx) { + + rei_host_context_t ctx; + + context_from_segfault(&ctx, segfault_ctx); - ucontext_t* ctx=(ucontext_t*)ctxr; + unat pc = (unat)ctx.pc; + bool dyna_cde = (pc>(unat)CodeCache) && (pc<(unat)(CodeCache + CODE_SIZE)); + + printf("SIGILL @ %08X, fault_handler+0x%08X ... %08X -> was not in vram, %d\n", pc, pc - (u32)sigill_handler, (unat)si->si_addr, dyna_cde); + + printf("Entering infiniloop"); + + for (;;); + printf("PC is used here %08X\n", pc); +} +#endif + +void fault_handler (int sn, siginfo_t * si, void *segfault_ctx) +{ + rei_host_context_t ctx; + + context_from_segfault(&ctx, segfault_ctx); + + bool dyna_cde = ((unat)ctx.pc>(unat)CodeCache) && ((unat)ctx.pc<(unat)(CodeCache + CODE_SIZE)); + + //ucontext_t* ctx=(ucontext_t*)ctxr; //printf("mprot hit @ ptr 0x%08X @@ code: %08X, %d\n",si->si_addr,ctx->uc_mcontext.arm_pc,dyna_cde); if (VramLockedWrite((u8*)si->si_addr) || BM_LockedWrite((u8*)si->si_addr)) return; -#ifndef HOST_NO_REC - else if (dyna_cde) - { - GET_PC_FROM_CONTEXT(ctxr)=(u32)ngen_readm_fail_v2((u32*)GET_PC_FROM_CONTEXT(ctxr),(u32*)&(ctx->uc_mcontext.arm_r0),(unat)si->si_addr); - } -#endif + #if !defined(HOST_NO_REC) + #if HOST_CPU==CPU_ARM + else if (dyna_cde) + { + ctx.pc = (u32)ngen_readm_fail_v2((u32*)ctx.pc, ctx.r, (unat)si->si_addr); + + context_to_segfault(&ctx, segfault_ctx); + } + #elif HOST_CPU==CPU_X86 + else if (ngen_Rewrite((unat&)ctx.pc, *(unat*)ctx.esp, ctx.eax)) + { + //remove the call from call stack + ctx.esp += 4; + //restore the addr from eax to ecx so it's valid again + ctx.ecx = ctx.eax; + + context_to_segfault(&ctx, segfault_ctx); + } + #else + #error JIT: Not supported arch + #endif + #endif else { - printf("SIGSEGV @ fault_handler+0x%08X ... %08X -> was not in vram\n",GET_PC_FROM_CONTEXT(ctxr)-(u32)fault_handler,si->si_addr); + printf("SIGSEGV @ %08X (fault_handler+0x%08X) ... %08X -> was not in vram\n", ctx.pc, ctx.pc - (unat)fault_handler, si->si_addr); die("segfault"); -// asm volatile("bkpt 0x0001\n\t"); signal(SIGSEGV, SIG_DFL); } } @@ -91,6 +99,14 @@ void install_fault_handler (void) sigemptyset(&act.sa_mask); act.sa_flags = SA_SIGINFO; sigaction(SIGSEGV, &act, &segv_oact); + +#if HOST_OS == OS_DARWIN + //this is broken on osx/ios/mach in general + sigaction(SIGBUS, &act, &segv_oact); + + act.sa_sigaction = sigill_handler; + sigaction(SIGILL, &act, &segv_oact); +#endif } @@ -118,8 +134,8 @@ cResetEvent::cResetEvent(bool State,bool Auto) { //sem_init((sem_t*)hEvent, 0, State?1:0); verify(State==false&&Auto==true); - mutx = PTHREAD_MUTEX_INITIALIZER; - cond = PTHREAD_COND_INITIALIZER; + pthread_mutex_init(&mutx, NULL); + pthread_cond_init(&cond, NULL); } cResetEvent::~cResetEvent() { @@ -172,7 +188,7 @@ void VArray2::LockRegion(u32 offset,u32 size) void print_mem_addr() { FILE *ifp, *ofp; - char *mode = "r"; + const char *mode = "r"; char outputFilename[] = "/data/data/com.reicast.emulator/files/mem_alloc.txt"; ifp = fopen("/proc/self/maps", mode); @@ -218,6 +234,12 @@ double os_GetSeconds() return a.tv_sec-tvs_base+a.tv_usec/1000000.0; } +#if HOST_OS != OS_LINUX +void os_DebugBreak() +{ + __builtin_trap(); +} +#endif void enable_runfast() { diff --git a/core/linux/context.cpp b/core/linux/context.cpp new file mode 100644 index 000000000..ae7939911 --- /dev/null +++ b/core/linux/context.cpp @@ -0,0 +1,74 @@ +#include "context.h" + +#if defined(_ANDROID) + #include +#else + #if HOST_OS == OS_DARWIN + #define _XOPEN_SOURCE 1 + #define __USE_GNU 1 + #endif + + #include +#endif + + +////// + +#define MCTX(p) (((ucontext_t *)(segfault_ctx))->uc_mcontext p) +template +void bicopy(Ta& rei, Tb& seg, bool to_segfault) { + if (to_segfault) { + seg = rei; + } + else { + rei = seg; + } +} + +void context_segfault(rei_host_context_t* reictx, void* segfault_ctx, bool to_segfault) { + +#if HOST_CPU == CPU_ARM + #if HOST_OS == OS_LINUX + bicopy(reictx->pc, MCTX(.arm_pc), to_segfault); + u32* r =(u32*) &MCTX(.arm_r0); + + for (int i = 0; i < 15; i++) + bicopy(reictx->r[i], r[i], to_segfault); + + #elif HOST_OS == OS_DARWIN + bicopy(reictx->pc, MCTX(->__ss.__pc), to_segfault); + + for (int i = 0; i < 15; i++) + bicopy(reictx->r[i], MCTX(->__ss.__r[i]), to_segfault); + #else + #error HOST_OS + #endif +#elif HOST_CPU == CPU_X86 + #if HOST_OS == OS_LINUX + bicopy(reictx->pc, MCTX(.gregs[REG_EIP]), to_segfault); + bicopy(reictx->esp, MCTX(.gregs[REG_ESP]), to_segfault); + bicopy(reictx->eax, MCTX(.gregs[REG_EAX]), to_segfault); + bicopy(reictx->ecx, MCTX(.gregs[REG_ECX]), to_segfault); + #elif HOST_OS == OS_DARWIN + bicopy(reictx->pc, MCTX(->__ss.__eip), to_segfault); + bicopy(reictx->esp, MCTX(->__ss.__esp), to_segfault); + bicopy(reictx->eax, MCTX(->__ss.__eax), to_segfault); + bicopy(reictx->ecx, MCTX(->__ss.__ecx), to_segfault); + #else + #error HOST_OS + #endif +#elif HOST_CPU == CPU_MIPS + bicopy(reictx->pc, MCTX(.pc), to_segfault); +#else + #error Unsupported HOST_CPU +#endif + +} + +void context_from_segfault(rei_host_context_t* reictx, void* segfault_ctx) { + context_segfault(reictx, segfault_ctx, false); +} + +void context_to_segfault(rei_host_context_t* reictx, void* segfault_ctx) { + context_segfault(reictx, segfault_ctx, true); +} \ No newline at end of file diff --git a/core/linux/context.h b/core/linux/context.h new file mode 100644 index 000000000..7c53a4a86 --- /dev/null +++ b/core/linux/context.h @@ -0,0 +1,17 @@ +#include "types.h" + + +struct rei_host_context_t { + unat pc; + +#if HOST_CPU == CPU_X86 + u32 eax; + u32 ecx; + u32 esp; +#elif HOST_CPU == CPU_ARM + u32 r[15]; +#endif +}; + +void context_from_segfault(rei_host_context_t* reictx, void* segfault_ctx); +void context_to_segfault(rei_host_context_t* reictx, void* segfault_ctx); \ No newline at end of file diff --git a/core/linux/nixprof.cpp b/core/linux/nixprof.cpp index 0ccc57b5c..7e5f90547 100644 --- a/core/linux/nixprof.cpp +++ b/core/linux/nixprof.cpp @@ -33,46 +33,7 @@ #include #include "deps/libelf/elf.h" -#if defined(_ANDROID) -#include -#if 0 -typedef struct ucontext_t -{ - unsigned long uc_flags; - struct ucontext_t *uc_link; - struct - { - void *p; - int flags; - size_t size; - } sstack_data; - - struct sigcontext uc_mcontext; - /* some 2.6.x kernel has fp data here after a few other fields - * we don't use them for now... - */ -} ucontext_t; -#endif -#include -#endif - -#if HOST_CPU == CPU_ARM -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.arm_pc) -#elif HOST_CPU == CPU_MIPS -#if 0 && _ANDROID -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.sc_pc) -#else -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.pc) -#endif -#elif HOST_CPU == CPU_X86 -#if 0 && _ANDROID -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.eip) -#else -#define GET_PC_FROM_CONTEXT(c) (((ucontext_t *)(c))->uc_mcontext.gregs[REG_EIP]) -#endif -#else -#error fix ->pc support -#endif +#include "context.h" /** @file CallStack_Android.h @@ -100,13 +61,15 @@ void sample_Syms(u8* data,u32 len) void prof_handler (int sn, siginfo_t * si, void *ctxr) { - ucontext_t* ctx=(ucontext_t*)ctxr; + rei_host_context_t ctx; + context_from_segfault(&ctx, ctxr); + int thd=-1; if (pthread_self()==thread[0]) thd=0; else if (pthread_self()==thread[1]) thd=1; else return; - prof_address[thd]=(void*)GET_PC_FROM_CONTEXT(ctx); + prof_address[thd] = (void*)ctx.pc; } @@ -314,6 +277,8 @@ void* prof(void *ptr) fclose(maps); fclose(prof_out); + + return 0; } void sample_Start(int freq) diff --git a/core/nullDC.cpp b/core/nullDC.cpp index 0cd29315b..953d1b6fd 100755 --- a/core/nullDC.cpp +++ b/core/nullDC.cpp @@ -66,7 +66,7 @@ int GetFile(char *szFileName, char *szParse=0,u32 flags=0) //strcpy(szFileName,ofn.lpstrFile); } #else - strcpy(szFileName,GetPath("/discs/game.gdi").c_str()); + strcpy(szFileName,GetPath("/game.chd").c_str()); #endif #endif } @@ -131,7 +131,7 @@ void plugins_Reset(bool Manual) void* webui_th(void* p) { - #if (HOST_OS == OS_WINDOWS || HOST_OS == OS_LINUX) && !defined(TARGET_PANDORA) + #if (HOST_OS == OS_WINDOWS || HOST_OS == OS_LINUX) && !defined(TARGET_PANDORA) && defined(WEBUI) webui_start(); #endif @@ -169,10 +169,15 @@ int dc_init(int argc,wchar* argv[]) int rv= 0; - - if (settings.bios.UseReios || !LoadRomFiles(GetPath("/data/"))) +#if HOST_OS != OS_DARWIN + #define DATA_PATH "/data/" +#else + #define DATA_PATH "/" +#endif + + if (settings.bios.UseReios || !LoadRomFiles(GetPath(DATA_PATH))) { - if (!LoadHle(GetPath("/data/"))) + if (!LoadHle(GetPath(DATA_PATH))) return -3; else printf("Did not load bios, using reios\n"); diff --git a/core/oslib/alsa_audiostream.cpp b/core/oslib/alsa_audiostream.cpp index 055fe778d..801d6bc7b 100644 --- a/core/oslib/alsa_audiostream.cpp +++ b/core/oslib/alsa_audiostream.cpp @@ -4,14 +4,37 @@ #include "cfg/cfg.h" -#if 0 && HOST_OS==OS_LINUX && !defined(TARGET_NACL32) +#if HOST_OS==OS_LINUX && !defined(TARGET_NACL32) && !defined(ANDROID) -#if !defined(ANDROID) +#if 1 #include #include snd_pcm_t *handle; +u32 alsa_Push(void* frame, u32 samples, bool wait) { + + snd_pcm_nonblock(handle, wait ? 0 : 1); + + int rc = snd_pcm_writei(handle, frame, samples); + if (rc == -EPIPE) + { + /* EPIPE means underrun */ + fprintf(stderr, "ALSA: underrun occurred\n"); + snd_pcm_prepare(handle); + alsa_Push(frame, samples * 8, wait); + } + else if (rc < 0) + { + fprintf(stderr, "ALSA: error from writei: %s\n", snd_strerror(rc)); + } + else if (rc != samples) + { + fprintf(stderr, "ALSA: short write, wrote %d frames of %d\n", rc, samples); + } + return 1; +} +#if 0 u8 Tempbuffer[8192*4]; void* AudioThread(void*) { @@ -44,6 +67,7 @@ void* AudioThread(void*) } cThread aud_thread(AudioThread,0); +#endif void os_InitAudio() { @@ -123,7 +147,7 @@ void os_InitAudio() } /* Set period size to settings.aica.BufferSize frames. */ - frames = settings.aica.BufferSize; + frames = 2 * 1024;//settings.aica.BufferSize; rc=snd_pcm_hw_params_set_period_size_near(handle, params, &frames, &dir); if (rc < 0) { @@ -145,8 +169,6 @@ void os_InitAudio() fprintf(stderr, "Unable to set hw parameters: %s\n", snd_strerror(rc)); return; } - - aud_thread.Start(); } void os_TermAudio() diff --git a/core/oslib/oslib.h b/core/oslib/oslib.h index 8d9df70ff..08ca94a23 100644 --- a/core/oslib/oslib.h +++ b/core/oslib/oslib.h @@ -16,7 +16,7 @@ void WriteSample(s16 right, s16 left); #include #endif -u32 INLINE bitscanrev(u32 v) +u32 static INLINE bitscanrev(u32 v) { #if (BUILD_COMPILER==COMPILER_GCC) return 31-__builtin_clz(v); diff --git a/core/rec-ARM/arm_dyna.cpp b/core/rec-ARM/arm_dyna.cpp index 7cfff89cd..1b8a4fc7a 100755 --- a/core/rec-ARM/arm_dyna.cpp +++ b/core/rec-ARM/arm_dyna.cpp @@ -2,6 +2,7 @@ #include #include "types.h" +#ifndef HOST_NO_REC #include "hw/sh4/sh4_opcode_list.h" #include "hw/sh4/sh4_mmr.h" @@ -55,10 +56,17 @@ struct DynaRBI: RuntimeBlockInfo #include // for cache flushing. #endif -#if !defined(ARMCC) +#if HOST_OS == OS_DARWIN +#include void CacheFlush(void* code, void* pEnd) { -#ifndef _ANDROID + sys_dcache_flush(code, (u8*)pEnd - (u8*)code + 1); + sys_icache_invalidate(code, (u8*)pEnd - (u8*)code + 1); +} +#elif !defined(ARMCC) +void CacheFlush(void* code, void* pEnd) +{ +#if !defined(_ANDROID) && HOST_OS!=OS_DARWIN __clear_cache((void*)code, pEnd); #else void* start=code; @@ -249,7 +257,11 @@ EmitAPI StoreSh4Reg64(eReg Rt, shil_param Sh4_Reg, eCC CC=CC_AL) #include "hw/sh4/dyna/regalloc.h" +#if HOST_OS == OS_DARWIN +eReg alloc_regs[]={r5,r6,r7,r10,(eReg)-1}; +#else eReg alloc_regs[]={r5,r6,r7,r10,r11,(eReg)-1}; +#endif eFSReg alloc_fpu[]={f16,f17,f18,f19,f20,f21,f22,f23, f24,f25,f26,f27,f28,f29,f30,f31,(eFSReg)-1}; @@ -535,14 +547,14 @@ void ngen_Binary(shil_opcode* op, BinaryOP dtop,BinaryOPImm dtopimm, bool has_im dtop(reg.mapg(op->rd),reg.mapg(op->rs1), rs2, CC_AL); } -void ngen_fp_bin(shil_opcode* op, FPBinOP fpop) +void ngen_fp_bin(shil_opcode* op, const FPBinOP fpop) { verify(op->rs1.is_r32f()); verify(op->rs2.is_r32f()); fpop(reg.mapfs(op->rd),reg.mapfs(op->rs1),reg.mapfs(op->rs2),CC_AL); } -void ngen_fp_una(shil_opcode* op, FPUnOP fpop) +void ngen_fp_una(shil_opcode* op, const FPUnOP fpop) { verify(op->rd.is_r32f()); verify(op->rs1.is_r32f()); @@ -1979,7 +1991,7 @@ __default: void ngen_Compile(RuntimeBlockInfo* block,bool force_checks, bool reset, bool staging,bool optimise) { //printf("Compile: %08X, %d, %d\n",block->addr,staging,optimise); - block->code=(DynarecCodeEntry*)EMIT_GET_PTR(); + block->code=(DynarecCodeEntryPtr)EMIT_GET_PTR(); //StoreImms(r0,r1,(u32)&last_run_block,(u32)code); //useful when code jumps to random locations ... ++blockno; @@ -2026,7 +2038,11 @@ void ngen_Compile(RuntimeBlockInfo* block,bool force_checks, bool reset, bool st cyc&=~3; } +#if HOST_OS == OS_DARWIN + SUB(r11,r11,cyc,true,CC_AL); +#else SUB(rfp_r9,rfp_r9,cyc,true,CC_AL); +#endif CALL((u32)intc_sched, CC_LE); //compile the block's opcodes @@ -2217,3 +2233,5 @@ RuntimeBlockInfo* ngen_AllocateBlock() { return new DynaRBI(); }; + +#endif diff --git a/core/rec-ARM/ngen_arm.S b/core/rec-ARM/ngen_arm.S index df90fc2de..2d10c0d64 100644 --- a/core/rec-ARM/ngen_arm.S +++ b/core/rec-ARM/ngen_arm.S @@ -1,5 +1,7 @@ @@ +#include "build.h" + .arm .align 8 @@ -7,14 +9,21 @@ .equ BM_BLOCKLIST_MASK, 65532 @FFFC .equ CPU_RATIO, 5 +#if HOST_OS == OS_DARWIN +#define CSYM(n) _##n +#define HIDDEN(n) +#else +#define CSYM(n) n +#define HIDDEN(n) .hidden CSYM(n) +#endif @@@@@@@@@@ some helpers @@@@@@@@@@ -.global do_sqw_nommu_area_3 -.hidden do_sqw_nommu_area_3 +.global CSYM(do_sqw_nommu_area_3) +HIDDEN(do_sqw_nommu_area_3) @r0: addr @r1: sq_both -do_sqw_nommu_area_3: +CSYM(do_sqw_nommu_area_3): add r3,r1,#0x0C000000 @ get ram ptr from r1, part 1 and r2,r0,#0x20 @ SQ# selection, isolate ubfx r0,r0,#5,#19 @ get ram offset @@ -25,24 +34,24 @@ vldm r1,{d0-d3} vstm r3,{d0-d3} bx lr -.global TAWriteSQ -.hidden TAWriteSQ +.global CSYM(TAWriteSQ) +HIDDEN(TAWriteSQ) @r0: addr @r1: sq_both -TAWriteSQ: +CSYM(TAWriteSQ): BIC R3, R0, #0xFE000000 @clear unused bits AND R0, R0, #0x20 @SQ#, isolate CMP R3, #0x800000 @TA write? ADD R0, R1, R0 @SQ#, add to SQ ptr -BCC _Z13ta_vtx_data32Pv @TA write? +BCC CSYM(_Z13ta_vtx_data32Pv) @TA write? -TAWriteSQ_yuv: +CSYM(TAWriteSQ_yuv): CMP R3, #0x1000000 @Yuv write ? -BCS TAWriteSQ_vram +BCS CSYM(TAWriteSQ_vram) MOV R1, #1 -B _Z8YUV_dataPjj +B CSYM(_Z8YUV_dataPjj) -TAWriteSQ_vram: @vram write .. +CSYM(TAWriteSQ_vram): @vram write .. #ifdef TARGET_IPHONE bkpt #0 #else @@ -56,56 +65,59 @@ vldm r1,{d0-d3} vstm r3,{d0-d3} bx lr + +#ifndef HOST_NO_REC + @@@@@@@@@@ ngen_LinkBlock_*****_stub @@@@@@@@@@ -.global ngen_LinkBlock_Generic_stub -.hidden ngen_LinkBlock_Generic_stub -ngen_LinkBlock_Generic_stub: +.global CSYM(ngen_LinkBlock_Generic_stub) +HIDDEN(ngen_LinkBlock_Generic_stub) +CSYM(ngen_LinkBlock_Generic_stub): mov r1,r4 @ djump/pc -> in case we need it .. - b ngen_LinkBlock_Shared_stub + b CSYM(ngen_LinkBlock_Shared_stub) -.global ngen_LinkBlock_cond_Branch_stub -.hidden ngen_LinkBlock_cond_Branch_stub -ngen_LinkBlock_cond_Branch_stub: +.global CSYM(ngen_LinkBlock_cond_Branch_stub) +HIDDEN(ngen_LinkBlock_cond_Branch_stub) +CSYM(ngen_LinkBlock_cond_Branch_stub): mov r1,#1 - b ngen_LinkBlock_Shared_stub + b CSYM(ngen_LinkBlock_Shared_stub) -.global ngen_LinkBlock_cond_Next_stub -.hidden ngen_LinkBlock_cond_Next_stub -ngen_LinkBlock_cond_Next_stub: +.global CSYM(ngen_LinkBlock_cond_Next_stub) +HIDDEN(ngen_LinkBlock_cond_Next_stub) +CSYM(ngen_LinkBlock_cond_Next_stub): mov r1,#0 - b ngen_LinkBlock_Shared_stub + b CSYM(ngen_LinkBlock_Shared_stub) -.global ngen_LinkBlock_Shared_stub -.hidden ngen_LinkBlock_Shared_stub -ngen_LinkBlock_Shared_stub: +.global CSYM(ngen_LinkBlock_Shared_stub) +HIDDEN(ngen_LinkBlock_Shared_stub) +CSYM(ngen_LinkBlock_Shared_stub): mov r0,lr sub r0,#4 @go before the call - bl rdv_LinkBlock + bl CSYM(rdv_LinkBlock) bx r0 @@@@@@@@@@ ngen_FailedToFindBlock_ @@@@@@@@@@ -.global ngen_FailedToFindBlock_ -.hidden ngen_FailedToFindBlock_ -ngen_FailedToFindBlock_: +.global CSYM(ngen_FailedToFindBlock_) +HIDDEN(ngen_FailedToFindBlock_) +CSYM(ngen_FailedToFindBlock_): mov r0,r4 - bl rdv_FailedToFindBlock + bl CSYM(rdv_FailedToFindBlock) bx r0 @@@@@@@@@@ ngen_blockcheckfail @@@@@@@@@@ -.global ngen_blockcheckfail -.hidden ngen_blockcheckfail -ngen_blockcheckfail: - bl rdv_BlockCheckFail +.global CSYM(ngen_blockcheckfail) +HIDDEN(ngen_blockcheckfail) +CSYM(ngen_blockcheckfail): + bl CSYM(rdv_BlockCheckFail) bx r0 @@ -118,40 +130,48 @@ ngen_blockcheckfail: -.global ngen_mainloop -.hidden ngen_mainloop -ngen_mainloop: +.global CSYM(ngen_mainloop) +HIDDEN(ngen_mainloop) +CSYM(ngen_mainloop): push { r4-r12,lr } +#if HOST_OS == OS_DARWIN + mov r11, #SH4_TIMESLICE @ load cycle counter +#else mov r9, #SH4_TIMESLICE @ load cycle counter +#endif mov r8, r0 @Load context ldr r4, [r8,#-184] @load pc - b no_update @Go to mainloop ! + b CSYM(no_update) @Go to mainloop ! @this code is here for fall-through behavior of do_iter -.global intc_sched -.hidden intc_sched -intc_sched: @ next_pc _MUST_ be on ram + .global CSYM(intc_sched) + HIDDEN(intc_sched) +CSYM(intc_sched): @ next_pc _MUST_ be on ram +#if HOST_OS == OS_DARWIN + add r11,r11,#SH4_TIMESLICE +#else add r9,r9,#SH4_TIMESLICE +#endif mov r4,lr - bl UpdateSystem + bl CSYM(UpdateSystem) mov lr,r4 cmp r0,#0 bxeq lr @faster than bxeq r4 (as it should, call stack cache) do_iter: mov r0,r4 - bl rdv_DoInterrupts + bl CSYM(rdv_DoInterrupts) mov r4,r0 -.global no_update -.hidden no_update -no_update: @ next_pc _MUST_ be on r4 *R4 NOT R0 anymore* +.global CSYM(no_update) +HIDDEN(no_update) +CSYM(no_update): @ next_pc _MUST_ be on r4 *R4 NOT R0 anymore* sub r2,r8,#33816576 ubfx r1,r4,#1,#23 @@ -167,22 +187,26 @@ bx lr end_ngen_mainloop: @@@@@@@@@@ ngen_mainloop @@@@@@@@@@ -.global arm_compilecode -.hidden arm_compilecode -arm_compilecode: -bl CompileCode -b arm_dispatch +.global CSYM(arm_compilecode) +HIDDEN(arm_compilecode) +CSYM(arm_compilecode): +bl CSYM(CompileCode) +b CSYM(arm_dispatch) #ifdef TARGET_IPHONE -Xarm_Reg: .word arm_Reg -XEntryPoints: .word EntryPoints +Xarm_Reg: .word CSYM(arm_Reg) +XEntryPoints: .word CSYM(EntryPoints) #endif -.global arm_mainloop -.hidden arm_mainloop -arm_mainloop: @(cntx,lookup_base,cycles) +.global CSYM(arm_mainloop) +HIDDEN(arm_mainloop) +CSYM(arm_mainloop): @(cntx,lookup_base,cycles) +#if HOST_OS == OS_DARWIN +push {r4,r5,r8,r11,lr} +#else push {r4,r5,r8,r9,lr} +#endif #ifdef TARGET_IPHONE ldr r8,Xarm_Reg @load cntx @@ -195,11 +219,11 @@ push {r4,r5,r8,r9,lr} ldr r5,[r8,#192] @load cycle count add r5,r0 @add cycles for this timeslice - b arm_dispatch + b CSYM(arm_dispatch) -.global arm_dispatch -.hidden arm_dispatch -arm_dispatch: +.global CSYM(arm_dispatch) +HIDDEN(arm_dispatch) +CSYM(arm_dispatch): #ifdef TARGET_IPHONE ldrd r0,r1,[r8,#184] @load: Next PC, interrupt #else @@ -213,21 +237,25 @@ arm_dispatch: ldr pc,[r4,r2,lsl #2] arm_dofiq: - bl CPUFiq - b arm_dispatch + bl CSYM(CPUFiq) + b CSYM(arm_dispatch) -.global arm_exit -.hidden arm_exit -arm_exit: +.global CSYM(arm_exit) +HIDDEN(arm_exit) +CSYM(arm_exit): str r5,[r8,#192] @if timeslice is over, save remaining cycles - pop {r4,r5,r8,r9,pc} +#if HOST_OS == OS_DARWIN + pop {r4,r5,r8,r11,pc} +#else + pop {r4,r5,r8,r9,pc} +#endif @@@@@@ @matrix mul #ifndef _ANDROID -.global ftrv_asm -.hidden ftrv_asm -ftrv_asm: +.global CSYM(ftrv_asm) +HIDDEN(ftrv_asm) +CSYM(ftrv_asm): @r0=dst,r1=vec,r2=mtx @@ -244,9 +272,9 @@ vstm r0,{d4,d5} bx lr -.global fipr_asm -.hidden fipr_asm -fipr_asm: +.global CSYM(fipr_asm) +HIDDEN(fipr_asm) +CSYM(fipr_asm): @ vdot @ idp=fr[n+0]*fr[m+0]; @@ -268,3 +296,5 @@ vmov r0,s0 bx lr #endif + +#endif diff --git a/core/rec-x86/lin86_asm.S b/core/rec-x86/lin86_asm.S new file mode 100644 index 000000000..612cc4e89 --- /dev/null +++ b/core/rec-x86/lin86_asm.S @@ -0,0 +1,158 @@ +.section .text +.intel_syntax noprefix + + +.extern rdv_LinkBlock +.globl p_sh4rcb +.globl gas_offs +.globl rdv_FailedToFindBlock +.globl cycle_counter +.globl loop_no_update +.globl intc_sched +.globl bm_GetCode +.globl cycle_counter +.globl UpdateSystem +.globl rdv_DoInterrupts +.globl rdv_BlockCheckFail + +########################################### + +.globl ngen_LinkBlock_Shared_stub +.type ngen_LinkBlock_Shared_stub, @function + +ngen_LinkBlock_Shared_stub: + pop ecx + sub ecx,5 + call rdv_LinkBlock + jmp eax + + + +########################################### + +.globl ngen_LinkBlock_cond_Next_stub +.type ngen_LinkBlock_cond_Next_stub, @function + +ngen_LinkBlock_cond_Next_stub: + mov edx,0 + jmp ngen_LinkBlock_Shared_stub + + + +########################################### + +.globl ngen_LinkBlock_cond_Branch_stub +.type ngen_LinkBlock_cond_Branch_stub, @function + +ngen_LinkBlock_cond_Branch_stub: + mov edx,1 + jmp ngen_LinkBlock_Shared_stub + + +########################################### + +.globl ngen_LinkBlock_Generic_stub +.type ngen_LinkBlock_Generic_stub, @function + +# u32 gas_offs=offsetof(Sh4RCB,cntx.jdyn); +ngen_LinkBlock_Generic_stub: + mov edx,p_sh4rcb + add edx,gas_offs + mov edx,[edx] + jmp ngen_LinkBlock_Shared_stub + + + + +########################################### + +.globl ngen_FailedToFindBlock_ +.type ngen_FailedToFindBlock_, @function + +ngen_FailedToFindBlock_: + mov ecx,esi + call rdv_FailedToFindBlock + jmp eax + + + +########################################### +#define SH4_TIMESLICE 448 + +.globl ngen_mainloop +.type ngen_mainloop, @function + +ngen_mainloop: + # quick hack to maintain 16-byte alignment + push esi + push esi + push esi + + push esi + push edi + push ebp + push ebx + + mov ecx,0xA0000000 + mov dword ptr cycle_counter, 448 #SH4_TIMESLICE + + mov dword ptr loop_no_update,offset no_update + mov dword ptr intc_sched,offset intc_sched_offs + + mov eax,0 + +# next_pc _MUST_ be on ecx +no_update: + mov esi,ecx + call _Z10bm_GetCodej #bm_GetCode + jmp eax + +intc_sched_offs: + add dword ptr cycle_counter, 448 #SH4_TIMESLICE + call UpdateSystem + cmp eax,0 + jnz do_iter + ret + +do_iter: + pop ecx + call rdv_DoInterrupts + mov ecx,eax +# cmp byte ptr [sh4_int_bCpuRun],0 +# jz cleanup + jmp no_update + +cleanup: + pop ebx + pop ebp + pop edi + pop esi + + # quick hack to maintain 16-byte alignment + pop esi + pop esi + pop esi + + ret + + + +########################################### + +.globl ngen_blockcheckfail +.type ngen_blockcheckfail, @function + +ngen_blockcheckfail: + call rdv_BlockCheckFail + jmp eax + + +########################################### + +.globl ngen_blockcheckfail2 +.type ngen_blockcheckfail2, @function + +ngen_blockcheckfail2: + int 3 + call rdv_BlockCheckFail + jmp eax diff --git a/core/rec-x86/win86_driver.cpp b/core/rec-x86/win86_driver.cpp new file mode 100644 index 000000000..0e419aba9 --- /dev/null +++ b/core/rec-x86/win86_driver.cpp @@ -0,0 +1,790 @@ +#include "types.h" + +#ifndef HOST_NO_REC +#include "win86_ngen.h" + + + +struct DynaRBI: RuntimeBlockInfo +{ + x86_block_externs* reloc_info; + + virtual ~DynaRBI() { if (reloc_info) reloc_info->Free(); } + + virtual u32 Relink(); + virtual void Relocate(void* dst) + { + reloc_info->Apply(dst); + } +}; + +x86_block* x86e; + +u32 cycle_counter; + +void* loop_no_update; +void* intc_sched; + +bool sse_1=true; +bool sse_2=true; +bool sse_3=true; +bool ssse_3=true; +bool mmx=true; + +void DetectCpuFeatures() +{ + static bool detected=false; + if (detected) return; + detected=true; + +#if HOST_OS==OS_WINDOWS + __try + { + __asm addps xmm0,xmm0 + } + __except(1) + { + sse_1=false; + } + + __try + { + __asm addpd xmm0,xmm0 + } + __except(1) + { + sse_2=false; + } + + __try + { + __asm addsubpd xmm0,xmm0 + } + __except(1) + { + sse_3=false; + } + + __try + { + __asm phaddw xmm0,xmm0 + } + __except(1) + { + ssse_3=false; + } + + + __try + { + __asm paddd mm0,mm1 + __asm emms; + } + __except(1) + { + mmx=false; + } + #endif +} + + +#define CSC_SIZE 64 +struct csc_et +{ + u32 pc; + void* code; +}; +csc_et csc[CSC_SIZE<32?32:CSC_SIZE]; + + +#define CSC_SHIFT 1 +u32 csc_hash(u32 addr) +{ + return (addr>>CSC_SHIFT)&(CSC_SIZE-1); +} + +u32 csc_mode=0; + +u32 csc_sidx=1; + +x86_reg alloc_regs[]={EBX,EBP,ESI,EDI,NO_REG}; +x86_reg xmm_alloc_regs[]={XMM7,XMM6,XMM5,XMM4,NO_REG}; +f32 DECL_ALIGN(16) thaw_regs[4]; + + +void x86_reg_alloc::Preload(u32 reg,x86_reg nreg) +{ + x86e->Emit(op_mov32,nreg,GetRegPtr(reg)); +} +void x86_reg_alloc::Writeback(u32 reg,x86_reg nreg) +{ + x86e->Emit(op_mov32,GetRegPtr(reg),nreg); +} + +void x86_reg_alloc::Preload_FPU(u32 reg,x86_reg nreg) +{ + x86e->Emit(op_movss,nreg,GetRegPtr(reg)); +} +void x86_reg_alloc::Writeback_FPU(u32 reg,x86_reg nreg) +{ + x86e->Emit(op_movss,GetRegPtr(reg),nreg); +} +#ifdef PROF2 +extern u32 flsh; +#endif + +void x86_reg_alloc::FreezeXMM() +{ + x86_reg* fpreg=xmm_alloc_regs; + f32* slpc=thaw_regs; + while(*fpreg!=-1) + { + if (SpanNRegfIntr(current_opid,*fpreg)) + x86e->Emit(op_movss,slpc++,*fpreg); + fpreg++; + } +#ifdef PROF2 + x86e->Emit(op_add32,&flsh,1); +#endif +} + +void x86_reg_alloc::ThawXMM() +{ + x86_reg* fpreg=xmm_alloc_regs; + f32* slpc=thaw_regs; + while(*fpreg!=-1) + { + if (SpanNRegfIntr(current_opid,*fpreg)) + x86e->Emit(op_movss,*fpreg,slpc++); + fpreg++; + } +} + + +x86_reg_alloc reg; + +u32 ret_hit,ret_all,ret_stc; + +void csc_push(RuntimeBlockInfo* block) +{ + if (csc_mode==0) + { + x86e->Emit(op_mov32,&csc[csc_hash(block->NextBlock)].pc,block->NextBlock); + } + else if (csc_mode==1) + { + //x86e->Emit(op_int3); + x86e->Emit(op_ror32,&csc_sidx,1); + x86e->Emit(op_bsr32,EAX,&csc_sidx); + x86e->Emit(op_mov32,x86_mrm(EAX,sib_scale_8,x86_ptr(csc)),block->NextBlock); + } +} + +void DYNACALL csc_fail(u32 addr,u32 addy) +{ + if (csc_mode==0) + { + //too bad ? + } + else if (csc_mode==1) + { + u32 fail_idx=(csc_sidx>>1)|(csc_sidx<<31); + + printf("Ret Mismatch: %08X instead of %08X!\n",addr,addy); + } +} +void csc_pop(RuntimeBlockInfo* block) +{ + x86_Label* end=x86e->CreateLabel(false,8); + x86_Label* try_dyn=x86e->CreateLabel(false,8); + + //static guess + x86_Label* stc_hit=x86e->CreateLabel(false,8); + x86e->Emit(op_cmp32,ECX,&block->csc_RetCache); + x86e->Emit(op_je,stc_hit); + //if !eq + { + //if (cached) goto dyn + x86e->Emit(op_cmp32,&block->csc_RetCache,-1); + x86e->Emit(op_jne,try_dyn); + //else, do cache + x86e->Emit(op_mov32,&block->csc_RetCache,ECX); + } + + x86e->MarkLabel(stc_hit); + x86e->Emit(op_add32,&ret_stc,1); + if (csc_mode==1) + x86e->Emit(op_rol32,&csc_sidx,1); + x86e->Emit(op_jmp,end); + + x86e->MarkLabel(try_dyn); + + if (csc_mode==0) + { + //csc ! + //x86e->Emit(op_int3); + x86e->Emit(op_mov32,ECX,GetRegPtr(reg_pc_dyn)); + x86e->Emit(op_mov32,EAX,ECX); + x86e->Emit(op_shr32,EAX,CSC_SHIFT); + x86e->Emit(op_and32,EAX,CSC_SIZE-1); + x86e->Emit(op_cmp32,x86_mrm(EAX,sib_scale_8,x86_ptr(csc)),ECX); + } + else if (csc_mode==1) + { + //x86e->Emit(op_int3); + x86e->Emit(op_mov32,ECX,GetRegPtr(reg_pc_dyn)); + x86e->Emit(op_bsr32,EAX,&csc_sidx); + x86e->Emit(op_rol32,&csc_sidx,1); + x86e->Emit(op_mov32,EDX,x86_mrm(EAX,sib_scale_8,x86_ptr(csc))); + x86e->Emit(op_cmp32,EDX,ECX); + } + + + x86e->Emit(op_jne,end); + x86e->Emit(op_add32,&ret_hit,1); + //x86e->Emit(op_jmp,end); + + x86e->MarkLabel(end); + x86e->Emit(op_add32,&ret_all,1); + +} + +void DYNACALL PrintBlock(u32 pc) +{ + printf("block: 0x%08X\n",pc); + for (int i=0;i<16;i++) + printf("%08X ",r[i]); + printf("\n"); +} + +u32* GetRegPtr(u32 reg) +{ + return Sh4_int_GetRegisterPtr((Sh4RegType)reg); +} + +u32 cvld; +u32 rdmt[6]; +extern u32 memops_t,memops_l; + +void CheckBlock(RuntimeBlockInfo* block,x86_ptr_imm place) +{ + s32 sz=block->sh4_code_size; + u32 sa=block->addr; + while(sz>0) + { + void* ptr=(void*)GetMemPtr(sa,4); + if (ptr) + { + if (sz==2) + x86e->Emit(op_cmp16,ptr,*(u16*)ptr); + else + x86e->Emit(op_cmp32,ptr,*(u32*)ptr); + x86e->Emit(op_jne,place); + } + sz-=4; + sa+=4; + } + +} +void ngen_Compile(RuntimeBlockInfo* block,bool force_checks, bool reset, bool staging,bool optimise) +{ + //initialise stuff + DetectCpuFeatures(); + + ((DynaRBI*)block)->reloc_info=0; + + + //Setup emitter + x86e = new x86_block(); + x86e->Init(0,0); + x86e->x86_buff=(u8*)emit_GetCCPtr(); + x86e->x86_size=emit_FreeSpace(); + x86e->do_realloc=false; + + block->code=(DynarecCodeEntryPtr)emit_GetCCPtr(); + + x86e->Emit(op_add32,&memops_t,block->memops); + x86e->Emit(op_add32,&memops_l,block->linkedmemops); + + //run register allocator + reg.DoAlloc(block,alloc_regs,xmm_alloc_regs); + + //block header// + + //block invl. checks + x86e->Emit(op_mov32,ECX,block->addr); + + CheckBlock(block,force_checks?x86_ptr_imm(ngen_blockcheckfail):x86_ptr_imm(ngen_blockcheckfail2)); + + //Scheduler + x86_Label* no_up=x86e->CreateLabel(false,8); + + x86e->Emit(op_sub32,&cycle_counter,block->guest_cycles); + + x86e->Emit(op_jns,no_up); + { + x86e->Emit(op_call,x86_ptr_imm(intc_sched)); + } + + x86e->MarkLabel(no_up); + + //stating counter + if (staging) x86e->Emit(op_sub32,&block->staging_runs,1); + + //profiler + if (prof.enable || 1) + x86e->Emit(op_add32,&block->runs,1); + + if (prof.enable) + { + if (force_checks) + x86e->Emit(op_add32,&prof.counters.blkrun.force_check,1); + + x86e->Emit(op_add32,&prof.counters.blkrun.cycles[block->guest_cycles],1); + } + + for (size_t i=0;ioplist.size();i++) + { + shil_opcode* op=&block->oplist[i]; + + u32 opcd_start=x86e->opcode_count; + if (prof.enable) + { + x86e->Emit(op_add32,&prof.counters.shil.executed[op->op],1); + } + + op->host_offs=x86e->x86_indx; + + if (prof.enable) + { + set reg_wt; + set reg_rd; + + for (int z=0;op->rd.is_reg() && zrd.count();z++) + reg_wt.insert(op->rd._reg+z); + + for (int z=0;op->rd2.is_reg() && zrd2.count();z++) + reg_wt.insert(op->rd2._reg+z); + + for (int z=0;op->rs1.is_reg() && zrs1.count();z++) + reg_rd.insert(op->rs1._reg+z); + + for (int z=0;op->rs2.is_reg() && zrs2.count();z++) + reg_rd.insert(op->rs2._reg+z); + + for (int z=0;op->rs3.is_reg() && zrs3.count();z++) + reg_rd.insert(op->rs3._reg+z); + + set::iterator iter=reg_wt.begin(); + while( iter != reg_wt.end() ) + { + if (reg_rd.count(*iter)) + { + reg_rd.erase(*iter); + x86e->Emit(op_add32, &prof.counters.ralloc.reg_rw[*iter], 1); + } + else + { + x86e->Emit(op_add32, &prof.counters.ralloc.reg_w[*iter], 1); + } + + ++iter; + } + + iter=reg_rd.begin(); + while( iter != reg_rd.end() ) + { + x86e->Emit(op_add32,&prof.counters.ralloc.reg_r[*iter],1); + ++iter; + } + } + + reg.OpBegin(op,i); + + ngen_opcode(block,op,x86e,staging,optimise); + + if (prof.enable) x86e->Emit(op_add32,&prof.counters.shil.host_ops[op->op],x86e->opcode_count-opcd_start); + + reg.OpEnd(op); + } + + block->relink_offset=x86e->x86_indx; + block->relink_data=0; + + x86e->x86_indx+=block->Relink(); + + x86e->Generate(); + block->host_code_size=x86e->x86_indx; + block->host_opcodes=x86e->opcode_count; + + emit_Skip(block->host_code_size); + + delete x86e; + x86e=0; +} + +u32 DynaRBI::Relink() +{ + x86_block* x86e=new x86_block(); + x86e->Init(0,0); + x86e->x86_buff=(u8*)code + relink_offset; + x86e->x86_size=512; + x86e->do_realloc=false; + + if (BlockType==BET_StaticCall || BlockType==BET_DynamicCall) + { + //csc_push(this); + } + + switch(BlockType) + { + case BET_Cond_0: + case BET_Cond_1: + { + x86e->Emit(op_cmp32,GetRegPtr(has_jcond?reg_pc_dyn:reg_sr_T),BlockType&1); + + x86_Label* noBranch=x86e->CreateLabel(0,8); + + x86e->Emit(op_jne,noBranch); + { + //branch block + if (pBranchBlock) + x86e->Emit(op_jmp,x86_ptr_imm(pBranchBlock->code)); + else + x86e->Emit(op_call,x86_ptr_imm(ngen_LinkBlock_cond_Branch_stub)); + } + x86e->MarkLabel(noBranch); + { + //no branch block + if (pNextBlock) + x86e->Emit(op_jmp,x86_ptr_imm(pNextBlock->code)); + else + x86e->Emit(op_call,x86_ptr_imm(ngen_LinkBlock_cond_Next_stub)); + } + } + break; + + + case BET_DynamicRet: + { + //csc_pop(this); + } + case BET_DynamicCall: + case BET_DynamicJump: + { + if (relink_data==0) + { + if (pBranchBlock) + { + x86e->Emit(op_cmp32,GetRegPtr(reg_pc_dyn),pBranchBlock->addr); + x86e->Emit(op_je,x86_ptr_imm(pBranchBlock->code)); + x86e->Emit(op_call,x86_ptr_imm(ngen_LinkBlock_Generic_stub)); + } + else + { + x86e->Emit(op_cmp32,GetRegPtr(reg_pc_dyn),0xFABCDECF); + x86e->Emit(op_call,x86_ptr_imm(ngen_LinkBlock_Generic_stub)); + x86e->Emit(op_je,x86_ptr_imm(ngen_LinkBlock_Generic_stub)); + } + } + else + { + verify(pBranchBlock==0); + x86e->Emit(op_mov32,ECX,GetRegPtr(reg_pc_dyn)); + x86e->Emit(op_jmp,x86_ptr_imm(loop_no_update)); + } + } + break; + + case BET_StaticCall: + case BET_StaticJump: + { + if (pBranchBlock) + x86e->Emit(op_jmp,x86_ptr_imm(pBranchBlock->code)); + else + x86e->Emit(op_call,x86_ptr_imm(ngen_LinkBlock_Generic_stub)); + break; + } + + case BET_StaticIntr: + case BET_DynamicIntr: + if (BlockType==BET_StaticIntr) + { + x86e->Emit(op_mov32,&next_pc,NextBlock); + } + else + { + x86e->Emit(op_mov32,EAX,GetRegPtr(reg_pc_dyn)); + x86e->Emit(op_mov32,&next_pc,EAX); + } + x86e->Emit(op_call,x86_ptr_imm(UpdateINTC)); + + x86e->Emit(op_mov32,ECX,&next_pc); + + x86e->Emit(op_jmp,x86_ptr_imm(loop_no_update)); + + break; + } + + + + x86e->Generate(); + return x86e->x86_indx; +} + + +/* + //10 + R S8 B,M + R S16 B,M + R I32 B,M + R F32 B,M + R F32v2 B{,M} + + //13 + W I8 B,M + W I16 B,M + W I32 B,S,M + W F32 B,S,M + W F32v2 B,S{,M} +*/ + +extern u8* virt_ram_base; +#include "hw/sh4/sh4_mmr.h" + +enum mem_op_type +{ + SZ_8, + SZ_16, + SZ_32I, + SZ_32F, + SZ_64F, +}; + +void gen_hande(u32 w, u32 sz, u32 mode) +{ + static const x86_ptr_imm rwm[2][5]= + { + {x86_ptr_imm(&_vmem_ReadMem8SX32),x86_ptr_imm(&_vmem_ReadMem16SX32),x86_ptr_imm(&ReadMem32),x86_ptr_imm(&ReadMem32),x86_ptr_imm(&ReadMem64),}, + {x86_ptr_imm(&WriteMem8),x86_ptr_imm(&WriteMem16),x86_ptr_imm(&WriteMem32),x86_ptr_imm(&WriteMem32),x86_ptr_imm(&WriteMem64),} + }; + + static const x86_opcode_class opcl_i[2][3]= + { + {op_movsx8to32,op_movsx16to32,op_mov32}, + {op_mov8,op_mov16,op_mov32} + }; + + u32 si=x86e->x86_indx; + + if (mode==0) + { + //Buffer + x86e->Emit(op_mov32,EAX,ECX); + x86e->Emit(op_and32,ECX,0x1FFFFFFF); + + x86_mrm_t buff=x86_mrm(ECX,virt_ram_base); + x86_mrm_t buff4=x86_mrm(ECX,virt_ram_base+4); + + if (sz==SZ_8 || sz==SZ_16 || sz==SZ_32I) + { + if (w==0) + x86e->Emit(opcl_i[w][sz],sz==SZ_8?AL:sz==SZ_16?AX:EAX,buff); + else + x86e->Emit(opcl_i[w][sz],buff,sz==SZ_8?DL:sz==SZ_16?DX:EDX); + } + else + { + if (w==0) + { + x86e->Emit(op_movss,XMM0,buff); + if (sz==SZ_64F) + x86e->Emit(op_movss,XMM1,buff4); + } + else + { + x86e->Emit(op_movss,buff,XMM0); + if (sz==SZ_64F) + x86e->Emit(op_movss,buff4,XMM1); + } + } + } + else if (mode==1) + { + //SQ + verify(w==1); + x86e->Emit(op_mov32,EAX,ECX); + x86e->Emit(op_and32,ECX,0x3f); + + x86e->Emit(op_shr32,EAX,26); + x86e->Emit(op_cmp32,EAX,0x38); + x86_Label* l=x86e->CreateLabel(false,8); + x86e->Emit(op_je,l); + x86e->Emit(op_int3); + x86e->MarkLabel(l); + + if (sz==SZ_32I) + x86e->Emit(op_mov32,x86_mrm(ECX,sq_both),EDX); + else if (sz==SZ_32F || sz==SZ_64F) + { + x86e->Emit(op_movss,x86_mrm(ECX,sq_both),XMM0); + if (sz==SZ_64F) + x86e->Emit(op_movss,x86_mrm(ECX,sq_both+4),XMM1); + } + else + { + die("Can't happen\n"); + } + } + else + { + //General + + //maintain 16 byte alignment + x86e->Emit(op_sub32, ESP, 12); + + if ((sz==SZ_32F || sz==SZ_64F) && w==1) + { + if (sz==SZ_32F) + { + x86e->Emit(op_movd_xmm_to_r32,EDX,XMM0); + } + else + { + x86e->Emit(op_movss,x86_mrm(ESP,x86_ptr::create(+4)),XMM1); + x86e->Emit(op_movss,x86_mrm(ESP,x86_ptr::create(-0)),XMM0); + } + } + + x86e->Emit(op_call,rwm[w][sz]); + + if ((sz==SZ_32F || sz==SZ_64F) && w==0) + { + x86e->Emit(op_movd_xmm_from_r32,XMM0,EAX); + if (sz==SZ_64F) + { + x86e->Emit(op_movd_xmm_from_r32,XMM1,EDX); + } + } + + if ((sz == SZ_64F) && w == 1) { + x86e->Emit(op_add32, ESP, 4); + } + else { + x86e->Emit(op_add32, ESP, 12); + } + } + + x86e->Emit(op_ret); + + emit_Skip(x86e->x86_indx-si); +} + +unat mem_code_base=0; +unat mem_code_end=0; +void* mem_code[3][2][5]; + +void ngen_init() +{ + //Setup emitter + x86e = new x86_block(); + x86e->Init(0,0); + x86e->x86_buff=(u8*)emit_GetCCPtr(); + x86e->x86_size=emit_FreeSpace(); + x86e->do_realloc=false; + + + mem_code_base=(unat)emit_GetCCPtr(); + + for (int sz=0;sz<5;sz++) + { + for (int w=0;w<2;w++) + { + for (int m=0;m<3;m++) + { + if (m==1 && (sz<=SZ_16 || w==0)) + continue; + + mem_code[m][w][sz]=emit_GetCCPtr(); + gen_hande(w,sz,m); + } + } + } + + mem_code_end=(unat)emit_GetCCPtr(); + + x86e->Generate(); + + delete x86e; + + emit_SetBaseAddr(); +} + +void ngen_ResetBlocks() +{ +} + +void ngen_GetFeatures(ngen_features* dst) +{ + dst->InterpreterFallback=false; + dst->OnlyDynamicEnds=false; +} + + +RuntimeBlockInfo* ngen_AllocateBlock() +{ + return new DynaRBI(); +} + + +bool ngen_Rewrite(unat& addr,unat retadr,unat acc) +{ + if (addr>=mem_code_base && addrInit(0,0); + x86e->x86_buff=(u8*)retadr-5; + x86e->x86_size=emit_FreeSpace(); + x86e->do_realloc=false; + + for (int i=0;i<5;i++) + { + for (int w=0;w<2;w++) + { + if ((u32)mem_code[0][w][i]==ca) + { + //found ! + + if ((acc >> 26) == 0x38) //sq ? + { + verify(w == 1); + x86e->Emit(op_call, x86_ptr_imm(mem_code[1][w][i])); + } + else + { + x86e->Emit(op_call, x86_ptr_imm(mem_code[2][w][i])); + } + + x86e->Generate(); + delete x86e; + + addr=retadr-5; + + //printf("Patched: %08X for access @ %08X\n",addr,acc); + return true; + } + } + } + + die("Failed to match the code :(\n"); + + return false; + } + else + { + return false; + } +} +#endif diff --git a/core/rec-x86/win86_il.cpp b/core/rec-x86/win86_il.cpp new file mode 100644 index 000000000..99fe9f912 --- /dev/null +++ b/core/rec-x86/win86_il.cpp @@ -0,0 +1,1529 @@ +#include "win86_ngen.h" +#include "hw/sh4/sh4_mmr.h" +#include "hw/sh4/sh4_rom.h" + +void ngen_Bin(shil_opcode* op,x86_opcode_class natop,bool has_imm=true,bool has_wb=true) +{ + //x86e->Emit(op_mov32,EAX,op->rs1.reg_ptr()); + + verify(reg.IsAllocg(op->rs1._reg)); + verify(reg.IsAllocg(op->rd._reg)); + + if (has_wb && reg.mapg(op->rs1)!=reg.mapg(op->rd)) + { + x86e->Emit(op_mov32,reg.mapg(op->rd),reg.mapg(op->rs1)); + } + + if (has_imm && op->rs2.is_imm()) + { + x86e->Emit(natop,has_wb?reg.mapg(op->rd):reg.mapg(op->rs1),op->rs2._imm); + } + else if (op->rs2.is_r32i()) + { + verify(reg.IsAllocg(op->rs2._reg)); + + x86e->Emit(natop,has_wb?reg.mapg(op->rd):reg.mapg(op->rs1),reg.mapg(op->rs2)); + } + else + { + printf("%d \n",op->rs1.type); + verify(false); + } +} + +void ngen_fp_bin(shil_opcode* op,x86_opcode_class natop) +{ + verify(reg.IsAllocf(op->rs1)); + verify(reg.IsAllocf(op->rs2)); + verify(reg.IsAllocf(op->rd)); + + if (op->rd._reg!=op->rs1._reg) + x86e->Emit(op_movss,reg.mapf(op->rd),reg.mapf(op->rs1)); + + if (op->rs2.is_r32f()) + { + x86e->Emit(natop,reg.mapf(op->rd),reg.mapf(op->rs2)); + } + else + { + printf("%d \n",op->rs2.type); + verify(false); + } +// verify(has_wb); + //x86e->Emit(op_movss,op->rd.reg_ptr(),XMM0); +} +void ngen_Unary(shil_opcode* op,x86_opcode_class natop) +{ + verify(reg.IsAllocg(op->rs1)); + verify(reg.IsAllocg(op->rd)); + + if (reg.mapg(op->rs1)!=reg.mapg(op->rd)) + x86e->Emit(op_mov32,reg.mapg(op->rd),reg.mapg(op->rs1)); + + x86e->Emit(natop,reg.mapg(op->rd)); +} + +void* _vmem_read_const(u32 addr,bool& ismem,u32 sz); + +u32 ngen_CC_BytesPushed; +void ngen_CC_Start(shil_opcode* op) +{ + ngen_CC_BytesPushed=0; +} +void ngen_CC_Param(shil_opcode* op,shil_param* par,CanonicalParamType tp) +{ + switch(tp) + { + //push the contents + case CPT_u32: + case CPT_f32: + if (par->is_reg()) + { + if (reg.IsAllocg(*par)) + x86e->Emit(op_push32,reg.mapg(*par)); + else if (reg.IsAllocf(*par)) + { + x86e->Emit(op_sub32,ESP,4); + x86e->Emit(op_movss,x86_mrm(ESP), reg.mapf(*par)); + } + else + { + die("Must not happen !\n"); + x86e->Emit(op_push32,x86_ptr(par->reg_ptr())); + } + } + else if (par->is_imm()) + x86e->Emit(op_push,par->_imm); + else + die("invalid combination"); + ngen_CC_BytesPushed+=4; + break; + //push the ptr itself + case CPT_ptr: + verify(par->is_reg()); + + die("FAIL"); + x86e->Emit(op_push,(unat)par->reg_ptr()); + + for (u32 ri=0; ri<(*par).count(); ri++) + { + if (reg.IsAllocf(*par,ri)) + { + x86e->Emit(op_sub32,ESP,4); + x86e->Emit(op_movss,x86_mrm(ESP),reg.mapfv(*par,ri)); + } + else + { + verify(!reg.IsAllocAny((Sh4RegType)(par->_reg+ri))); + } + } + + + ngen_CC_BytesPushed+=4; + break; + + //store from EAX + case CPT_u64rvL: + case CPT_u32rv: + if (reg.IsAllocg(*par)) + x86e->Emit(op_mov32,reg.mapg(*par),EAX); + /*else if (reg.IsAllocf(*par)) + x86e->Emit(op_movd_xmm_from_r32,reg.mapf(*par),EAX);*/ + else + die("Must not happen!\n"); + break; + + case CPT_u64rvH: + if (reg.IsAllocg(*par)) + x86e->Emit(op_mov32,reg.mapg(*par),EDX); + else + die("Must not happen!\n"); + break; + + //Store from ST(0) + case CPT_f32rv: + verify(reg.IsAllocf(*par)); + x86e->Emit(op_fstp32f,x86_ptr(par->reg_ptr())); + x86e->Emit(op_movss,reg.mapf(*par),x86_ptr(par->reg_ptr())); + break; + + } +} + +void ngen_CC_Call(shil_opcode*op,void* function) +{ + reg.FreezeXMM(); + x86e->Emit(op_call,x86_ptr_imm(function)); + reg.ThawXMM(); +} +void ngen_CC_Finish(shil_opcode* op) +{ + x86e->Emit(op_add32,ESP,ngen_CC_BytesPushed); +} + +extern u32 vrml_431; +#ifdef PROF2 + +extern u32 srmls,srmlu,srmlc; +extern u32 rmls,rmlu; +extern u32 wmls,wmlu; +extern u32 vrd; +#endif + + +void DYNACALL VERIFYME(u32 addr) +{ + verify((addr>>26)==0x38); +} + +extern u8* virt_ram_base; + +/* + + ReadM + I8 GAI1 [m] + I16 GAI2 [m] + I32 GAI4 [m] + F32 GA4 [m] + F32v2 RA4 [m,m] + F32v4 RA4 [m,m,m,m] + F32v4r3i1 RA4 [m,m,m,1.0] + F32v4r3i0 RA4 [m,m,m,0.0] + + WriteM + I8 GA1 + I16 GA2 + I32 GA4 + F32 GA4 + F32v2 SA + F32v4 + F32v4s3 + F32v4s4 + + + //10 + R S8 B,M + R S16 B,M + R I32 B,M + R F32 B,M + R F32v2 B{,M} + + //13 + W I8 B,M + W I16 B,M + W I32 B,S,M + W F32 B,S,M + W F32v2 B,S{,M} +*/ + +extern void* mem_code[3][2][5]; + +void ngen_opcode(RuntimeBlockInfo* block, shil_opcode* op,x86_block* x86e, bool staging, bool optimise) +{ + switch(op->op) + { + case shop_readm: + { + void* fuct=0; + bool isram=false; + verify(op->rs1.is_imm() || op->rs1.is_r32i()); + + verify(op->rs1.is_imm() || reg.IsAllocg(op->rs1)); + verify(op->rs3.is_null() || op->rs3.is_imm() || reg.IsAllocg(op->rs3)); + + for (u32 i=0;ird.count();i++) + { + verify(reg.IsAllocAny((Sh4RegType)(op->rd._reg+i))); + } + + u32 size=op->flags&0x7f; + + if (op->rs1.is_imm()) + { + if (prof.enable) x86e->Emit(op_add32,&prof.counters.shil.readm_const,1); + void* ptr=_vmem_read_const(op->rs1._imm,isram,size); + if (isram) + { +#ifdef PROF2 + x86e->Emit(op_add32,&srmlu,1); +#endif + if (size==1) + x86e->Emit(op_movsx8to32,EAX,ptr); + else if (size==2) + x86e->Emit(op_movsx16to32,EAX,ptr); + else if (size==4) + { + x86e->Emit(op_mov32,EAX,ptr); + //this is a pretty good sieve, but its not perfect. + //whitelisting is much better, but requires side channel data + //Page locking w/ invalidation is another strategy we can try (leads to 'excessive' + //compiling. Maybe a mix of both ?), its what the mainline nulldc uses + if (optimise) + { + if (staging && !is_s8(*(u32*)ptr) && abs((int)op->rs1._imm-(int)block->addr)<=1024) + { + x86_Label* _same=x86e->CreateLabel(false,8); + x86e->Emit(op_cmp32,EAX,*(u32*)ptr); + x86e->Emit(op_je,_same); + x86e->Emit(op_and32,&op->flags,~0x40000000); + x86e->MarkLabel(_same); + + op->flags|=0x40000000; + } + else if (!staging && op->flags & 0x40000000) + { + x86_Label* _same=x86e->CreateLabel(false,8); + x86e->Emit(op_cmp32,EAX,*(u32*)ptr); + x86e->Emit(op_je,_same); + x86e->Emit(op_int3); + x86e->MarkLabel(_same); +#ifdef PROF2 + x86e->Emit(op_add32,&srmlc,1); +#endif + } + } + } + else if (size==8) + { + x86e->Emit(op_mov32,EAX,ptr); + x86e->Emit(op_mov32,EDX,(u8*)ptr+4); + } + else + { + die("Invalid mem read size"); + } + } + else + { +#ifdef PROF2 + x86e->Emit(op_add32,&srmls,1); +#endif + x86e->Emit(op_mov32,ECX,op->rs1._imm); + fuct=ptr; + } + } + else + { + x86e->Emit(op_mov32,ECX,reg.mapg(op->rs1)); + if (op->rs3.is_imm()) + { + x86e->Emit(op_add32,ECX,op->rs3._imm); + if (prof.enable) x86e->Emit(op_add32,&prof.counters.shil.readm_reg_imm,1); + } + else if (op->rs3.is_r32i()) + { + x86e->Emit(op_add32,ECX,reg.mapg(op->rs3)); + if (prof.enable) x86e->Emit(op_add32,&prof.counters.shil.readm_reg_reg,1); + } + else if (!op->rs3.is_null()) + { + die("invalid rs3"); + } + else + if (prof.enable) x86e->Emit(op_add32,&prof.counters.shil.readm_reg,1); +#if 0 + if (op->flags==0x431 || op->flags==0x440) + { + verify(!reg.IsAllocAny(op->rd)); + verify(!reg.IsAllocAny((Sh4RegType)(op->rd._reg+1))); + verify(!reg.IsAllocAny((Sh4RegType)(op->rd._reg+2))); + verify(!reg.IsAllocAny((Sh4RegType)(op->rd._reg+3))); + + x86e->Emit(op_add32,&vrml_431,1); + x86e->Emit(op_mov32,EDX,ECX); + x86e->Emit(op_and32,EDX,0x1FFFFFFF); + x86e->Emit(op_movups,XMM0,x86_mrm(EDX,x86_ptr(virt_ram_base))); + x86e->Emit(op_movaps,op->rd.reg_ptr(),XMM0); + + if (op->flags==0x431) + x86e->Emit(op_mov32,op->rd.reg_ptr()+3,0x3f800000); + else if (op->flags==0x430) + x86e->Emit(op_mov32,op->rd.reg_ptr()+3,0); + + break; + } + + bool vect=op->flags&0x80; + + if (vect) + { + u32 sz=size; + //x86e->Emit(op_add32,&cvld,sz/(op->flags&0x100?8:4)); + x86e->Emit(op_add32,&vrml_431,sz/(op->flags&0x100?8:4)*2); + verify(sz==8 || sz==12 || sz==16 || sz==32 || sz==64); + + void** vmap,** funct; + _vmem_get_ptrs(4,false,&vmap,&funct); + x86e->Emit(op_mov32,EAX,ECX); + x86e->Emit(op_shr32,EAX,24); + x86e->Emit(op_mov32,EAX,x86_mrm(EAX,sib_scale_4,vmap)); + + x86e->Emit(op_test32,EAX,~0x7F); + x86e->Emit(op_jz,x86_ptr_imm::create(op->flags)); + x86e->Emit(op_xchg32,ECX,EAX); + x86e->Emit(op_shl32,EAX,ECX); + x86e->Emit(op_shr32,EAX,ECX); + x86e->Emit(op_and32,ECX,~0x7F); + + int i=0; + for (i=0;(i+16)<=sz;i+=16) + { + x86e->Emit(op_movups,XMM0,x86_mrm(EAX,ECX,sib_scale_1,x86_ptr::create(i))); + if (op->rd._reg&3) + x86e->Emit(op_movups,op->rd.reg_ptr()+i/4,XMM0); + else + x86e->Emit(op_movaps,op->rd.reg_ptr()+i/4,XMM0); + } + for (;(i+8)<=sz;i+=8) + { + x86e->Emit(op_movlps,XMM0,x86_mrm(EAX,ECX,sib_scale_1,x86_ptr::create(i))); + x86e->Emit(op_movlps,op->rd.reg_ptr()+i/4,XMM0); + } + for (;(i+4)<=sz;i+=4) + { + x86e->Emit(op_movss,XMM0,x86_mrm(EAX,ECX,sib_scale_1,x86_ptr::create(i))); + x86e->Emit(op_movss,op->rd.reg_ptr()+i/4,XMM0); + } + + verify(i==sz); + + break; + + } + + if (optimise) + { + if (staging || op->flags&0x80000000) + { + + //opt disabled for now + op->flags|=0x80000000; + + x86_Label* _ram=x86e->CreateLabel(false,8); + void** vmap,** funct; + _vmem_get_ptrs(4,false,&vmap,&funct); + x86e->Emit(op_mov32,EAX,ECX); + x86e->Emit(op_shr32,EAX,24); + x86e->Emit(op_mov32,EAX,x86_mrm(EAX,sib_scale_4,vmap)); + + x86e->Emit(op_test32,EAX,~0x7F); + x86e->Emit(op_jnz,_ram); + + if (staging) + { + x86e->Emit(op_and32,&op->flags,~0x80000000); + } + else + { + //x86e->Emit(op_int3); + } + + x86e->MarkLabel(_ram); + } + + if ( !staging) + { + if (op->flags & 0x80000000) + { +#ifdef PROF2 + x86e->Emit(op_add32,&rmlu,1); +#endif + if (true) + { + u32 sz=op->flags&0x7f; + if (sz!=8) + { + x86e->Emit(op_mov32,EDX,ECX); + x86e->Emit(op_and32,EDX,0x1FFFFFFF); + if (sz==1) + { + x86e->Emit(op_movsx8to32,EAX,x86_mrm(EDX,x86_ptr(virt_ram_base))); + } + else if (sz==2) + { + x86e->Emit(op_movsx16to32,EAX,x86_mrm(EDX,x86_ptr(virt_ram_base))); + } + else if (sz==4) + { + x86e->Emit(op_mov32,EAX,x86_mrm(EDX,x86_ptr(virt_ram_base))); + } + isram=true; + } + } + + } +#ifdef PROF2 + else + { + x86e->Emit(op_add32,&rmls,1); + } +#endif + } + } +#endif +#if 1 + //new code ... + //yay ... + + int Lsz=0; + int sz=size; + if (sz==2) Lsz=1; + if (sz==4 && op->rd.is_r32i()) Lsz=2; + if (sz==4 && op->rd.is_r32f()) Lsz=3; + if (sz==8) Lsz=4; + + //x86e->Emit(op_int3); + + reg.FreezeXMM(); + x86e->Emit(op_call,x86_ptr_imm(mem_code[0][0][Lsz])); + reg.ThawXMM(); + + if (Lsz <= 2) + { + x86e->Emit(op_mov32, reg.mapg(op->rd), EAX); + } + else + { + x86e->Emit(op_movss, reg.mapfv(op->rd, 0), XMM0); + if (Lsz == 4) + x86e->Emit(op_movss, reg.mapfv(op->rd, 1), XMM1); + } + break; +#endif + } + + if (size<=8) + { + + if (size==8 && optimise) + { + verify(op->rd.count()==2 && reg.IsAllocf(op->rd,0) && reg.IsAllocf(op->rd,1)); + + x86e->Emit(op_mov32,EDX,ECX); + x86e->Emit(op_and32,EDX,0x1FFFFFFF); + x86e->Emit(op_movss,reg.mapfv(op->rd,0),x86_mrm(EDX,x86_ptr(virt_ram_base))); + x86e->Emit(op_movss,reg.mapfv(op->rd,1),x86_mrm(EDX,x86_ptr(4+virt_ram_base))); + break; + } + if (!isram) + { + reg.FreezeXMM(); + switch(size) + { + case 1: + if (!fuct) fuct=ReadMem8; + x86e->Emit(op_call,x86_ptr_imm(fuct)); + x86e->Emit(op_movsx8to32,EAX,EAX); + break; + case 2: + if (!fuct) fuct=ReadMem16; + x86e->Emit(op_call,x86_ptr_imm(fuct)); + x86e->Emit(op_movsx16to32,EAX,EAX); + break; + case 4: + if (!fuct) fuct=ReadMem32; + x86e->Emit(op_call,x86_ptr_imm(fuct)); + break; + case 8: + if (!fuct) fuct=ReadMem64; + x86e->Emit(op_call,x86_ptr_imm(fuct)); + break; + default: + verify(false); + } + reg.ThawXMM(); + } + + if (size!=8) + { + if (reg.IsAllocg(op->rd)) + x86e->Emit(op_mov32,reg.mapg(op->rd),EAX); + else if (reg.IsAllocf(op->rd)) + x86e->Emit(op_movd_xmm_from_r32,reg.mapf(op->rd),EAX); + else + x86e->Emit(op_mov32,op->rd.reg_ptr(),EAX); + } + else + { + verify(op->rd.count()==2 && reg.IsAllocf(op->rd,0) && reg.IsAllocf(op->rd,1)); + + x86e->Emit(op_movd_xmm_from_r32,reg.mapfv(op->rd,0),EAX); + x86e->Emit(op_movd_xmm_from_r32,reg.mapfv(op->rd,1),EDX); + } + + } + } + break; + + case shop_writem: + { + u32 size=op->flags&0x7f; + verify(reg.IsAllocg(op->rs1) || op->rs1.is_imm()); + + verify(op->rs2.is_r32() || (op->rs2.count()==2 && reg.IsAllocf(op->rs2,0) && reg.IsAllocf(op->rs2,1))); + + if (op->rs1.is_imm() && size<=4) + { + if (prof.enable) x86e->Emit(op_add32,&prof.counters.shil.readm_const,1); + bool isram; + void* ptr=_vmem_read_const(op->rs1._imm,isram,size); + if (isram) + { + if (size<=2) + x86e->Emit(op_mov32,EAX,reg.mapg(op->rs2)); + if (size==1) + x86e->Emit(op_mov8,ptr,EAX); + else if (size==2) + x86e->Emit(op_mov16,ptr,EAX); + else if (size==4) + { + if (op->rs2.is_r32i()) + x86e->Emit(op_mov32,ptr,reg.mapg(op->rs2)); + else + x86e->Emit(op_movss,ptr,reg.mapf(op->rs2)); + } + + else if (size==8) + { + die("A"); + } + else + die("Invalid mem read size"); + + goto done_writem; + } + else + x86e->Emit(op_mov32,ECX,op->rs1._imm); + } + else + { + x86e->Emit(op_mov32,ECX,reg.mapg(op->rs1)); + } + + if (op->rs3.is_imm()) + { + x86e->Emit(op_add32,ECX,op->rs3._imm); + } + else if (op->rs3.is_r32i()) + { + verify(reg.IsAllocg(op->rs3)); + x86e->Emit(op_add32,ECX,reg.mapg(op->rs3)); + } + else if (!op->rs3.is_null()) + { + printf("rs3: %08X\n",op->rs3.type); + die("invalid rs3"); + } + +#if 1 + //new code ... + //yay ... + + int Lsz=0; + int sz=size; + if (sz==2) Lsz=1; + if (sz==4 && op->rs2.is_r32i()) Lsz=2; + if (sz==4 && op->rs2.is_r32f()) Lsz=3; + if (sz==8) Lsz=4; + + //x86e->Emit(op_int3); + //if (Lsz==0) + { + + if (Lsz<=2) + x86e->Emit(op_mov32,EDX,reg.mapg(op->rs2)); + else + { + x86e->Emit(op_movss,XMM0,reg.mapfv(op->rs2,0)); + if (Lsz==4) + x86e->Emit(op_movss,XMM1,reg.mapfv(op->rs2,1)); + } + + reg.FreezeXMM(); + x86e->Emit(op_call,x86_ptr_imm(mem_code[2][1][Lsz])); + reg.ThawXMM(); + + break; + } +#endif + + die("woohoo"); + /* + if (size==8 && optimise) + { + verify(!reg.IsAllocAny(op->rd)); + verify(!reg.IsAllocAny((Sh4RegType)(op->rd._reg+1))); + + x86e->Emit(op_mov32,EDX,ECX); + x86e->Emit(op_and32,EDX,0x1FFFFFFF); + x86e->Emit(op_movlps,XMM0,op->rs2.reg_ptr()); + x86e->Emit(op_movlps,x86_mrm(EDX,x86_ptr(virt_ram_base)),XMM0); + break; + }*/ + + bool vect=op->flags&0x80; + + if (!vect && size<=8) + { + if (size!=8) + { + if (reg.IsAllocg(op->rs2)) + { + x86e->Emit(op_mov32,EDX,reg.mapg(op->rs2)); + } + else if (reg.IsAllocf(op->rs2)) + { + x86e->Emit(op_movd_xmm_to_r32,EDX,reg.mapf(op->rs2)); + } + else + { + die("Must not happen\n"); + } + } + else + { + verify(op->rs2.count()==2 && reg.IsAllocf(op->rs2,0) && reg.IsAllocf(op->rs2,1)); + + x86e->Emit(op_sub32,ESP,8); + //[ESP+4]=rs2[1]//-4 +8= +4 + //[ESP+0]=rs2[0]//-8 +8 = 0 + x86e->Emit(op_movss,x86_mrm(ESP,x86_ptr::create(+4)),reg.mapfv(op->rs2,1)); + x86e->Emit(op_movss,x86_mrm(ESP,x86_ptr::create(-0)),reg.mapfv(op->rs2,0)); + } + + + + if (optimise) + { + if (staging || op->flags&0x80000000) + { + + //opt disabled for now + op->flags|=0x80000000; + x86_Label* _ram=x86e->CreateLabel(false,8); + void** vmap,** funct; + _vmem_get_ptrs(4,false,&vmap,&funct); + x86e->Emit(op_mov32,EAX,ECX); + x86e->Emit(op_shr32,EAX,24); + x86e->Emit(op_mov32,EAX,x86_mrm(EAX,sib_scale_4,vmap)); + + x86e->Emit(op_test32,EAX,~0x7F); + x86e->Emit(op_jnz,_ram); + + if (staging) + { + x86e->Emit(op_and32,&op->flags,~0x80000000); + } + else + { + //x86e->Emit(op_int3); + } + + x86e->MarkLabel(_ram); + } + + + if (!staging) + { + if (op->flags & 0x80000000) + { +#ifdef PROF2 + x86e->Emit(op_add32,&wmlu,1); +#endif + if (false && size<4) + { + x86e->Emit(op_mov32,EAX,ECX); + x86e->Emit(op_and32,EAX,0x1FFFFFFF); + + if (size==1) + { + x86e->Emit(op_mov8,x86_mrm(EAX,x86_ptr(virt_ram_base)),EDX); + } + else if (size==2) + { + x86e->Emit(op_mov16,x86_mrm(EAX,x86_ptr(virt_ram_base)),EDX); + } + else if (size==4) + { + x86e->Emit(op_mov32,x86_mrm(EAX,x86_ptr(virt_ram_base)),EAX); + } + break; + } + + } +#ifdef PROF2 + else + x86e->Emit(op_add32,&wmls,1); +#endif + } + } + } + + if (vect) + { + u32 sz=op->flags&0x7f; + x86e->Emit(op_add32,&vrml_431,sz/(op->flags&0x100?8:4)*5); + verify(sz==8 || sz==12 || sz==16 || sz==32 || sz==64); + + void** vmap,** funct; + _vmem_get_ptrs(4,false,&vmap,&funct); + x86e->Emit(op_mov32,EAX,ECX); + x86e->Emit(op_shr32,EAX,24); + x86e->Emit(op_mov32,EAX,x86_mrm(EAX,sib_scale_4,vmap)); + + x86e->Emit(op_test32,EAX,~0x7F); + x86e->Emit(op_jz,x86_ptr_imm::create(op->flags)); + x86e->Emit(op_xchg32,ECX,EAX); + x86e->Emit(op_shl32,EAX,ECX); + x86e->Emit(op_shr32,EAX,ECX); + x86e->Emit(op_and32,ECX,~0x7F); + + u32 i=0; + for (; (i+16)<=sz; i+=16) + { + if (op->rs2._reg&3) + x86e->Emit(op_movups,XMM0,op->rs2.reg_ptr()+i/4); + else + x86e->Emit(op_movaps,XMM0,op->rs2.reg_ptr()+i/4); + + x86e->Emit(op_movups,x86_mrm(EAX,ECX,sib_scale_1,x86_ptr::create(i)),XMM0); + } + for (; (i+8)<=sz; i+=8) + { + x86e->Emit(op_movlps,XMM0,op->rs2.reg_ptr()+i/4); + x86e->Emit(op_movlps,x86_mrm(EAX,ECX,sib_scale_1,x86_ptr::create(i)),XMM0); + } + for (; (i+4)<=sz; i+=4) + { + x86e->Emit(op_movss,XMM0,op->rs2.reg_ptr()+i/4); + x86e->Emit(op_movss,x86_mrm(EAX,ECX,sib_scale_1,x86_ptr::create(i)),XMM0); + } + + verify(i==sz); + } + else + { + + reg.FreezeXMM(); + switch(size) + { + case 1: + x86e->Emit(op_call,x86_ptr_imm(&WriteMem8)); + break; + case 2: + x86e->Emit(op_call,x86_ptr_imm(&WriteMem16)); + break; + case 4: + x86e->Emit(op_call,x86_ptr_imm(&WriteMem32)); + break; + case 8: + x86e->Emit(op_call,x86_ptr_imm(&WriteMem64)); + break; + default: + verify(false); + } + reg.ThawXMM(); + } + } + done_writem: + break; + + case shop_ifb: + { + /* + //reg alloc should be flushed here. Add Check + for (int i=0;irs1._imm) + { + x86e->Emit(op_mov32,&next_pc,op->rs2._imm); + } + x86e->Emit(op_mov32,ECX,op->rs3._imm); +#ifdef PROF2 + x86e->Emit(op_add32,&OpDesc[op->rs3._imm]->fallbacks,1); + x86e->Emit(op_adc32,((u8*)&OpDesc[op->rs3._imm]->fallbacks)+4,0); +#endif + x86e->Emit(op_call,x86_ptr_imm(OpDesc[op->rs3._imm]->oph)); + } + break; + + case shop_jdyn: + { + + verify(reg.IsAllocg(op->rs1)); + verify(reg.IsAllocg(op->rd)); + + x86e->Emit(op_mov32,reg.mapg(op->rd),reg.mapg(op->rs1)); + if (op->rs2.is_imm()) + { + x86e->Emit(op_add32,reg.mapg(op->rd),op->rs2._imm); + } + //x86e->Emit(op_mov32,op->rd.reg_ptr(),EAX); + } + break; + + case shop_jcond: + { + verify(block->has_jcond); + verify(reg.IsAllocg(op->rs1)); + verify(reg.IsAllocg(op->rd)); + + x86e->Emit(op_mov32,reg.mapg(op->rd),reg.mapg(op->rs1)); + //x86e->Emit(op_mov32,op->rd.reg_ptr(),EAX); + } + break; + + case shop_mov64: + { + verify(op->rd.is_r64()); + verify(op->rs1.is_r64()); + + verify(reg.IsAllocf(op->rs1,0) && reg.IsAllocf(op->rs1,1)); + verify(reg.IsAllocf(op->rd,0) && reg.IsAllocf(op->rd,1)); + + + x86e->Emit(op_movaps,reg.mapfv(op->rd,0),reg.mapfv(op->rs1,0)); + x86e->Emit(op_movaps,reg.mapfv(op->rd,1),reg.mapfv(op->rs1,1)); + } + break; + + case shop_mov32: + { + verify(op->rd.is_r32()); + + if (op->rs1.is_imm()) + { + if (op->rd.is_r32i()) + { + x86e->Emit(op_mov32,reg.mapg(op->rd),op->rs1._imm); + // x86e->Emit(op_add32,&rdmt[4],1); + } + else + { + //verify(!reg.IsAllocAny(op->rd)); + x86e->Emit(op_mov32,EAX,op->rs1._imm); + x86e->Emit(op_movd_xmm_from_r32,reg.mapf(op->rd),EAX); + // x86e->Emit(op_add32,&rdmt[5],1); + } + } + else if (op->rs1.is_r32()) + { + u32 type=0; + + if (reg.IsAllocf(op->rd)) + type|=1; + + if (reg.IsAllocf(op->rs1)) + type|=2; + // x86e->Emit(op_add32,&rdmt[type],1); + switch(type) + { + case 0: //reg=reg + if (reg.mapg(op->rd) != reg.mapg(op->rs1)) + x86e->Emit(op_mov32,reg.mapg(op->rd),reg.mapg(op->rs1)); + + break; + + case 1: //xmm=reg + x86e->Emit(op_movd_xmm_from_r32,reg.mapf(op->rd),reg.mapg(op->rs1)); + break; + + case 2: //reg=xmm + x86e->Emit(op_movd_xmm_to_r32,reg.mapg(op->rd),reg.mapf(op->rs1)); + break; + + case 3: //xmm=xmm + if (reg.mapf(op->rd) != reg.mapf(op->rs1)) + x86e->Emit(op_movss,reg.mapf(op->rd),reg.mapf(op->rs1)); + else + printf("Renamed fmov !\n"); + break; + + } + } + else + { + die("Invalid mov32 size"); + } + + } + break; + +//if CANONICAL_TEST is defined all opcodes use the C-based canonical implementation ! +//#define CANONICAL_TEST 1 +#ifndef CANONICAL_TEST + case shop_and: ngen_Bin(op,op_and32); break; + case shop_or: ngen_Bin(op,op_or32); break; + case shop_xor: ngen_Bin(op,op_xor32); break; + case shop_add: ngen_Bin(op,op_add32); break; + case shop_sub: ngen_Bin(op,op_sub32); break; + case shop_ror: ngen_Bin(op,op_ror32); break; + + case shop_shl: + case shop_shr: + case shop_sar: + { + x86_opcode_class opcd[]={op_shl32,op_shr32,op_sar32}; + ngen_Bin(op,opcd[op->op-shop_shl]); + } + break; + + case shop_rocr: + case shop_rocl: + { + x86e->Emit(op_sar32,reg.mapg(op->rs2),1); + x86e->Emit(op->op==shop_rocr?op_rcr32:op_rcl32,reg.mapg(op->rd),1); + x86e->Emit(op_rcl32,reg.mapg(op->rd2),1); + } + break; + + case shop_test: + case shop_seteq: + case shop_setge: + case shop_setgt: + case shop_setae: + case shop_setab: + { + x86_opcode_class opcls1=op->op==shop_test?op_test32:op_cmp32; + x86_opcode_class opcls2[]={op_setz,op_sete,op_setge,op_setg,op_setae,op_seta }; + ngen_Bin(op,opcls1,true,false); + x86e->Emit(opcls2[op->op-shop_test],AL); + x86e->Emit(op_movzx8to32,reg.mapg(op->rd),AL); + } + break; + + case shop_adc: + { + x86e->Emit(op_sar32,reg.mapg(op->rs3),1); + if (reg.mapg(op->rd)!=reg.mapg(op->rs1)) + x86e->Emit(op_mov32,reg.mapg(op->rd),reg.mapg(op->rs1)); + x86e->Emit(op_adc32,reg.mapg(op->rd),reg.mapg(op->rs2)); + x86e->Emit(op_rcl32,reg.mapg(op->rd2),1); + } + break; + + //rd=rs1<rs1)); + verify(op->rs2.is_imm() || reg.IsAllocg(op->rs2)); + verify(reg.IsAllocg(op->rd)); + + x86_opcode_class sl32=op->op==shop_shad?op_sal32:op_shl32; + x86_opcode_class sr32=op->op==shop_shad?op_sar32:op_shr32; + + if (reg.mapg(op->rd)!=reg.mapg(op->rs1)) + x86e->Emit(op_mov32,reg.mapg(op->rd),reg.mapg(op->rs1)); + + if (op->rs2.is_imm()) + { + die("sh*d: no imms please\n"); + } + else + { + x86e->Emit(op_mov32,ECX,reg.mapg(op->rs2)); + + x86_Label* _exit=x86e->CreateLabel(false,8); + x86_Label* _neg=x86e->CreateLabel(false,8); + x86_Label* _nz=x86e->CreateLabel(false,8); + + x86e->Emit(op_cmp32,reg.mapg(op->rs2),0); + x86e->Emit(op_js,_neg); + { + //>=0 + //r[n]<<=sf; + x86e->Emit(sl32,reg.mapg(op->rd),ECX); + x86e->Emit(op_jmp,_exit); + } + x86e->MarkLabel(_neg); + x86e->Emit(op_test32,reg.mapg(op->rs2),0x1f); + x86e->Emit(op_jnz,_nz); + { + //1fh==0 + if (op->op!=shop_shad) + { + //r[n]=0; + x86e->Emit(op_mov32,reg.mapg(op->rd),0); + } + else + { + //r[n]>>=31; + x86e->Emit(op_sar32,reg.mapg(op->rd),31); + } + x86e->Emit(op_jmp,_exit); + } + x86e->MarkLabel(_nz); + { + //<0 + //r[n]>>=(-sf); + x86e->Emit(op_neg32,ECX); + x86e->Emit(sr32,reg.mapg(op->rd),ECX); + } + x86e->MarkLabel(_exit); + } + } + break; + + case shop_swaplb: + { + if (reg.mapg(op->rd)!=reg.mapg(op->rs1)) + x86e->Emit(op_mov32,reg.mapg(op->rd),reg.mapg(op->rs1)); + x86e->Emit(op_ror16,reg.mapg(op->rd),8); + } + break; + + + case shop_neg: ngen_Unary(op,op_neg32); break; + case shop_not: ngen_Unary(op,op_not32); break; + + + case shop_sync_sr: + { + //reg alloc should be flushed here. Add Check + for (int i=0;i<8;i++) + { + verify(!reg.IsAllocAny((Sh4RegType)(reg_r0+i))); + verify(!reg.IsAllocAny((Sh4RegType)(reg_r0_Bank+i))); + } + + verify(!reg.IsAllocAny(reg_old_sr_status)); + verify(!reg.IsAllocAny(reg_sr_status)); + + //reg alloc should be flushed here, add checks + x86e->Emit(op_call,x86_ptr_imm(UpdateSR)); + } + break; + + case shop_sync_fpscr: + { + //reg alloc should be flushed here. Add Check + for (int i=0;i<16;i++) + { + verify(!reg.IsAllocAny((Sh4RegType)(reg_fr_0+i))); + verify(!reg.IsAllocAny((Sh4RegType)(reg_xf_0+i))); + } + + verify(!reg.IsAllocAny(reg_old_fpscr)); + verify(!reg.IsAllocAny(reg_fpscr)); + + + //reg alloc should be flushed here, add checks + x86e->Emit(op_call,x86_ptr_imm(UpdateFPSCR)); + } + break; + + + case shop_mul_u16: + case shop_mul_s16: + case shop_mul_i32: + case shop_mul_u64: + case shop_mul_s64: + { + verify(reg.IsAllocg(op->rs1)); + verify(reg.IsAllocg(op->rs2)); + verify(reg.IsAllocg(op->rd)); + + x86_opcode_class opdt[]={op_movzx16to32,op_movsx16to32,op_mov32,op_mov32,op_mov32}; + x86_opcode_class opmt[]={op_mul32,op_mul32,op_mul32,op_mul32,op_imul32}; + //only the top 32 bits are different on signed vs unsigned + + u32 opofs=op->op-shop_mul_u16; + + x86e->Emit(opdt[opofs],EAX,reg.mapg(op->rs1)); + x86e->Emit(opdt[opofs],EDX,reg.mapg(op->rs2)); + + x86e->Emit(opmt[opofs],EDX); + x86e->Emit(op_mov32,reg.mapg(op->rd),EAX); + + if (op->op>=shop_mul_u64) + x86e->Emit(op_mov32,reg.mapg(op->rd2),EDX); + } + break; + + + //fpu + case shop_fadd: + case shop_fsub: + case shop_fmul: + case shop_fdiv: + { + verify(reg.IsAllocf(op->rs1)); + verify(reg.IsAllocf(op->rs2)); + verify(reg.IsAllocf(op->rd)); + + const x86_opcode_class opcds[]= { op_addss, op_subss, op_mulss, op_divss }; + ngen_fp_bin(op,opcds[op->op-shop_fadd]); + } + break; + + case shop_fabs: + { + verify(reg.IsAllocf(op->rs1)); + verify(reg.IsAllocf(op->rd)); + + static DECL_ALIGN(16) u32 AND_ABS_MASK[4] = { 0x7FFFFFFF, 0x7FFFFFFF, 0x7FFFFFFF, 0x7FFFFFFF }; + + verify(op->rd._reg==op->rs1._reg); + x86e->Emit(op_pand,reg.mapf(op->rd),AND_ABS_MASK); + } + break; + + case shop_fneg: + { + verify(reg.IsAllocf(op->rs1)); + verify(reg.IsAllocf(op->rd)); + + static DECL_ALIGN(16) u32 XOR_NEG_MASK[4] = { 0x80000000, 0x80000000, 0x80000000, 0x80000000 }; + + verify(op->rd._reg==op->rs1._reg); + x86e->Emit(op_pxor,reg.mapf(op->rd),XOR_NEG_MASK); + } + break; + + case shop_fsca: + { + verify(op->rs1.is_r32i()); + + //verify(op->rd.is_vector); //double ? vector(2) ? + + verify(reg.IsAllocg(op->rs1)); + verify(reg.IsAllocf(op->rd,0) && reg.IsAllocf(op->rd,1)); + + //sin/cos + x86e->Emit(op_movzx16to32,EAX,reg.mapg(op->rs1)); + x86e->Emit(op_movss,reg.mapfv(op->rd,0),x86_mrm(EAX,sib_scale_8,x86_ptr(&sin_table->u[0]))); + x86e->Emit(op_movss,reg.mapfv(op->rd,1),x86_mrm(EAX,sib_scale_8,x86_ptr(&sin_table->u[1]))); + } + break; + + case shop_fipr: + { + //rd=rs1*rs2 (vectors) +// verify(!reg.IsAllocAny(op->rs1)); +// verify(!reg.IsAllocAny(op->rs2)); + verify(reg.IsAllocf(op->rd)); + + verify(op->rs1.is_r32fv()==4); + verify(op->rs2.is_r32fv()==4); + verify(op->rd.is_r32()); + + if (sse_3) + { + x86_reg xmm=reg.mapf(op->rd); + + x86e->Emit(op_movaps ,xmm,op->rs1.reg_ptr()); + x86e->Emit(op_mulps ,xmm,op->rs2.reg_ptr()); + //xmm0={a0 ,a1 ,a2 ,a3} + x86e->Emit(op_haddps,xmm,xmm); //xmm0={a0+a1 ,a2+a3 ,a0+a1 ,a2+a3} + x86e->Emit(op_haddps,xmm,xmm); //xmm0={(a0+a1)+(a2+a3) ,(a0+a1)+(a2+a3),(a0+a1)+(a2+a3),(a0+a1)+(a2+a3)} + } + else + { + x86_reg xmm=reg.mapf(op->rd); + + x86e->Emit(op_movaps ,xmm,op->rs1.reg_ptr()); + x86e->Emit(op_mulps ,xmm,op->rs2.reg_ptr()); + x86e->Emit(op_movhlps ,XMM1,xmm); + x86e->Emit(op_addps ,xmm,XMM1); + x86e->Emit(op_movaps ,XMM1,xmm); + x86e->Emit(op_shufps ,XMM1,XMM1,1); + x86e->Emit(op_addss ,xmm,XMM1); + } + } + break; + + case shop_fsqrt: + { + verify(reg.IsAllocf(op->rs1)); + verify(reg.IsAllocf(op->rd)); + + //rd=sqrt(rs1) + x86e->Emit(op_sqrtss ,reg.mapf(op->rd),reg.mapf(op->rs1)); + //x86e->Emit(op_movss ,op->rd.reg_ptr(),XMM0); + } + break; + + case shop_ftrv: + { +#ifdef PROF2 + x86e->Emit(op_add32,&vrd,16); +#endif + verify(!reg.IsAllocAny(op->rs1)); + verify(!reg.IsAllocAny(op->rs2)); + verify(!reg.IsAllocAny(op->rd)); + + //rd(vector)=rs1(vector)*rs2(matrix) + verify(op->rd.is_r32fv()==4); + verify(op->rs1.is_r32fv()==4); + verify(op->rs2.is_r32fv()==16); + +#if 1 + //load the vector .. + if (sse_2) + { + x86e->Emit(op_movaps ,XMM3,op->rs1.reg_ptr()); //xmm0=vector + x86e->Emit(op_pshufd ,XMM0,XMM3,0); //xmm0={v0} + x86e->Emit(op_pshufd ,XMM1,XMM3,0x55); //xmm1={v1} + x86e->Emit(op_pshufd ,XMM2,XMM3,0xaa); //xmm2={v2} + x86e->Emit(op_pshufd ,XMM3,XMM3,0xff); //xmm3={v3} + } + else + { + x86e->Emit(op_movaps ,XMM0,op->rs1.reg_ptr()); //xmm0=vector + + x86e->Emit(op_movaps ,XMM3,XMM0); //xmm3=vector + x86e->Emit(op_shufps ,XMM0,XMM0,0); //xmm0={v0} + x86e->Emit(op_movaps ,XMM1,XMM3); //xmm1=vector + x86e->Emit(op_movaps ,XMM2,XMM3); //xmm2=vector + x86e->Emit(op_shufps ,XMM3,XMM3,0xff); //xmm3={v3} + x86e->Emit(op_shufps ,XMM1,XMM1,0x55); //xmm1={v1} + x86e->Emit(op_shufps ,XMM2,XMM2,0xaa); //xmm2={v2} + } + + //do the matrix mult ! + x86e->Emit(op_mulps ,XMM0,op->rs2.reg_ptr() + 0); //v0*=vm0 + x86e->Emit(op_mulps ,XMM1,op->rs2.reg_ptr() + 4); //v1*=vm1 + x86e->Emit(op_mulps ,XMM2,op->rs2.reg_ptr() + 8); //v2*=vm2 + x86e->Emit(op_mulps ,XMM3,op->rs2.reg_ptr() + 12); //v3*=vm3 + + x86e->Emit(op_addps ,XMM0,XMM1); //sum it all up + x86e->Emit(op_addps ,XMM2,XMM3); + x86e->Emit(op_addps ,XMM0,XMM2); + + x86e->Emit(op_movaps ,op->rd.reg_ptr(),XMM0); +#else + /* + AABB CCDD + + ABCD * 0 1 2 3 0 1 4 5 + 4 5 6 7 2 3 6 7 + 8 9 a b 8 9 c d + c d e f a b e f + */ + + x86e->Emit(op_movaps ,XMM1,op->rs1.reg_ptr()); //xmm1=vector + + x86e->Emit(op_pshufd ,XMM0,XMM1,0x05); //xmm0={v0,v0,v1,v1} + x86e->Emit(op_pshufd ,XMM1,XMM1,0xaf); //xmm1={v2,v2,v3,v3} + + x86e->Emit(op_movaps,XMM2,XMM0); //xmm2={v0,v0,v1,v1} + x86e->Emit(op_movaps,XMM3,XMM1); //xmm3={v2,v2,v3,v3} + + x86e->Emit(op_mulps ,XMM0,op->rs2.reg_ptr() + 0); //aabb * 0145 + x86e->Emit(op_mulps ,XMM2,op->rs2.reg_ptr() + 4); //aabb * 2367 + x86e->Emit(op_mulps ,XMM1,op->rs2.reg_ptr() + 8); //ccdd * 89cd + x86e->Emit(op_mulps ,XMM3,op->rs2.reg_ptr() + 12); //ccdd * abef + + + x86e->Emit(op_addps ,XMM0,XMM1); //sum it all up + x86e->Emit(op_addps ,XMM2,XMM3); + + //XMM0 -> A0C8 | A1C9 | B4DC | B5DD + verify(sse_3); + + x86e->Emit(op_shufps,XMM0,XMM0,0x27); //A0C8 B4DC A1C9 B5DC + x86e->Emit(op_shufps,XMM2,XMM2,0x27); + + x86e->Emit(op_haddps,XMM0,XMM2); //haddps ={a0+a1 ,a2+a3 ,b0+b1 ,b2+b3} + + + x86e->Emit(op_movaps ,op->rd.reg_ptr(),XMM0); +#endif + } + break; + + case shop_fmac: + { + verify(reg.IsAllocf(op->rs1)); + verify(reg.IsAllocf(op->rs2)); + verify(reg.IsAllocf(op->rs3)); + verify(reg.IsAllocf(op->rd)); + + //rd=rs1+rs2*rs3 + //rd might be rs1,rs2 or rs3, so can't prestore here (iirc, rd==rs1==fr0) + x86e->Emit(op_movss ,XMM0,reg.mapf(op->rs2)); + x86e->Emit(op_mulss ,XMM0,reg.mapf(op->rs3)); + x86e->Emit(op_addss ,XMM0,reg.mapf(op->rs1)); + x86e->Emit(op_movss ,reg.mapf(op->rd),XMM0); + } + break; + + case shop_fsrra: + { + verify(reg.IsAllocf(op->rs1)); + verify(reg.IsAllocf(op->rd)); + + //rd=1/sqrt(rs1) + static float one=1.0f; + x86e->Emit(op_sqrtss ,XMM0,reg.mapf(op->rs1)); + x86e->Emit(op_movss ,reg.mapf(op->rd),&one); + x86e->Emit(op_divss ,reg.mapf(op->rd),XMM0); + } + break; + + case shop_fseteq: + case shop_fsetgt: + { + verify(reg.IsAllocf(op->rs1)); + verify(reg.IsAllocf(op->rs2)); + verify(reg.IsAllocg(op->rd)); + + //x86e->Emit(op_movss,XMM0,op->rs1.reg_ptr()); + x86e->Emit(op_ucomiss,reg.mapf(op->rs1),reg.mapf(op->rs2)); + + if (op->op==shop_fseteq) + { + //special case + //We want to take in account the 'unordered' case on the fpu + x86e->Emit(op_lahf); + x86e->Emit(op_test8,AH,0x44); + x86e->Emit(op_setnp,AL); + } + else + { + x86e->Emit(op_seta,AL); + } + + x86e->Emit(op_movzx8to32,reg.mapg(op->rd),AL); + } + break; + + case shop_pref: + { + verify(op->rs1.is_r32i()); + verify(reg.IsAllocg(op->rs1)); + + if (op->flags==0x1337) + { + // + x86e->Emit(op_mov32 ,ECX,reg.mapg(op->rs1)); + x86e->Emit(op_call,x86_ptr_imm(&VERIFYME)); //call do_sqw_mmu + } + + x86e->Emit(op_mov32 ,EDX,reg.mapg(op->rs1)); + x86e->Emit(op_mov32 ,ECX,reg.mapg(op->rs1)); + x86e->Emit(op_shr32 ,EDX,26); + + x86_Label* nosq=x86e->CreateLabel(false,8); + + x86e->Emit(op_cmp32,EDX,0x38); + x86e->Emit(op_jne,nosq); + { + if (CCN_MMUCR.AT) + x86e->Emit(op_call,x86_ptr_imm(&do_sqw_mmu)); //call do_sqw_mmu + else + { + x86e->Emit(op_mov32 ,EDX,(u32)sq_both); + x86e->Emit(op_call32,x86_ptr(&do_sqw_nommu)); //call [do_sqw_nommu] + } + } + x86e->MarkLabel(nosq); + } + break; + + case shop_ext_s8: + case shop_ext_s16: + { + verify(op->rd.is_r32i()); + verify(op->rs1.is_r32i()); + + verify(reg.IsAllocg(op->rd)); + verify(reg.IsAllocg(op->rs1)); + + x86e->Emit(op_mov32,EAX,reg.mapg(op->rs1)); + + if (op->op==shop_ext_s8) + x86e->Emit(op_movsx8to32,reg.mapg(op->rd),EAX); + else + x86e->Emit(op_movsx16to32,reg.mapg(op->rd),EAX); + } + break; + + case shop_cvt_f2i_t: + verify(op->rd.is_r32i()); + verify(op->rs1.is_r32f()); + verify(reg.IsAllocg(op->rd)); + verify(reg.IsAllocf(op->rs1)); + + x86e->Emit(op_cvttss2si,reg.mapg(op->rd),reg.mapf(op->rs1)); + break; + + //i hope that the round mode bit is set properly here :p + case shop_cvt_i2f_n: + case shop_cvt_i2f_z: + verify(op->rd.is_r32f()); + verify(op->rs1.is_r32i()); + verify(reg.IsAllocf(op->rd)); + verify(reg.IsAllocg(op->rs1)); + + x86e->Emit(op_cvtsi2ss,reg.mapf(op->rd),reg.mapg(op->rs1)); + //x86e->Emit(op_movss,op->rd.reg_ptr(),XMM0); + break; + + case shop_frswap: + { + verify(op->rd._reg==op->rs2._reg); + verify(op->rd2._reg==op->rs1._reg); + + verify(op->rs1.count()==16 && op->rs2.count()==16); + verify(op->rd2.count()==16 && op->rd.count()==16); +#ifdef PROF2 + x86e->Emit(op_add32,&vrd,32); +#endif + for (int i=0;i<4;i++) + { + x86e->Emit(op_movaps,XMM0,op->rs1.reg_ptr()+i*4); + x86e->Emit(op_movaps,XMM1,op->rs2.reg_ptr()+i*4); + x86e->Emit(op_movaps,op->rd.reg_ptr()+i*4,XMM0); + x86e->Emit(op_movaps,op->rd2.reg_ptr()+i*4,XMM1); + } + } + break; + + case shop_div32s: + case shop_div32u: + { + x86e->Emit(op_mov32,EAX,reg.mapg(op->rs1)); + if (op->op==shop_div32s) + x86e->Emit(op_cdq); + else + x86e->Emit(op_xor32,EDX,EDX); + + x86e->Emit(op->op==shop_div32s?op_idiv32:op_div32,reg.mapg(op->rs2)); + + x86e->Emit(op_mov32,reg.mapg(op->rd),EAX); + x86e->Emit(op_mov32,reg.mapg(op->rd2),EDX); + } + break; + + case shop_div32p2: + { + x86e->Emit(op_xor32,EAX,EAX); + x86e->Emit(op_cmp32,reg.mapg(op->rs3),0); + x86e->Emit(op_cmove32,EAX,reg.mapg(op->rs2)); + if (reg.mapg(op->rd)!=reg.mapg(op->rs1)) + x86e->Emit(op_mov32,reg.mapg(op->rd),reg.mapg(op->rs1)); + + x86e->Emit(op_sub32,reg.mapg(op->rd),EAX); + } + break; + + +#endif + + default: +#if 1 || CANONICAL_TEST + shil_chf[op->op](op); + break; +#endif + + +defaulty: + printf("OH CRAP %d\n",op->op); + verify(false); + } +} \ No newline at end of file diff --git a/core/rec-x86/win86_ngen.cpp b/core/rec-x86/win86_ngen.cpp new file mode 100644 index 000000000..64986ec51 --- /dev/null +++ b/core/rec-x86/win86_ngen.cpp @@ -0,0 +1,128 @@ +#include "win86_ngen.h" + +#if HOST_OS == OS_WINDOWS + +naked void ngen_LinkBlock_Shared_stub() +{ + __asm + { + pop ecx; + sub ecx,5; + call rdv_LinkBlock; + jmp eax; + } +} + +naked void ngen_LinkBlock_cond_Next_stub() +{ + __asm + { + mov edx,0 + jmp ngen_LinkBlock_Shared_stub; + } +} +naked void ngen_LinkBlock_cond_Branch_stub() +{ + __asm + { + mov edx,1 + jmp ngen_LinkBlock_Shared_stub; + } +} + +const u32 offs=offsetof(Sh4RCB,cntx.jdyn); +naked void ngen_LinkBlock_Generic_stub() +{ + __asm + { + mov edx,[p_sh4rcb]; + add edx,[offs]; + mov edx,[edx]; + jmp ngen_LinkBlock_Shared_stub; + } +} + + + + +naked void ngen_FailedToFindBlock_() +{ + __asm + { + mov ecx,esi; + call rdv_FailedToFindBlock; + jmp eax; + } +} + +void (*ngen_FailedToFindBlock)()=&ngen_FailedToFindBlock_; +naked void ngen_mainloop(void* cntx) +{ + __asm + { + push esi; + push edi; + push ebp; + push ebx; + + mov ecx,0xA0000000; + mov [cycle_counter],SH4_TIMESLICE; + + mov [loop_no_update],offset no_update; + mov [intc_sched],offset intc_sched_offs; + + mov eax,0; + //next_pc _MUST_ be on ecx +no_update: + mov esi,ecx; + call bm_GetCode + jmp eax; + +intc_sched_offs: + add [cycle_counter],SH4_TIMESLICE; + call UpdateSystem; + cmp eax,0; + jnz do_iter; + ret; + +do_iter: + pop ecx; + call rdv_DoInterrupts; + mov ecx,eax; +// cmp byte ptr [sh4_int_bCpuRun],0; + // jz cleanup; + jmp no_update; + +cleanup: + pop ebx; + pop ebp; + pop edi; + pop esi; + + ret; + } +} + + +naked void DYNACALL ngen_blockcheckfail(u32 addr) +{ + __asm + { + call rdv_BlockCheckFail; + jmp eax; + } +} + +naked void DYNACALL ngen_blockcheckfail2(u32 addr) +{ + __asm + { + int 3; + call rdv_BlockCheckFail; + jmp eax; + } +} +#else + u32 gas_offs=offsetof(Sh4RCB,cntx.jdyn); + void (*ngen_FailedToFindBlock)()=&ngen_FailedToFindBlock_; +#endif \ No newline at end of file diff --git a/core/rec-x86/win86_ngen.h b/core/rec-x86/win86_ngen.h new file mode 100644 index 000000000..680e9cc5c --- /dev/null +++ b/core/rec-x86/win86_ngen.h @@ -0,0 +1,59 @@ +#include "types.h" + +#include "hw/sh4/sh4_opcode_list.h" +#include "hw/sh4/modules/ccn.h" +#include "hw/sh4/sh4_interrupts.h" + +#include "hw/sh4/sh4_core.h" +#include "hw/sh4/dyna/ngen.h" +#include "hw/sh4/sh4_mem.h" +#include "hw/sh4/dyna/regalloc.h" +#include "emitter/x86_emitter.h" +#include "profiler/profiler.h" +#include "oslib/oslib.h" + +void ngen_opcode(RuntimeBlockInfo* block, shil_opcode* op,x86_block* x86e, bool staging, bool optimise); + +#if BUILD_COMPILER == COMPILER_GCC +extern "C" +{ +#endif + +void ngen_LinkBlock_Generic_stub(); +void ngen_LinkBlock_cond_Next_stub(); +void ngen_LinkBlock_cond_Branch_stub(); +void ngen_FailedToFindBlock_(); +void ngen_mainloop(void* p); + + +void DYNACALL ngen_blockcheckfail(u32 addr); +void DYNACALL ngen_blockcheckfail2(u32 addr); + +#if BUILD_COMPILER == COMPILER_GCC +} +#endif + +extern x86_block* x86e; + +extern u32 cycle_counter; + +extern void* loop_no_update; +extern void* intc_sched; + +extern bool sse_1; +extern bool sse_2; +extern bool sse_3; +extern bool ssse_3; +extern bool mmx; + +struct x86_reg_alloc: RegAlloc +{ + virtual void Preload(u32 reg,x86_reg nreg); + virtual void Writeback(u32 reg,x86_reg nreg); + virtual void Preload_FPU(u32 reg,x86_reg nreg); + virtual void Writeback_FPU(u32 reg,x86_reg nreg); + void FreezeXMM(); + void ThawXMM(); +}; + +extern x86_reg_alloc reg; diff --git a/core/rend/gles/gles.cpp b/core/rend/gles/gles.cpp index a0b079d68..5200a9e08 100755 --- a/core/rend/gles/gles.cpp +++ b/core/rend/gles/gles.cpp @@ -354,6 +354,7 @@ gl_ctx gl; int screen_width; int screen_height; +#if HOST_OS != OS_DARWIN #ifdef GLES // Create a basic GLES context bool gl_init(void* wind, void* disp) @@ -617,17 +618,45 @@ int screen_height; (GLXDrawable)libPvr_GetRenderTarget(), (GLXContext)x11_glc); + screen_width = 640; + screen_height = 480; return gl3wInit() != -1 && gl3wIsSupported(3, 1); } void gl_swap() { glXSwapBuffers((Display*)libPvr_GetRenderSurface(), (GLXDrawable)libPvr_GetRenderTarget()); + + Window win; + int temp; + unsigned int tempu, new_w, new_h; + XGetGeometry((Display*)libPvr_GetRenderSurface(), (GLXDrawable)libPvr_GetRenderTarget(), + &win, &temp, &temp, &new_w, &new_h,&tempu,&tempu); + + //if resized, clear up the draw buffers, to avoid out-of-draw-area junk data + if (new_w != screen_width || new_h != screen_height) { + screen_width = new_w; + screen_height = new_h; + } + + #if 0 + //handy to debug really stupid render-not-working issues ... + + glClearColor( 0, 0.5, 1, 1 ); + glClear( GL_COLOR_BUFFER_BIT ); + glXSwapBuffers((Display*)libPvr_GetRenderSurface(), (GLXDrawable)libPvr_GetRenderTarget()); + + + glClearColor ( 1, 0.5, 0, 1 ); + glClear ( GL_COLOR_BUFFER_BIT ); + glXSwapBuffers((Display*)libPvr_GetRenderSurface(), (GLXDrawable)libPvr_GetRenderTarget()); + #endif } #endif #endif #endif +#endif struct ShaderUniforms_t { @@ -932,7 +961,7 @@ bool gles_init() if (!gl_create_resources()) return false; -#ifdef GLES +#if defined(GLES) && HOST_OS != OS_DARWIN #ifdef TARGET_PANDORA fbdev=open("/dev/fb0", O_RDONLY); #else @@ -1411,6 +1440,7 @@ bool RenderFrame() bool is_rtt=pvrrc.isRTT; + OSD_HOOK(); //if (FrameCount&7) return; @@ -1706,7 +1736,10 @@ bool RenderFrame() } else { +#if HOST_OS != OS_DARWIN + //Fix this in a proper way glBindFramebuffer(GL_FRAMEBUFFER,0); +#endif } //Clear depth @@ -1745,6 +1778,14 @@ bool RenderFrame() //not all scaling affects pixel operations, scale to adjust for that scale_x *= scissoring_scale_x; + + #if 0 + //handy to debug really stupid render-not-working issues ... + printf("SS: %dx%d\n", screen_width, screen_height); + printf("SCI: %d, %f\n", pvrrc.fb_X_CLIP.max, dc2s_scale_h); + printf("SCI: %f, %f, %f, %f\n", offs_x+pvrrc.fb_X_CLIP.min/scale_x,(pvrrc.fb_Y_CLIP.min/scale_y)*dc2s_scale_h,(pvrrc.fb_X_CLIP.max-pvrrc.fb_X_CLIP.min+1)/scale_x*dc2s_scale_h,(pvrrc.fb_Y_CLIP.max-pvrrc.fb_Y_CLIP.min+1)/scale_y*dc2s_scale_h); + #endif + glScissor(offs_x+pvrrc.fb_X_CLIP.min/scale_x,(pvrrc.fb_Y_CLIP.min/scale_y)*dc2s_scale_h,(pvrrc.fb_X_CLIP.max-pvrrc.fb_X_CLIP.min+1)/scale_x*dc2s_scale_h,(pvrrc.fb_Y_CLIP.max-pvrrc.fb_Y_CLIP.min+1)/scale_y*dc2s_scale_h); if (settings.rend.WideScreen && pvrrc.fb_X_CLIP.min==0 && ((pvrrc.fb_X_CLIP.max+1)/scale_x==640) && (pvrrc.fb_Y_CLIP.min==0) && ((pvrrc.fb_Y_CLIP.max+1)/scale_y==480 ) ) { @@ -1753,6 +1794,7 @@ bool RenderFrame() else glEnable(GL_SCISSOR_TEST); + //restore scale_x scale_x /= scissoring_scale_x; @@ -1812,7 +1854,7 @@ void rend_set_fb_scale(float x,float y) struct glesrend : Renderer { bool Init() { return gles_init(); } - void Resize(int w, int h) { } + void Resize(int w, int h) { screen_width=w; screen_height=h; } void Term() { } bool Process(TA_context* ctx) { return ProcessFrame(ctx); } diff --git a/core/rend/gles/gles.h b/core/rend/gles/gles.h index ebe845908..0aaa6f04d 100755 --- a/core/rend/gles/gles.h +++ b/core/rend/gles/gles.h @@ -4,7 +4,7 @@ #ifdef GLES #ifdef TARGET_IPHONE //apple-specific ogles2 headers -#include +//#include #include #include #else @@ -57,7 +57,7 @@ struct PipelineShader struct gl_ctx { -#ifdef GLES +#if defined(GLES) && HOST_OS != OS_DARWIN struct { EGLNativeWindowType native_wind; diff --git a/core/rend/norend/norend.cpp b/core/rend/norend/norend.cpp index 494fbdd21..01d507df9 100644 --- a/core/rend/norend/norend.cpp +++ b/core/rend/norend/norend.cpp @@ -15,14 +15,20 @@ struct norend : Renderer void Resize(int w, int h) { } void Term() { } + + bool Process(TA_context* ctx) { return true; } + + void DrawOSD() { } + bool Render() { - return !pvrrc.isRTT; + return true;//!pvrrc.isRTT; } - bool Process(TA_context*) { } void Present() { } }; Renderer* rend_norend() { return new norend(); } + +u32 GetTexture(TSP tsp,TCW tcw) { return 0; } diff --git a/core/rend/rend.h b/core/rend/rend.h index 25c7b56fc..3386fbdf8 100644 --- a/core/rend/rend.h +++ b/core/rend/rend.h @@ -1,3 +1,11 @@ #pragma once #include "hw/pvr/ta_ctx.h" -#include "hw/pvr/Renderer_if.h" \ No newline at end of file +#include "hw/pvr/Renderer_if.h" + + +#ifdef GLuint +GLuint +#else +u32 +#endif +GetTexture(TSP tsp,TCW tcw); diff --git a/core/stdclass.h b/core/stdclass.h index f7f351bbc..529927e33 100644 --- a/core/stdclass.h +++ b/core/stdclass.h @@ -220,7 +220,7 @@ public : #if HOST_OS==OS_WINDOWS InitializeCriticalSection(&cs); #else - mutx=PTHREAD_MUTEX_INITIALIZER; + pthread_mutex_init ( &mutx, NULL); #endif } ~cMutex() diff --git a/core/types.h b/core/types.h index 4d3636488..e90e5c3c4 100644 --- a/core/types.h +++ b/core/types.h @@ -3,18 +3,25 @@ #include "build.h" #if BUILD_COMPILER==COMPILER_VC -#define ALIGN(x) __declspec(align(x)) +#define DECL_ALIGN(x) __declspec(align(x)) #else #define __forceinline inline -#define ALIGN(x) __attribute__((aligned(x))) +#define DECL_ALIGN(x) __attribute__((aligned(x))) #define __debugbreak #endif -#if BUILD_COMPILER==COMPILER_VC -#define DYNACALL __fastcall +#if HOST_CPU == CPU_X86 + + #if BUILD_COMPILER==COMPILER_VC + #define DYNACALL __fastcall + #else + //android defines fastcall as regparm(3), it doesn't work for us + #undef fastcall + #define DYNACALL __attribute__((fastcall)) + #endif #else -#define DYNACALL + #define DYNACALL #endif #if BUILD_COMPILER==COMPILER_VC @@ -509,7 +516,6 @@ void os_DebugBreak(); #define stricmp strcasecmp #endif -//#define __fastcall #ifndef STRIP_TEXT #define verify(x) if((x)==false){ msgboxf("Verify Failed : " #x "\n in %s -> %s : %d \n",MBX_ICONERROR,(__FUNCTION__),(__FILE__),__LINE__); dbgbreak;} #define die(reason) { msgboxf("Fatal error : %s\n in %s -> %s : %d \n",MBX_ICONERROR,(reason),(__FUNCTION__),(__FILE__),__LINE__); dbgbreak;} diff --git a/core/windows/win86_driver.cpp b/core/windows/win86_driver.cpp index 41efb2630..b59db8961 100644 --- a/core/windows/win86_driver.cpp +++ b/core/windows/win86_driver.cpp @@ -107,7 +107,7 @@ u32 csc_sidx=1; x86_reg alloc_regs[]={EBX,EBP,ESI,EDI,NO_REG}; x86_reg xmm_alloc_regs[]={XMM7,XMM6,XMM5,XMM4,NO_REG}; -f32 ALIGN(16) thaw_regs[4]; +f32 DECL_ALIGN(16) thaw_regs[4]; void x86_reg_alloc::Preload(u32 reg,x86_reg nreg) @@ -299,7 +299,7 @@ void ngen_Compile(RuntimeBlockInfo* block,bool force_checks, bool reset, bool st x86e->x86_size=emit_FreeSpace(); x86e->do_realloc=false; - block->code=(DynarecCodeEntry*)emit_GetCCPtr(); + block->code=(DynarecCodeEntryPtr)emit_GetCCPtr(); x86e->Emit(op_add32,&memops_t,block->memops); x86e->Emit(op_add32,&memops_l,block->linkedmemops); diff --git a/core/windows/win86_il.cpp b/core/windows/win86_il.cpp index b75b98330..13917124b 100644 --- a/core/windows/win86_il.cpp +++ b/core/windows/win86_il.cpp @@ -1168,7 +1168,7 @@ void ngen_opcode(RuntimeBlockInfo* block, shil_opcode* op,x86_block* x86e, bool verify(reg.IsAllocf(op->rs1)); verify(reg.IsAllocf(op->rd)); - static ALIGN(16) u32 AND_ABS_MASK[4]={0x7FFFFFFF,0x7FFFFFFF,0x7FFFFFFF,0x7FFFFFFF}; + static DECL_ALIGN(16) u32 AND_ABS_MASK[4] = { 0x7FFFFFFF, 0x7FFFFFFF, 0x7FFFFFFF, 0x7FFFFFFF }; verify(op->rd._reg==op->rs1._reg); x86e->Emit(op_pand,reg.mapf(op->rd),AND_ABS_MASK); @@ -1180,7 +1180,7 @@ void ngen_opcode(RuntimeBlockInfo* block, shil_opcode* op,x86_block* x86e, bool verify(reg.IsAllocf(op->rs1)); verify(reg.IsAllocf(op->rd)); - static ALIGN(16) u32 XOR_NEG_MASK[4]={0x80000000,0x80000000,0x80000000,0x80000000}; + static DECL_ALIGN(16) u32 XOR_NEG_MASK[4] = { 0x80000000, 0x80000000, 0x80000000, 0x80000000 }; verify(op->rd._reg==op->rs1._reg); x86e->Emit(op_pxor,reg.mapf(op->rd),XOR_NEG_MASK); diff --git a/shell/android/jni/Android.mk b/shell/android/jni/Android.mk index ec4ce06f3..80b9fbac9 100644 --- a/shell/android/jni/Android.mk +++ b/shell/android/jni/Android.mk @@ -24,22 +24,41 @@ WEBUI := 1 ifneq ($(TARGET_ARCH_ABI),armeabi-v7a) NOT_ARM := 1 - NO_REC := 1 +else + NOT_ARM := +endif + +ifeq ($(TARGET_ARCH_ABI),x86) + X86_REC := 1 +else + X86_REC := endif ifeq ($(TARGET_ARCH_ABI),mips) ISMIPS := 1 + NO_REC := 1 +else + ISMIPS := + NO_REC := endif +$(info $$TARGET_ARCH_ABI is [${TARGET_ARCH_ABI}]) + include $(LOCAL_PATH)/../../core/core.mk LOCAL_SRC_FILES := $(RZDCY_FILES) LOCAL_SRC_FILES += $(wildcard $(LOCAL_PATH)/jni/src/Android.cpp) LOCAL_SRC_FILES += $(wildcard $(LOCAL_PATH)/jni/src/utils.cpp) -LOCAL_CFLAGS := $(RZDCY_CFLAGS) -fvisibility=hidden -fvisibility-inlines-hidden -ffunction-sections -fdata-sections +LOCAL_CFLAGS := $(RZDCY_CFLAGS) -fvisibility=hidden -ffunction-sections -fdata-sections LOCAL_CXXFLAGS := $(RZDCY_CXXFLAGS) -fvisibility=hidden -fvisibility-inlines-hidden -ffunction-sections -fdata-sections LOCAL_CPPFLAGS := $(RZDCY_CXXFLAGS) -fvisibility=hidden -fvisibility-inlines-hidden -ffunction-sections -fdata-sections +ifeq ($(TARGET_ARCH_ABI),x86) + LOCAL_CFLAGS+= -DHOST_NO_AREC + LOCAL_CXXFLAGS+= -DHOST_NO_AREC -fpermissive + LOCAL_CPPFLAGS+= -DHOST_NO_AREC +endif + LOCAL_CPP_FEATURES := LOCAL_SHARED_LIBRARIES:= libcutils libutils LOCAL_PRELINK_MODULE := false diff --git a/shell/ios/emulator.xcodeproj/project.pbxproj b/shell/ios/emulator.xcodeproj/project.pbxproj index 42bc4997a..f9a3d2ee8 100644 --- a/shell/ios/emulator.xcodeproj/project.pbxproj +++ b/shell/ios/emulator.xcodeproj/project.pbxproj @@ -7,6 +7,23 @@ objects = { /* Begin PBXBuildFile section */ + 846293C61A6CE61900262464 /* EmulatorView.mm in Sources */ = {isa = PBXBuildFile; fileRef = 846293C51A6CE61900262464 /* EmulatorView.mm */; }; + 8497BCBF1A41A0E900EFB9ED /* common.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8497BCBC1A41A0E900EFB9ED /* common.cpp */; }; + 8497BCC01A41A0E900EFB9ED /* nixprof.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8497BCBD1A41A0E900EFB9ED /* nixprof.cpp */; }; + 8497BCC21A41B02000EFB9ED /* ios_main.mm in Sources */ = {isa = PBXBuildFile; fileRef = 8497BCC11A41B02000EFB9ED /* ios_main.mm */; }; + 8497BCC91A41BFBA00EFB9ED /* alsa_audiostream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8497BCC41A41BFBA00EFB9ED /* alsa_audiostream.cpp */; }; + 8497BCCA1A41BFBA00EFB9ED /* audiostream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8497BCC51A41BFBA00EFB9ED /* audiostream.cpp */; }; + 8497BCCB1A41BFBA00EFB9ED /* ds_audiostream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8497BCC71A41BFBA00EFB9ED /* ds_audiostream.cpp */; }; + 8497BCCF1A41BFD800EFB9ED /* coreio.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 8497BCCD1A41BFD800EFB9ED /* coreio.cpp */; }; + 849C0D621B072C07008BAAA4 /* context.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 849C0D601B072C07008BAAA4 /* context.cpp */; }; + 849C0D661B072CF8008BAAA4 /* reios.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 849C0D641B072CF8008BAAA4 /* reios.cpp */; }; + 849C0D6D1B072D14008BAAA4 /* descrambl.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 849C0D671B072D14008BAAA4 /* descrambl.cpp */; }; + 849C0D6E1B072D14008BAAA4 /* gdrom_hle.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 849C0D691B072D14008BAAA4 /* gdrom_hle.cpp */; }; + 849C0D6F1B072D14008BAAA4 /* reios_elf.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 849C0D6B1B072D14008BAAA4 /* reios_elf.cpp */; }; + 8703BC3B1A44B8DA00E7E939 /* Icon-72.png in Resources */ = {isa = PBXBuildFile; fileRef = 8703BC371A44B8DA00E7E939 /* Icon-72.png */; }; + 8703BC3C1A44B8DA00E7E939 /* Icon-72@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = 8703BC381A44B8DA00E7E939 /* Icon-72@2x.png */; }; + 8703BC3D1A44B8DA00E7E939 /* Icon.png in Resources */ = {isa = PBXBuildFile; fileRef = 8703BC391A44B8DA00E7E939 /* Icon.png */; }; + 8703BC3E1A44B8DA00E7E939 /* Icon@2x.png in Resources */ = {isa = PBXBuildFile; fileRef = 8703BC3A1A44B8DA00E7E939 /* Icon@2x.png */; }; 87078A8718A47FE90034C7A0 /* Foundation.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 87078A8618A47FE90034C7A0 /* Foundation.framework */; }; 87078A8918A47FE90034C7A0 /* CoreGraphics.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 87078A8818A47FE90034C7A0 /* CoreGraphics.framework */; }; 87078A8B18A47FE90034C7A0 /* UIKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 87078A8A18A47FE90034C7A0 /* UIKit.framework */; }; @@ -16,8 +33,9 @@ 87078A9B18A47FE90034C7A0 /* AppDelegate.m in Sources */ = {isa = PBXBuildFile; fileRef = 87078A9A18A47FE90034C7A0 /* AppDelegate.m */; }; 87078AA318A47FE90034C7A0 /* Shader.fsh in Resources */ = {isa = PBXBuildFile; fileRef = 87078AA218A47FE90034C7A0 /* Shader.fsh */; }; 87078AA518A47FE90034C7A0 /* Shader.vsh in Resources */ = {isa = PBXBuildFile; fileRef = 87078AA418A47FE90034C7A0 /* Shader.vsh */; }; - 87078AA818A47FE90034C7A0 /* EmulatorViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 87078AA718A47FE90034C7A0 /* EmulatorViewController.m */; }; - 87078AAA18A47FE90034C7A0 /* Images.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 87078AA918A47FE90034C7A0 /* Images.xcassets */; }; + 87078AA818A47FE90034C7A0 /* EmulatorViewController.mm in Sources */ = {isa = PBXBuildFile; fileRef = 87078AA718A47FE90034C7A0 /* EmulatorViewController.mm */; }; + 87C4AA541A440BEB0048DBF4 /* libz.dylib in Frameworks */ = {isa = PBXBuildFile; fileRef = 87C4AA531A440BEB0048DBF4 /* libz.dylib */; }; + 87C4AA561A4414070048DBF4 /* AssetsLibrary.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 87C4AA551A4414070048DBF4 /* AssetsLibrary.framework */; }; 9C7A393318C804A80070BB5F /* reicast.entitlements in Resources */ = {isa = PBXBuildFile; fileRef = 9C7A393218C804A80070BB5F /* reicast.entitlements */; }; 9C7A3AA218C806E00070BB5F /* cfg.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A395118C806DE0070BB5F /* cfg.cpp */; }; 9C7A3AA318C806E00070BB5F /* cl.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A395318C806DE0070BB5F /* cl.cpp */; }; @@ -169,22 +187,15 @@ 9C7A3B3818C806E00070BB5F /* gdi.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A6018C806E00070BB5F /* gdi.cpp */; }; 9C7A3B3918C806E00070BB5F /* ImgReader.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A6118C806E00070BB5F /* ImgReader.cpp */; }; 9C7A3B3A18C806E00070BB5F /* ioctl.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A6318C806E00070BB5F /* ioctl.cpp */; }; - 9C7A3B3E18C806E00070BB5F /* nacl.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A7B18C806E00070BB5F /* nacl.cpp */; }; 9C7A3B3F18C806E00070BB5F /* nullDC.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A7C18C806E00070BB5F /* nullDC.cpp */; }; - 9C7A3B4018C806E00070BB5F /* alsa_audiostream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A7E18C806E00070BB5F /* alsa_audiostream.cpp */; }; - 9C7A3B4118C806E00070BB5F /* audiostream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A7F18C806E00070BB5F /* audiostream.cpp */; }; - 9C7A3B4218C806E00070BB5F /* ds_audiostream.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A8118C806E00070BB5F /* ds_audiostream.cpp */; }; 9C7A3B4318C806E00070BB5F /* profiler.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A8418C806E00070BB5F /* profiler.cpp */; }; 9C7A3B4418C806E00070BB5F /* README.md in Resources */ = {isa = PBXBuildFile; fileRef = 9C7A3A8618C806E00070BB5F /* README.md */; }; 9C7A3B4518C806E00070BB5F /* arm_dyna.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A8818C806E00070BB5F /* arm_dyna.cpp */; }; 9C7A3B4618C806E00070BB5F /* ngen_arm.S in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A8918C806E00070BB5F /* ngen_arm.S */; }; - 9C7A3B4718C806E00070BB5F /* d3d11.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A8C18C806E00070BB5F /* d3d11.cpp */; }; 9C7A3B4818C806E00070BB5F /* gldraw.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A8E18C806E00070BB5F /* gldraw.cpp */; }; 9C7A3B4918C806E00070BB5F /* gles.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A8F18C806E00070BB5F /* gles.cpp */; }; 9C7A3B4A18C806E00070BB5F /* gltex.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A9118C806E00070BB5F /* gltex.cpp */; }; - 9C7A3B4B18C806E00070BB5F /* norend.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A9318C806E00070BB5F /* norend.cpp */; }; 9C7A3B4C18C806E00070BB5F /* TexCache.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A9518C806E00070BB5F /* TexCache.cpp */; }; - 9C7A3B4D18C806E00070BB5F /* main.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A9818C806E00070BB5F /* main.cpp */; }; 9C7A3B4E18C806E00070BB5F /* stdclass.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3A9918C806E00070BB5F /* stdclass.cpp */; }; 9C7A3B5918C81A4F0070BB5F /* SWRevealViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3B5818C81A4F0070BB5F /* SWRevealViewController.m */; }; 9C7A3B5C18C81BC80070BB5F /* SideDrawerViewController.m in Sources */ = {isa = PBXBuildFile; fileRef = 9C7A3B5B18C81BC80070BB5F /* SideDrawerViewController.m */; }; @@ -220,6 +231,33 @@ /* End PBXBuildFile section */ /* Begin PBXFileReference section */ + 846293C41A6CE61900262464 /* EmulatorView.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = EmulatorView.h; path = emulator/EmulatorView.h; sourceTree = ""; }; + 846293C51A6CE61900262464 /* EmulatorView.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = EmulatorView.mm; path = emulator/EmulatorView.mm; sourceTree = ""; }; + 8497BCBC1A41A0E900EFB9ED /* common.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = common.cpp; sourceTree = ""; }; + 8497BCBD1A41A0E900EFB9ED /* nixprof.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = nixprof.cpp; sourceTree = ""; }; + 8497BCBE1A41A0E900EFB9ED /* typedefs.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = typedefs.h; sourceTree = ""; }; + 8497BCC11A41B02000EFB9ED /* ios_main.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = ios_main.mm; sourceTree = ""; }; + 8497BCC41A41BFBA00EFB9ED /* alsa_audiostream.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = alsa_audiostream.cpp; sourceTree = ""; }; + 8497BCC51A41BFBA00EFB9ED /* audiostream.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = audiostream.cpp; sourceTree = ""; }; + 8497BCC61A41BFBA00EFB9ED /* audiostream_rif.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = audiostream_rif.h; sourceTree = ""; }; + 8497BCC71A41BFBA00EFB9ED /* ds_audiostream.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ds_audiostream.cpp; sourceTree = ""; }; + 8497BCC81A41BFBA00EFB9ED /* oslib.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = oslib.h; sourceTree = ""; }; + 8497BCCD1A41BFD800EFB9ED /* coreio.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = coreio.cpp; sourceTree = ""; }; + 8497BCCE1A41BFD800EFB9ED /* coreio.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = coreio.h; sourceTree = ""; }; + 849C0D601B072C07008BAAA4 /* context.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = context.cpp; sourceTree = ""; }; + 849C0D611B072C07008BAAA4 /* context.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = context.h; sourceTree = ""; }; + 849C0D641B072CF8008BAAA4 /* reios.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = reios.cpp; path = reios/reios.cpp; sourceTree = ""; }; + 849C0D651B072CF8008BAAA4 /* reios.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = reios.h; path = reios/reios.h; sourceTree = ""; }; + 849C0D671B072D14008BAAA4 /* descrambl.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = descrambl.cpp; path = reios/descrambl.cpp; sourceTree = ""; }; + 849C0D681B072D14008BAAA4 /* descrambl.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = descrambl.h; path = reios/descrambl.h; sourceTree = ""; }; + 849C0D691B072D14008BAAA4 /* gdrom_hle.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = gdrom_hle.cpp; path = reios/gdrom_hle.cpp; sourceTree = ""; }; + 849C0D6A1B072D14008BAAA4 /* gdrom_hle.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = gdrom_hle.h; path = reios/gdrom_hle.h; sourceTree = ""; }; + 849C0D6B1B072D14008BAAA4 /* reios_elf.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = reios_elf.cpp; path = reios/reios_elf.cpp; sourceTree = ""; }; + 849C0D6C1B072D14008BAAA4 /* reios_elf.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = reios_elf.h; path = reios/reios_elf.h; sourceTree = ""; }; + 8703BC371A44B8DA00E7E939 /* Icon-72.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = "Icon-72.png"; sourceTree = ""; }; + 8703BC381A44B8DA00E7E939 /* Icon-72@2x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = "Icon-72@2x.png"; sourceTree = ""; }; + 8703BC391A44B8DA00E7E939 /* Icon.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = Icon.png; sourceTree = ""; }; + 8703BC3A1A44B8DA00E7E939 /* Icon@2x.png */ = {isa = PBXFileReference; lastKnownFileType = image.png; path = "Icon@2x.png"; sourceTree = ""; }; 87078A8318A47FE90034C7A0 /* emulator.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = emulator.app; sourceTree = BUILT_PRODUCTS_DIR; }; 87078A8618A47FE90034C7A0 /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Foundation.framework; path = System/Library/Frameworks/Foundation.framework; sourceTree = SDKROOT; }; 87078A8818A47FE90034C7A0 /* CoreGraphics.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = CoreGraphics.framework; path = System/Library/Frameworks/CoreGraphics.framework; sourceTree = SDKROOT; }; @@ -234,9 +272,10 @@ 87078AA218A47FE90034C7A0 /* Shader.fsh */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.glsl; name = Shader.fsh; path = Shaders/Shader.fsh; sourceTree = ""; }; 87078AA418A47FE90034C7A0 /* Shader.vsh */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.glsl; name = Shader.vsh; path = Shaders/Shader.vsh; sourceTree = ""; }; 87078AA618A47FE90034C7A0 /* EmulatorViewController.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = EmulatorViewController.h; path = emulator/EmulatorViewController.h; sourceTree = ""; }; - 87078AA718A47FE90034C7A0 /* EmulatorViewController.m */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.objc; name = EmulatorViewController.m; path = emulator/EmulatorViewController.m; sourceTree = ""; }; - 87078AA918A47FE90034C7A0 /* Images.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; name = Images.xcassets; path = emulator/Images.xcassets; sourceTree = ""; }; + 87078AA718A47FE90034C7A0 /* EmulatorViewController.mm */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.objcpp; name = EmulatorViewController.mm; path = emulator/EmulatorViewController.mm; sourceTree = ""; }; 87078AB018A47FE90034C7A0 /* XCTest.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = XCTest.framework; path = Library/Frameworks/XCTest.framework; sourceTree = DEVELOPER_DIR; }; + 87C4AA531A440BEB0048DBF4 /* libz.dylib */ = {isa = PBXFileReference; lastKnownFileType = "compiled.mach-o.dylib"; name = libz.dylib; path = usr/lib/libz.dylib; sourceTree = SDKROOT; }; + 87C4AA551A4414070048DBF4 /* AssetsLibrary.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = AssetsLibrary.framework; path = System/Library/Frameworks/AssetsLibrary.framework; sourceTree = SDKROOT; }; 9C7A393218C804A80070BB5F /* reicast.entitlements */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.xml; path = reicast.entitlements; sourceTree = ""; }; 9C7A393A18C806DE0070BB5F /* arm_coding.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = arm_coding.h; sourceTree = ""; }; 9C7A393B18C806DE0070BB5F /* arm_disasm.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = arm_disasm.h; sourceTree = ""; }; @@ -510,28 +549,19 @@ 9C7A3A7018C806E00070BB5F /* gl3.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = gl3.h; sourceTree = ""; }; 9C7A3A7118C806E00070BB5F /* gl3platform.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = gl3platform.h; sourceTree = ""; }; 9C7A3A7318C806E00070BB5F /* khrplatform.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = khrplatform.h; sourceTree = ""; }; - 9C7A3A7B18C806E00070BB5F /* nacl.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = nacl.cpp; sourceTree = ""; }; 9C7A3A7C18C806E00070BB5F /* nullDC.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = nullDC.cpp; sourceTree = ""; }; - 9C7A3A7E18C806E00070BB5F /* alsa_audiostream.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = alsa_audiostream.cpp; sourceTree = ""; }; - 9C7A3A7F18C806E00070BB5F /* audiostream.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = audiostream.cpp; sourceTree = ""; }; - 9C7A3A8018C806E00070BB5F /* audiostream_rif.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = audiostream_rif.h; sourceTree = ""; }; - 9C7A3A8118C806E00070BB5F /* ds_audiostream.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ds_audiostream.cpp; sourceTree = ""; }; - 9C7A3A8218C806E00070BB5F /* oslib.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = oslib.h; sourceTree = ""; }; 9C7A3A8418C806E00070BB5F /* profiler.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = profiler.cpp; sourceTree = ""; }; 9C7A3A8518C806E00070BB5F /* profiler.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = profiler.h; sourceTree = ""; }; 9C7A3A8618C806E00070BB5F /* README.md */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = README.md; sourceTree = ""; }; 9C7A3A8818C806E00070BB5F /* arm_dyna.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = arm_dyna.cpp; sourceTree = ""; }; 9C7A3A8918C806E00070BB5F /* ngen_arm.S */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.asm; path = ngen_arm.S; sourceTree = ""; usesTabs = 1; }; - 9C7A3A8C18C806E00070BB5F /* d3d11.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = d3d11.cpp; sourceTree = ""; }; 9C7A3A8E18C806E00070BB5F /* gldraw.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = gldraw.cpp; sourceTree = ""; }; 9C7A3A8F18C806E00070BB5F /* gles.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = gles.cpp; sourceTree = ""; }; 9C7A3A9018C806E00070BB5F /* gles.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = gles.h; sourceTree = ""; }; 9C7A3A9118C806E00070BB5F /* gltex.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = gltex.cpp; sourceTree = ""; }; - 9C7A3A9318C806E00070BB5F /* norend.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = norend.cpp; sourceTree = ""; }; 9C7A3A9418C806E00070BB5F /* rend.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = rend.h; sourceTree = ""; }; 9C7A3A9518C806E00070BB5F /* TexCache.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = TexCache.cpp; sourceTree = ""; }; 9C7A3A9618C806E00070BB5F /* TexCache.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = TexCache.h; sourceTree = ""; }; - 9C7A3A9818C806E00070BB5F /* main.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = main.cpp; sourceTree = ""; }; 9C7A3A9918C806E00070BB5F /* stdclass.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = stdclass.cpp; sourceTree = ""; }; 9C7A3A9A18C806E00070BB5F /* stdclass.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = stdclass.h; sourceTree = ""; }; 9C7A3A9B18C806E00070BB5F /* types.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = types.h; sourceTree = ""; }; @@ -581,6 +611,8 @@ isa = PBXFrameworksBuildPhase; buildActionMask = 2147483647; files = ( + 87C4AA561A4414070048DBF4 /* AssetsLibrary.framework in Frameworks */, + 87C4AA541A440BEB0048DBF4 /* libz.dylib in Frameworks */, 87078A8F18A47FE90034C7A0 /* OpenGLES.framework in Frameworks */, 87078A8918A47FE90034C7A0 /* CoreGraphics.framework in Frameworks */, 87078A8B18A47FE90034C7A0 /* UIKit.framework in Frameworks */, @@ -592,6 +624,66 @@ /* End PBXFrameworksBuildPhase section */ /* Begin PBXGroup section */ + 8497BCBB1A41A0E900EFB9ED /* linux */ = { + isa = PBXGroup; + children = ( + 849C0D601B072C07008BAAA4 /* context.cpp */, + 849C0D611B072C07008BAAA4 /* context.h */, + 8497BCBC1A41A0E900EFB9ED /* common.cpp */, + 8497BCBD1A41A0E900EFB9ED /* nixprof.cpp */, + 8497BCBE1A41A0E900EFB9ED /* typedefs.h */, + ); + path = linux; + sourceTree = ""; + }; + 8497BCC31A41BFBA00EFB9ED /* oslib */ = { + isa = PBXGroup; + children = ( + 8497BCC41A41BFBA00EFB9ED /* alsa_audiostream.cpp */, + 8497BCC51A41BFBA00EFB9ED /* audiostream.cpp */, + 8497BCC61A41BFBA00EFB9ED /* audiostream_rif.h */, + 8497BCC71A41BFBA00EFB9ED /* ds_audiostream.cpp */, + 8497BCC81A41BFBA00EFB9ED /* oslib.h */, + ); + path = oslib; + sourceTree = ""; + }; + 8497BCCC1A41BFD800EFB9ED /* coreio */ = { + isa = PBXGroup; + children = ( + 8497BCCD1A41BFD800EFB9ED /* coreio.cpp */, + 8497BCCE1A41BFD800EFB9ED /* coreio.h */, + ); + name = coreio; + path = deps/coreio; + sourceTree = ""; + }; + 849C0D631B072CE0008BAAA4 /* reios */ = { + isa = PBXGroup; + children = ( + 849C0D671B072D14008BAAA4 /* descrambl.cpp */, + 849C0D681B072D14008BAAA4 /* descrambl.h */, + 849C0D691B072D14008BAAA4 /* gdrom_hle.cpp */, + 849C0D6A1B072D14008BAAA4 /* gdrom_hle.h */, + 849C0D6B1B072D14008BAAA4 /* reios_elf.cpp */, + 849C0D6C1B072D14008BAAA4 /* reios_elf.h */, + 849C0D641B072CF8008BAAA4 /* reios.cpp */, + 849C0D651B072CF8008BAAA4 /* reios.h */, + ); + name = reios; + sourceTree = ""; + }; + 8703BC361A44B8DA00E7E939 /* assets */ = { + isa = PBXGroup; + children = ( + 8703BC371A44B8DA00E7E939 /* Icon-72.png */, + 8703BC381A44B8DA00E7E939 /* Icon-72@2x.png */, + 8703BC391A44B8DA00E7E939 /* Icon.png */, + 8703BC3A1A44B8DA00E7E939 /* Icon@2x.png */, + ); + path = assets; + sourceTree = ""; + }; 87078A7A18A47FE90034C7A0 = { isa = PBXGroup; children = ( @@ -612,6 +704,8 @@ 87078A8518A47FE90034C7A0 /* Frameworks */ = { isa = PBXGroup; children = ( + 87C4AA551A4414070048DBF4 /* AssetsLibrary.framework */, + 87C4AA531A440BEB0048DBF4 /* libz.dylib */, 87078A8618A47FE90034C7A0 /* Foundation.framework */, 87078A8818A47FE90034C7A0 /* CoreGraphics.framework */, 87078A8A18A47FE90034C7A0 /* UIKit.framework */, @@ -636,6 +730,7 @@ 9C7A393418C805980070BB5F /* Third-Party Frameworks */, 87078A9118A47FE90034C7A0 /* Supporting Files */, 9C7A393818C806DE0070BB5F /* Emulator Core Code */, + 8497BCC11A41B02000EFB9ED /* ios_main.mm */, ); name = reicast; path = emulator; @@ -644,6 +739,7 @@ 87078A9118A47FE90034C7A0 /* Supporting Files */ = { isa = PBXGroup; children = ( + 8703BC361A44B8DA00E7E939 /* assets */, 87078A9218A47FE90034C7A0 /* emulator-Info.plist */, 87078A9618A47FE90034C7A0 /* main.m */, 87078A9818A47FE90034C7A0 /* emulator-Prefix.pch */, @@ -678,7 +774,9 @@ 9C7A3B5A18C81BC80070BB5F /* SideDrawerViewController.h */, 9C7A3B5B18C81BC80070BB5F /* SideDrawerViewController.m */, 87078AA618A47FE90034C7A0 /* EmulatorViewController.h */, - 87078AA718A47FE90034C7A0 /* EmulatorViewController.m */, + 87078AA718A47FE90034C7A0 /* EmulatorViewController.mm */, + 846293C41A6CE61900262464 /* EmulatorView.h */, + 846293C51A6CE61900262464 /* EmulatorView.mm */, ); name = "View Controller Subclasses"; path = ..; @@ -709,7 +807,6 @@ 9C7A3BFC18C851C50070BB5F /* RTrigger@2x.png */, 9C7A3BFD18C851C50070BB5F /* Start.png */, 9C7A3BFE18C851C50070BB5F /* Start@2x.png */, - 87078AA918A47FE90034C7A0 /* Images.xcassets */, ); name = Images; path = ..; @@ -718,6 +815,10 @@ 9C7A393818C806DE0070BB5F /* Emulator Core Code */ = { isa = PBXGroup; children = ( + 849C0D631B072CE0008BAAA4 /* reios */, + 8497BCCC1A41BFD800EFB9ED /* coreio */, + 8497BCC31A41BFBA00EFB9ED /* oslib */, + 8497BCBB1A41A0E900EFB9ED /* linux */, 9C7A393918C806DE0070BB5F /* arm_emitter */, 9C7A394F18C806DE0070BB5F /* build.h */, 9C7A395018C806DE0070BB5F /* cfg */, @@ -726,14 +827,11 @@ 9C7A39DE18C806DF0070BB5F /* hw */, 9C7A3A5A18C806E00070BB5F /* imgread */, 9C7A3A6518C806E00070BB5F /* khronos */, - 9C7A3A7A18C806E00070BB5F /* nacl */, 9C7A3A7C18C806E00070BB5F /* nullDC.cpp */, - 9C7A3A7D18C806E00070BB5F /* oslib */, 9C7A3A8318C806E00070BB5F /* profiler */, 9C7A3A8618C806E00070BB5F /* README.md */, 9C7A3A8718C806E00070BB5F /* rec-ARM */, 9C7A3A8A18C806E00070BB5F /* rend */, - 9C7A3A9718C806E00070BB5F /* sdl */, 9C7A3A9918C806E00070BB5F /* stdclass.cpp */, 9C7A3A9A18C806E00070BB5F /* stdclass.h */, 9C7A3A9B18C806E00070BB5F /* types.h */, @@ -1238,26 +1336,6 @@ path = KHR; sourceTree = ""; }; - 9C7A3A7A18C806E00070BB5F /* nacl */ = { - isa = PBXGroup; - children = ( - 9C7A3A7B18C806E00070BB5F /* nacl.cpp */, - ); - path = nacl; - sourceTree = ""; - }; - 9C7A3A7D18C806E00070BB5F /* oslib */ = { - isa = PBXGroup; - children = ( - 9C7A3A7E18C806E00070BB5F /* alsa_audiostream.cpp */, - 9C7A3A7F18C806E00070BB5F /* audiostream.cpp */, - 9C7A3A8018C806E00070BB5F /* audiostream_rif.h */, - 9C7A3A8118C806E00070BB5F /* ds_audiostream.cpp */, - 9C7A3A8218C806E00070BB5F /* oslib.h */, - ); - path = oslib; - sourceTree = ""; - }; 9C7A3A8318C806E00070BB5F /* profiler */ = { isa = PBXGroup; children = ( @@ -1279,9 +1357,7 @@ 9C7A3A8A18C806E00070BB5F /* rend */ = { isa = PBXGroup; children = ( - 9C7A3A8B18C806E00070BB5F /* d3d11 */, 9C7A3A8D18C806E00070BB5F /* gles */, - 9C7A3A9218C806E00070BB5F /* norend */, 9C7A3A9418C806E00070BB5F /* rend.h */, 9C7A3A9518C806E00070BB5F /* TexCache.cpp */, 9C7A3A9618C806E00070BB5F /* TexCache.h */, @@ -1289,14 +1365,6 @@ path = rend; sourceTree = ""; }; - 9C7A3A8B18C806E00070BB5F /* d3d11 */ = { - isa = PBXGroup; - children = ( - 9C7A3A8C18C806E00070BB5F /* d3d11.cpp */, - ); - path = d3d11; - sourceTree = ""; - }; 9C7A3A8D18C806E00070BB5F /* gles */ = { isa = PBXGroup; children = ( @@ -1308,22 +1376,6 @@ path = gles; sourceTree = ""; }; - 9C7A3A9218C806E00070BB5F /* norend */ = { - isa = PBXGroup; - children = ( - 9C7A3A9318C806E00070BB5F /* norend.cpp */, - ); - path = norend; - sourceTree = ""; - }; - 9C7A3A9718C806E00070BB5F /* sdl */ = { - isa = PBXGroup; - children = ( - 9C7A3A9818C806E00070BB5F /* main.cpp */, - ); - path = sdl; - sourceTree = ""; - }; /* End PBXGroup section */ /* Begin PBXNativeTarget section */ @@ -1352,7 +1404,12 @@ isa = PBXProject; attributes = { LastUpgradeCheck = 0500; - ORGANIZATIONNAME = "Karen Tsai (angelXwind)"; + ORGANIZATIONNAME = reicast; + TargetAttributes = { + 87078A8218A47FE90034C7A0 = { + DevelopmentTeam = QRT73U549N; + }; + }; }; buildConfigurationList = 87078A7E18A47FE90034C7A0 /* Build configuration list for PBXProject "emulator" */; compatibilityVersion = "Xcode 3.2"; @@ -1379,6 +1436,7 @@ files = ( 9C7A3C1818C851C50070BB5F /* LTrigger@2x.png in Resources */, 9C7A3C1318C851C50070BB5F /* JoystickBackground.png in Resources */, + 8703BC3C1A44B8DA00E7E939 /* Icon-72@2x.png in Resources */, 9C7A393318C804A80070BB5F /* reicast.entitlements in Resources */, 9C7A3C0018C851C50070BB5F /* 210-octocat@2x.png in Resources */, 9C7A3C1718C851C50070BB5F /* LTrigger.png in Resources */, @@ -1390,11 +1448,13 @@ 9C7A3C2118C851C50070BB5F /* RTrigger.png in Resources */, 9C7A3C1C18C851C50070BB5F /* menuicon@2x.png in Resources */, 9C7A3C0118C851C50070BB5F /* 210-twitterbird.png in Resources */, + 8703BC3D1A44B8DA00E7E939 /* Icon.png in Resources */, 9C7A3C0D18C851C50070BB5F /* DPad.png in Resources */, 9C7A3C1518C851C50070BB5F /* JoystickButton.png in Resources */, + 8703BC3E1A44B8DA00E7E939 /* Icon@2x.png in Resources */, 9C7A3BFF18C851C50070BB5F /* 210-octocat.png in Resources */, + 8703BC3B1A44B8DA00E7E939 /* Icon-72.png in Resources */, 9C7A3C1618C851C50070BB5F /* JoystickButton@2x.png in Resources */, - 87078AAA18A47FE90034C7A0 /* Images.xcassets in Resources */, 9C7A3C1418C851C50070BB5F /* JoystickBackground@2x.png in Resources */, 9C7A3C1918C851C50070BB5F /* menuback.png in Resources */, 9C7A3BC418C84EA10070BB5F /* MainStoryboard.storyboard in Resources */, @@ -1454,6 +1514,7 @@ 9C7A3B1018C806E00070BB5F /* maple_devs.cpp in Sources */, 9C7A3AE718C806E00070BB5F /* zip_source_function.c in Sources */, 9C7A3AE918C806E00070BB5F /* zip_stat.c in Sources */, + 849C0D661B072CF8008BAAA4 /* reios.cpp in Sources */, 9C7A3ABF18C806E00070BB5F /* zip_delete.c in Sources */, 9C7A3B0018C806E00070BB5F /* aica.cpp in Sources */, 9C7A3B3318C806E00070BB5F /* sh4_rom.cpp in Sources */, @@ -1472,6 +1533,7 @@ 9C7A3B2418C806E00070BB5F /* bsc.cpp in Sources */, 9C7A3AD318C806E00070BB5F /* zip_free.c in Sources */, 9C7A3AB918C806E00070BB5F /* pngwtran.c in Sources */, + 8497BCCA1A41BFBA00EFB9ED /* audiostream.cpp in Sources */, 9C7A3B4918C806E00070BB5F /* gles.cpp in Sources */, 9C7A3ADD18C806E00070BB5F /* zip_rename.c in Sources */, 9C7A3ADB18C806E00070BB5F /* zip_new.c in Sources */, @@ -1480,7 +1542,9 @@ 9C7A3B1418C806E00070BB5F /* drkPvr.cpp in Sources */, 9C7A3AB318C806E00070BB5F /* pngrtran.c in Sources */, 9C7A3AEC18C806E00070BB5F /* zip_strerror.c in Sources */, + 849C0D6F1B072D14008BAAA4 /* reios_elf.cpp in Sources */, 9C7A3AB718C806E00070BB5F /* pngwio.c in Sources */, + 8497BCCB1A41BFBA00EFB9ED /* ds_audiostream.cpp in Sources */, 9C7A3B2D18C806E00070BB5F /* ubc.cpp in Sources */, 9C7A3B2618C806E00070BB5F /* cpg.cpp in Sources */, 9C7A3B1A18C806E00070BB5F /* ta.cpp in Sources */, @@ -1498,8 +1562,8 @@ 9C7A3AF318C806E00070BB5F /* crc32.c in Sources */, 9C7A3B5F18C81D090070BB5F /* BrowserTableViewController.m in Sources */, 9C7D581019301E140004EA2C /* CloudVMUViewController.m in Sources */, + 8497BCC01A41A0E900EFB9ED /* nixprof.cpp in Sources */, 9C7A3AE118C806E00070BB5F /* zip_set_file_comment.c in Sources */, - 9C7A3B4118C806E00070BB5F /* audiostream.cpp in Sources */, 9C7A3AB118C806E00070BB5F /* pngread.c in Sources */, 9C7A3AAC18C806E00070BB5F /* png.c in Sources */, 9C7A3AC718C806E00070BB5F /* zip_error_get_sys_type.c in Sources */, @@ -1513,8 +1577,10 @@ 9C7A3B1218C806E00070BB5F /* maple_if.cpp in Sources */, 9C7A3AC818C806E00070BB5F /* zip_error_strerror.c in Sources */, 9C7A3AF518C806E00070BB5F /* infback.c in Sources */, + 8497BCCF1A41BFD800EFB9ED /* coreio.cpp in Sources */, 9C7A3B0E18C806E00070BB5F /* sb_mem.cpp in Sources */, 9C7A3B5C18C81BC80070BB5F /* SideDrawerViewController.m in Sources */, + 8497BCC21A41B02000EFB9ED /* ios_main.mm in Sources */, 9C7A3B2C18C806E00070BB5F /* tmu.cpp in Sources */, 9C7A3B4C18C806E00070BB5F /* TexCache.cpp in Sources */, 9C7A3B1618C806E00070BB5F /* pvr_regs.cpp in Sources */, @@ -1527,6 +1593,7 @@ 9C7A3B2018C806E00070BB5F /* shil.cpp in Sources */, 9C7A3B2518C806E00070BB5F /* ccn.cpp in Sources */, 9C7A3B4618C806E00070BB5F /* ngen_arm.S in Sources */, + 849C0D621B072C07008BAAA4 /* context.cpp in Sources */, 9C7A3AD618C806E00070BB5F /* zip_get_file_comment.c in Sources */, 9C7A3AEA18C806E00070BB5F /* zip_stat_index.c in Sources */, 9C7A3ACF18C806E00070BB5F /* zip_filerange_crc.c in Sources */, @@ -1539,7 +1606,7 @@ 9C7A3B1D18C806E00070BB5F /* blockmanager.cpp in Sources */, 9C7A3B2B18C806E00070BB5F /* serial.cpp in Sources */, 9C7A3B4A18C806E00070BB5F /* gltex.cpp in Sources */, - 87078AA818A47FE90034C7A0 /* EmulatorViewController.m in Sources */, + 87078AA818A47FE90034C7A0 /* EmulatorViewController.mm in Sources */, 9C7A3ACD18C806E00070BB5F /* zip_file_get_offset.c in Sources */, 9C7A3B2818C806E00070BB5F /* intc.cpp in Sources */, 9C7A3B3A18C806E00070BB5F /* ioctl.cpp in Sources */, @@ -1556,17 +1623,19 @@ 9C7A3B1518C806E00070BB5F /* pvr_mem.cpp in Sources */, 9C7A3B6218C820630070BB5F /* AboutViewController.m in Sources */, 9C7A3AF718C806E00070BB5F /* inflate.c in Sources */, + 846293C61A6CE61900262464 /* EmulatorView.mm in Sources */, 9C7A3AC918C806E00070BB5F /* zip_error_to_str.c in Sources */, 9C7A3B0918C806E00070BB5F /* gdrom_response.cpp in Sources */, 9C7A3B2218C806E00070BB5F /* sh4_interpreter.cpp in Sources */, 9C7A3B3818C806E00070BB5F /* gdi.cpp in Sources */, + 849C0D6D1B072D14008BAAA4 /* descrambl.cpp in Sources */, 9C7A3AF018C806E00070BB5F /* zip_unchange_data.c in Sources */, 9C7A3AB218C806E00070BB5F /* pngrio.c in Sources */, 9C7A3AC118C806E00070BB5F /* zip_entry_free.c in Sources */, - 9C7A3B4018C806E00070BB5F /* alsa_audiostream.cpp in Sources */, - 9C7A3B3E18C806E00070BB5F /* nacl.cpp in Sources */, 9C7A3AE518C806E00070BB5F /* zip_source_filep.c in Sources */, 9C7A3B0318C806E00070BB5F /* dsp.cpp in Sources */, + 8497BCC91A41BFBA00EFB9ED /* alsa_audiostream.cpp in Sources */, + 8497BCBF1A41A0E900EFB9ED /* common.cpp in Sources */, 9C7A3B0B18C806E00070BB5F /* holly_intc.cpp in Sources */, 87078A9718A47FE90034C7A0 /* main.m in Sources */, 9C7A3AC418C806E00070BB5F /* zip_error.c in Sources */, @@ -1582,18 +1651,16 @@ 9C7A3AF618C806E00070BB5F /* inffast.c in Sources */, 9C7A3B1318C806E00070BB5F /* _vmem.cpp in Sources */, 9C7A3B1118C806E00070BB5F /* maple_helper.cpp in Sources */, + 849C0D6E1B072D14008BAAA4 /* gdrom_hle.cpp in Sources */, 9C7A3AD018C806E00070BB5F /* zip_fopen.c in Sources */, - 9C7A3B4D18C806E00070BB5F /* main.cpp in Sources */, 9C7A3B1718C806E00070BB5F /* pvr_sb_regs.cpp in Sources */, 9C7A3B3918C806E00070BB5F /* ImgReader.cpp in Sources */, 9C7A3ACC18C806E00070BB5F /* zip_file_error_get.c in Sources */, 9C7A3B3F18C806E00070BB5F /* nullDC.cpp in Sources */, - 9C7A3B4218C806E00070BB5F /* ds_audiostream.cpp in Sources */, 9C7A3B0618C806E00070BB5F /* arm_mem.cpp in Sources */, 9C7A3AAF18C806E00070BB5F /* pngmem.c in Sources */, 9C7A3AAB18C806E00070BB5F /* elf64.cpp in Sources */, 9C7A3ADE18C806E00070BB5F /* zip_replace.c in Sources */, - 9C7A3B4B18C806E00070BB5F /* norend.cpp in Sources */, 9C7A3B0C18C806E00070BB5F /* sb.cpp in Sources */, 9C7A3B0118C806E00070BB5F /* aica_if.cpp in Sources */, 9C7A3ADF18C806E00070BB5F /* zip_set_archive_comment.c in Sources */, @@ -1602,7 +1669,6 @@ 9C7A3AC318C806E00070BB5F /* zip_err_str.c in Sources */, 9C7A3B4818C806E00070BB5F /* gldraw.cpp in Sources */, 9C7A3AE618C806E00070BB5F /* zip_source_free.c in Sources */, - 9C7A3B4718C806E00070BB5F /* d3d11.cpp in Sources */, 9C7A3AAE18C806E00070BB5F /* pngget.c in Sources */, 9C7A3AB018C806E00070BB5F /* pngpread.c in Sources */, 9C7A3AF118C806E00070BB5F /* adler32.c in Sources */, @@ -1651,7 +1717,7 @@ IPHONEOS_DEPLOYMENT_TARGET = 5.0; ONLY_ACTIVE_ARCH = YES; SDKROOT = iphoneos; - TARGETED_DEVICE_FAMILY = "1,2"; + TARGETED_DEVICE_FAMILY = 2; }; name = Debug; }; @@ -1685,7 +1751,7 @@ GCC_WARN_UNUSED_VARIABLE = YES; IPHONEOS_DEPLOYMENT_TARGET = 5.0; SDKROOT = iphoneos; - TARGETED_DEVICE_FAMILY = "1,2"; + TARGETED_DEVICE_FAMILY = 2; VALIDATE_PRODUCT = YES; }; name = Release; @@ -1693,16 +1759,17 @@ 87078AC118A47FE90034C7A0 /* Debug */ = { isa = XCBuildConfiguration; buildSettings = { - ARCHS = ( - armv7s, - armv7, - ); - ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; - ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage; - CODE_SIGN_ENTITLEMENTS = emulator/reicast.entitlements; - "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = ""; + ARCHS = "$(ARCHS_STANDARD)"; + CODE_SIGN_IDENTITY = "iPhone Developer"; + "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; GCC_PRECOMPILE_PREFIX_HEADER = YES; GCC_PREFIX_HEADER = "emulator/emulator-Prefix.pch"; + GCC_PREPROCESSOR_DEFINITIONS = ( + "GLES=1", + "DEBUG=1", + "TARGET_IPHONE=1", + "$(inherited)", + ); HEADER_SEARCH_PATHS = ( "$(inherited)", /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include, @@ -1711,8 +1778,12 @@ ../../core/khronos/, ); INFOPLIST_FILE = "emulator/emulator-Info.plist"; + IPHONEOS_DEPLOYMENT_TARGET = 8.0; ONLY_ACTIVE_ARCH = NO; + OTHER_CFLAGS = "-mno-thumb"; PRODUCT_NAME = "$(TARGET_NAME)"; + PROVISIONING_PROFILE = ""; + TARGETED_DEVICE_FAMILY = "1,2"; VALID_ARCHS = "armv7 armv7s"; WRAPPER_EXTENSION = app; }; @@ -1721,16 +1792,15 @@ 87078AC218A47FE90034C7A0 /* Release */ = { isa = XCBuildConfiguration; buildSettings = { - ARCHS = ( - armv7s, - armv7, - ); - ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; - ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME = LaunchImage; - CODE_SIGN_ENTITLEMENTS = emulator/reicast.entitlements; - "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = ""; + ARCHS = "$(ARCHS_STANDARD)"; + CODE_SIGN_IDENTITY = "iPhone Developer"; + "CODE_SIGN_IDENTITY[sdk=iphoneos*]" = "iPhone Developer"; GCC_PRECOMPILE_PREFIX_HEADER = YES; GCC_PREFIX_HEADER = "emulator/emulator-Prefix.pch"; + GCC_PREPROCESSOR_DEFINITIONS = ( + "GLES=1", + "TARGET_IPHONE=1", + ); HEADER_SEARCH_PATHS = ( "$(inherited)", /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include, @@ -1739,8 +1809,12 @@ ../../core/khronos/, ); INFOPLIST_FILE = "emulator/emulator-Info.plist"; + IPHONEOS_DEPLOYMENT_TARGET = 8.0; ONLY_ACTIVE_ARCH = NO; + OTHER_CFLAGS = "-mno-thumb"; PRODUCT_NAME = "$(TARGET_NAME)"; + PROVISIONING_PROFILE = ""; + TARGETED_DEVICE_FAMILY = "1,2"; VALID_ARCHS = "armv7 armv7s"; WRAPPER_EXTENSION = app; }; diff --git a/shell/ios/emulator/EmulatorView.h b/shell/ios/emulator/EmulatorView.h new file mode 100644 index 000000000..655a02aaf --- /dev/null +++ b/shell/ios/emulator/EmulatorView.h @@ -0,0 +1,13 @@ +// +// EmulatorView.h +// emulator +// +// Created by admin on 1/18/15. +// Copyright (c) 2015 reicast. All rights reserved. +// + +#import + +@interface EmulatorView : GLKView + +@end diff --git a/shell/ios/emulator/EmulatorView.mm b/shell/ios/emulator/EmulatorView.mm new file mode 100644 index 000000000..8909eb56c --- /dev/null +++ b/shell/ios/emulator/EmulatorView.mm @@ -0,0 +1,51 @@ +// +// EmulatorView.m +// emulator +// +// Created by admin on 1/18/15. +// Copyright (c) 2015 reicast. All rights reserved. +// + +#import "EmulatorView.h" + +#include "types.h" + +extern u16 kcode[4]; +extern u32 vks[4]; +extern s8 joyx[4],joyy[4]; +extern u8 rt[4],lt[4]; + +#define key_CONT_A (1 << 2) +#define key_CONT_START (1 << 3) +#define key_CONT_DPAD_LEFT (1 << 6) + +int dpad_or_btn = 0; + +@implementation EmulatorView + +/* +// Only override drawRect: if you perform custom drawing. +// An empty implementation adversely affects performance during animation. +- (void)drawRect:(CGRect)rect { + // Drawing code +} +*/ + +-(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event { + + if (dpad_or_btn &1) + kcode[0] &= ~(key_CONT_START|key_CONT_A); + else + kcode[0] &= ~(key_CONT_DPAD_LEFT); +} + +-(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event { + + if (dpad_or_btn &1) + kcode[0] |= (key_CONT_START|key_CONT_A); + else + kcode[0] |= (key_CONT_DPAD_LEFT); + + dpad_or_btn++; +} +@end diff --git a/shell/ios/emulator/EmulatorViewController.m b/shell/ios/emulator/EmulatorViewController.m deleted file mode 100644 index 192096a78..000000000 --- a/shell/ios/emulator/EmulatorViewController.m +++ /dev/null @@ -1,378 +0,0 @@ -// -// EmulatorViewController.m -// emulator -// -// Created by Karen Tsai (angelXwind) on 2014/3/5. -// Copyright (c) 2014 Karen Tsai (angelXwind). All rights reserved. -// - -#import "EmulatorViewController.h" - -#define BUFFER_OFFSET(i) ((char *)NULL + (i)) - -// Uniform index. -enum -{ - UNIFORM_MODELVIEWPROJECTION_MATRIX, - UNIFORM_NORMAL_MATRIX, - NUM_UNIFORMS -}; -GLint uniforms[NUM_UNIFORMS]; - -// Attribute index. -enum -{ - ATTRIB_VERTEX, - ATTRIB_NORMAL, - NUM_ATTRIBUTES -}; - -GLfloat gCubeVertexData[216] = -{ - // Data layout for each line below is: - // positionX, positionY, positionZ, normalX, normalY, normalZ, - 0.5f, -0.5f, -0.5f, 1.0f, 0.0f, 0.0f, - 0.5f, 0.5f, -0.5f, 1.0f, 0.0f, 0.0f, - 0.5f, -0.5f, 0.5f, 1.0f, 0.0f, 0.0f, - 0.5f, -0.5f, 0.5f, 1.0f, 0.0f, 0.0f, - 0.5f, 0.5f, -0.5f, 1.0f, 0.0f, 0.0f, - 0.5f, 0.5f, 0.5f, 1.0f, 0.0f, 0.0f, - - 0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f, - -0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f, - 0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f, - 0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f, - -0.5f, 0.5f, -0.5f, 0.0f, 1.0f, 0.0f, - -0.5f, 0.5f, 0.5f, 0.0f, 1.0f, 0.0f, - - -0.5f, 0.5f, -0.5f, -1.0f, 0.0f, 0.0f, - -0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f, - -0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f, - -0.5f, 0.5f, 0.5f, -1.0f, 0.0f, 0.0f, - -0.5f, -0.5f, -0.5f, -1.0f, 0.0f, 0.0f, - -0.5f, -0.5f, 0.5f, -1.0f, 0.0f, 0.0f, - - -0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f, - 0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f, - -0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f, - -0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f, - 0.5f, -0.5f, -0.5f, 0.0f, -1.0f, 0.0f, - 0.5f, -0.5f, 0.5f, 0.0f, -1.0f, 0.0f, - - 0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f, - -0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f, - 0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f, - 0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f, - -0.5f, 0.5f, 0.5f, 0.0f, 0.0f, 1.0f, - -0.5f, -0.5f, 0.5f, 0.0f, 0.0f, 1.0f, - - 0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f, - -0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f, - 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f, - 0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f, - -0.5f, -0.5f, -0.5f, 0.0f, 0.0f, -1.0f, - -0.5f, 0.5f, -0.5f, 0.0f, 0.0f, -1.0f -}; - -@interface ViewController () { - GLuint _program; - - GLKMatrix4 _modelViewProjectionMatrix; - GLKMatrix3 _normalMatrix; - float _rotation; - - GLuint _vertexArray; - GLuint _vertexBuffer; -} -@property (strong, nonatomic) EAGLContext *context; -@property (strong, nonatomic) GLKBaseEffect *effect; - -- (void)setupGL; -- (void)tearDownGL; - -- (BOOL)loadShaders; -- (BOOL)compileShader:(GLuint *)shader type:(GLenum)type file:(NSString *)file; -- (BOOL)linkProgram:(GLuint)prog; -- (BOOL)validateProgram:(GLuint)prog; -@end - -@implementation ViewController - -- (void)viewDidLoad -{ - [super viewDidLoad]; - - self.context = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2]; - - if (!self.context) { - NSLog(@"Failed to create ES context"); - } - - GLKView *view = (GLKView *)self.view; - view.context = self.context; - view.drawableDepthFormat = GLKViewDrawableDepthFormat24; - - [self setupGL]; -} - -- (void)dealloc -{ - [self tearDownGL]; - - if ([EAGLContext currentContext] == self.context) { - [EAGLContext setCurrentContext:nil]; - } -} - -- (void)didReceiveMemoryWarning -{ - [super didReceiveMemoryWarning]; - - if ([self isViewLoaded] && ([[self view] window] == nil)) { - self.view = nil; - - [self tearDownGL]; - - if ([EAGLContext currentContext] == self.context) { - [EAGLContext setCurrentContext:nil]; - } - self.context = nil; - } - - // Dispose of any resources that can be recreated. -} - -- (void)setupGL -{ - [EAGLContext setCurrentContext:self.context]; - - [self loadShaders]; - - self.effect = [[GLKBaseEffect alloc] init]; - self.effect.light0.enabled = GL_TRUE; - self.effect.light0.diffuseColor = GLKVector4Make(1.0f, 0.4f, 0.4f, 1.0f); - - glEnable(GL_DEPTH_TEST); - -} - -- (void)tearDownGL -{ - [EAGLContext setCurrentContext:self.context]; - - glDeleteBuffers(1, &_vertexBuffer); - glDeleteVertexArraysOES(1, &_vertexArray); - - self.effect = nil; - - if (_program) { - glDeleteProgram(_program); - _program = 0; - } -} - -#pragma mark - GLKView and GLKViewController delegate methods - -- (void)update -{ - float aspect = fabsf(self.view.bounds.size.width / self.view.bounds.size.height); - GLKMatrix4 projectionMatrix = GLKMatrix4MakePerspective(GLKMathDegreesToRadians(65.0f), aspect, 0.1f, 100.0f); - - self.effect.transform.projectionMatrix = projectionMatrix; - - GLKMatrix4 baseModelViewMatrix = GLKMatrix4MakeTranslation(0.0f, 0.0f, -4.0f); - baseModelViewMatrix = GLKMatrix4Rotate(baseModelViewMatrix, _rotation, 0.0f, 1.0f, 0.0f); - - // Compute the model view matrix for the object rendered with GLKit - GLKMatrix4 modelViewMatrix = GLKMatrix4MakeTranslation(0.0f, 0.0f, -1.5f); - modelViewMatrix = GLKMatrix4Rotate(modelViewMatrix, _rotation, 1.0f, 1.0f, 1.0f); - modelViewMatrix = GLKMatrix4Multiply(baseModelViewMatrix, modelViewMatrix); - - self.effect.transform.modelviewMatrix = modelViewMatrix; - - // Compute the model view matrix for the object rendered with ES2 - modelViewMatrix = GLKMatrix4MakeTranslation(0.0f, 0.0f, 1.5f); - modelViewMatrix = GLKMatrix4Rotate(modelViewMatrix, _rotation, 1.0f, 1.0f, 1.0f); - modelViewMatrix = GLKMatrix4Multiply(baseModelViewMatrix, modelViewMatrix); - - _normalMatrix = GLKMatrix3InvertAndTranspose(GLKMatrix4GetMatrix3(modelViewMatrix), NULL); - - _modelViewProjectionMatrix = GLKMatrix4Multiply(projectionMatrix, modelViewMatrix); - - _rotation += self.timeSinceLastUpdate * 0.5f; -} - -- (void)glkView:(GLKView *)view drawInRect:(CGRect)rect -{ - glClearColor(0.65f, 0.65f, 0.65f, 1.0f); - glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - - glBindVertexArrayOES(_vertexArray); - - // Render the object with GLKit - [self.effect prepareToDraw]; - - glDrawArrays(GL_TRIANGLES, 0, 36); - - // Render the object again with ES2 - glUseProgram(_program); - - glUniformMatrix4fv(uniforms[UNIFORM_MODELVIEWPROJECTION_MATRIX], 1, 0, _modelViewProjectionMatrix.m); - glUniformMatrix3fv(uniforms[UNIFORM_NORMAL_MATRIX], 1, 0, _normalMatrix.m); - - glDrawArrays(GL_TRIANGLES, 0, 36); -} - -#pragma mark - OpenGL ES 2 shader compilation - -- (BOOL)loadShaders -{ - GLuint vertShader, fragShader; - NSString *vertShaderPathname, *fragShaderPathname; - - // Create shader program. - _program = glCreateProgram(); - - // Create and compile vertex shader. - vertShaderPathname = [[NSBundle mainBundle] pathForResource:@"Shader" ofType:@"vsh"]; - if (![self compileShader:&vertShader type:GL_VERTEX_SHADER file:vertShaderPathname]) { - NSLog(@"Failed to compile vertex shader"); - return NO; - } - - // Create and compile fragment shader. - fragShaderPathname = [[NSBundle mainBundle] pathForResource:@"Shader" ofType:@"fsh"]; - if (![self compileShader:&fragShader type:GL_FRAGMENT_SHADER file:fragShaderPathname]) { - NSLog(@"Failed to compile fragment shader"); - return NO; - } - - // Attach vertex shader to program. - glAttachShader(_program, vertShader); - - // Attach fragment shader to program. - glAttachShader(_program, fragShader); - - // Bind attribute locations. - // This needs to be done prior to linking. - glBindAttribLocation(_program, GLKVertexAttribPosition, "position"); - glBindAttribLocation(_program, GLKVertexAttribNormal, "normal"); - - // Link program. - if (![self linkProgram:_program]) { - NSLog(@"Failed to link program: %d", _program); - - if (vertShader) { - glDeleteShader(vertShader); - vertShader = 0; - } - if (fragShader) { - glDeleteShader(fragShader); - fragShader = 0; - } - if (_program) { - glDeleteProgram(_program); - _program = 0; - } - - return NO; - } - - // Get uniform locations. - uniforms[UNIFORM_MODELVIEWPROJECTION_MATRIX] = glGetUniformLocation(_program, "modelViewProjectionMatrix"); - uniforms[UNIFORM_NORMAL_MATRIX] = glGetUniformLocation(_program, "normalMatrix"); - - // Release vertex and fragment shaders. - if (vertShader) { - glDetachShader(_program, vertShader); - glDeleteShader(vertShader); - } - if (fragShader) { - glDetachShader(_program, fragShader); - glDeleteShader(fragShader); - } - - return YES; -} - -- (BOOL)compileShader:(GLuint *)shader type:(GLenum)type file:(NSString *)file -{ - GLint status; - const GLchar *source; - - source = (GLchar *)[[NSString stringWithContentsOfFile:file encoding:NSUTF8StringEncoding error:nil] UTF8String]; - if (!source) { - NSLog(@"Failed to load vertex shader"); - return NO; - } - - *shader = glCreateShader(type); - glShaderSource(*shader, 1, &source, NULL); - glCompileShader(*shader); - -#if defined(DEBUG) - GLint logLength; - glGetShaderiv(*shader, GL_INFO_LOG_LENGTH, &logLength); - if (logLength > 0) { - GLchar *log = (GLchar *)malloc(logLength); - glGetShaderInfoLog(*shader, logLength, &logLength, log); - NSLog(@"Shader compile log:\n%s", log); - free(log); - } -#endif - - glGetShaderiv(*shader, GL_COMPILE_STATUS, &status); - if (status == 0) { - glDeleteShader(*shader); - return NO; - } - - return YES; -} - -- (BOOL)linkProgram:(GLuint)prog -{ - GLint status; - glLinkProgram(prog); - -#if defined(DEBUG) - GLint logLength; - glGetProgramiv(prog, GL_INFO_LOG_LENGTH, &logLength); - if (logLength > 0) { - GLchar *log = (GLchar *)malloc(logLength); - glGetProgramInfoLog(prog, logLength, &logLength, log); - NSLog(@"Program link log:\n%s", log); - free(log); - } -#endif - - glGetProgramiv(prog, GL_LINK_STATUS, &status); - if (status == 0) { - return NO; - } - - return YES; -} - -- (BOOL)validateProgram:(GLuint)prog -{ - GLint logLength, status; - - glValidateProgram(prog); - glGetProgramiv(prog, GL_INFO_LOG_LENGTH, &logLength); - if (logLength > 0) { - GLchar *log = (GLchar *)malloc(logLength); - glGetProgramInfoLog(prog, logLength, &logLength, log); - NSLog(@"Program validate log:\n%s", log); - free(log); - } - - glGetProgramiv(prog, GL_VALIDATE_STATUS, &status); - if (status == 0) { - return NO; - } - - return YES; -} - -@end diff --git a/shell/ios/emulator/EmulatorViewController.mm b/shell/ios/emulator/EmulatorViewController.mm new file mode 100644 index 000000000..2aa2404c6 --- /dev/null +++ b/shell/ios/emulator/EmulatorViewController.mm @@ -0,0 +1,138 @@ +// +// EmulatorViewController.m +// emulator +// +// Created by Karen Tsai (angelXwind) on 2014/3/5. +// Copyright (c) 2014 Karen Tsai (angelXwind). All rights reserved. +// + +#import "EmulatorViewController.h" +#import + +#include "types.h" +#include "profiler/profiler.h" +#include "cfg/cfg.h" +#include "rend/TexCache.h" +#include "hw/maple/maple_devs.h" +#include "hw/maple/maple_if.h" + +@interface ViewController () { +} + +@property (strong, nonatomic) EAGLContext *context; +@property (strong, nonatomic) GLKBaseEffect *effect; + +- (void)setupGL; +- (void)tearDownGL; +- (void)emuThread; + +@end + +//who has time for headers +extern int screen_width,screen_height; +bool rend_single_frame(); +bool gles_init(); +extern "C" int reicast_main(int argc, char* argv[]); + + +@implementation ViewController + +-(void)emuThread +{ + install_prof_handler(1); + + + //This looks like the right place, rite? + char text[2]=""; + + char* prms[2]; + prms[0]=text; + + reicast_main(1, prms); +} + +- (void)viewDidLoad +{ + [super viewDidLoad]; + + self.context = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES2]; + + if (!self.context) { + NSLog(@"Failed to create ES context"); + } + + GLKView *view = (GLKView *)self.view; + view.context = self.context; + view.drawableDepthFormat = GLKViewDrawableDepthFormat24; + + [self setupGL]; + + if (!gles_init()) + die("OPENGL FAILED"); + + NSThread* myThread = [[NSThread alloc] initWithTarget:self + selector:@selector(emuThread) + object:nil]; + [myThread start]; // Actually create the thread +} + +- (void)dealloc +{ + [self tearDownGL]; + + if ([EAGLContext currentContext] == self.context) { + [EAGLContext setCurrentContext:nil]; + } +} + +- (void)didReceiveMemoryWarning +{ + [super didReceiveMemoryWarning]; + + if ([self isViewLoaded] && ([[self view] window] == nil)) { + self.view = nil; + + [self tearDownGL]; + + if ([EAGLContext currentContext] == self.context) { + [EAGLContext setCurrentContext:nil]; + } + self.context = nil; + } + + // Dispose of any resources that can be recreated. +} + +- (void)setupGL +{ + [EAGLContext setCurrentContext:self.context]; + +} + +- (void)tearDownGL +{ + [EAGLContext setCurrentContext:self.context]; + +} + +#pragma mark - GLKView and GLKViewController delegate methods + +- (void)update +{ + +} + + +- (void)glkView:(GLKView *)view drawInRect:(CGRect)rect +{ + screen_width = view.drawableWidth; + screen_height = view.drawableHeight; + + glClearColor(0.65f, 0.65f, 0.65f, 1.0f); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + + while(!rend_single_frame()) ; +} + + +@end diff --git a/shell/ios/emulator/MainStoryboard.storyboard b/shell/ios/emulator/MainStoryboard.storyboard index db60bd89a..276a2a495 100644 --- a/shell/ios/emulator/MainStoryboard.storyboard +++ b/shell/ios/emulator/MainStoryboard.storyboard @@ -1,557 +1,21 @@ - + - - + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + - - + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -560,848 +24,13 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + - - - - - - - - - - - - - + diff --git a/shell/ios/emulator/assets/Icon-72.png b/shell/ios/emulator/assets/Icon-72.png new file mode 100644 index 000000000..647ca0bac Binary files /dev/null and b/shell/ios/emulator/assets/Icon-72.png differ diff --git a/shell/ios/emulator/assets/Icon-72@2x.png b/shell/ios/emulator/assets/Icon-72@2x.png new file mode 100644 index 000000000..0d528bcd5 Binary files /dev/null and b/shell/ios/emulator/assets/Icon-72@2x.png differ diff --git a/shell/ios/emulator/assets/Icon.png b/shell/ios/emulator/assets/Icon.png new file mode 100644 index 000000000..561092b98 Binary files /dev/null and b/shell/ios/emulator/assets/Icon.png differ diff --git a/shell/ios/emulator/assets/Icon@2x.png b/shell/ios/emulator/assets/Icon@2x.png new file mode 100644 index 000000000..b2c76f7b9 Binary files /dev/null and b/shell/ios/emulator/assets/Icon@2x.png differ diff --git a/shell/ios/emulator/emulator-Info.plist b/shell/ios/emulator/emulator-Info.plist index a57996257..f0895e952 100644 --- a/shell/ios/emulator/emulator-Info.plist +++ b/shell/ios/emulator/emulator-Info.plist @@ -5,11 +5,18 @@ CFBundleDevelopmentRegion en CFBundleDisplayName - ${PRODUCT_NAME} + Reicast CFBundleExecutable ${EXECUTABLE_NAME} + CFBundleIconFiles + + emulator/assets/Icon-72.png + emulator/assets/Icon-72@2x.png + emulator/assets/Icon.png + emulator/assets/Icon@2x.png + CFBundleIdentifier - com.reicast.${PRODUCT_NAME:rfc1034identifier} + com.reicast.$(PRODUCT_NAME:rfc1034identifier) CFBundleInfoDictionaryVersion 6.0 CFBundleName @@ -24,10 +31,16 @@ 1.0 LSRequiresIPhoneOS + NSHighResolutionCapable + + UIFileSharingEnabled + + UILaunchStoryboardName + MainStoryboard UIMainStoryboardFile MainStoryboard UIMainStoryboardFile~ipad - Main_iPad + MainStoryboard UIPrerenderedIcon UIRequiredDeviceCapabilities @@ -35,13 +48,13 @@ armv7 UIStatusBarHidden - + UISupportedInterfaceOrientations - UIInterfaceOrientationPortrait UIInterfaceOrientationLandscapeLeft UIInterfaceOrientationLandscapeRight UIInterfaceOrientationPortraitUpsideDown + UIInterfaceOrientationPortrait UISupportedInterfaceOrientations~ipad diff --git a/shell/ios/emulator/ios_main.mm b/shell/ios/emulator/ios_main.mm new file mode 100644 index 000000000..42c151887 --- /dev/null +++ b/shell/ios/emulator/ios_main.mm @@ -0,0 +1,116 @@ +// +// ios_main.m +// emulator +// +// Created by admin on 12/17/14. +// Copyright (c) 2014 Karen Tsai (angelXwind). All rights reserved. +// + +#import + +#include +#include +#include +//#include +#include +#include +#include +#include +#include +#include +#include +#include "hw/sh4/dyna/blockmanager.h" +#include + + +int msgboxf(const wchar* text,unsigned int type,...) +{ + va_list args; + + wchar temp[2048]; + va_start(args, type); + vsprintf(temp, text, args); + va_end(args); + + //printf(NULL,temp,VER_SHORTNAME,type | MB_TASKMODAL); + puts(temp); + return 0; +} + +void common_linux_setup(); +int dc_init(int argc,wchar* argv[]); +void dc_run(); + +u16 kcode[4]; +u32 vks[4]; +s8 joyx[4],joyy[4]; +u8 rt[4],lt[4]; + +extern "C" int reicast_main(int argc, wchar* argv[]) +{ + //if (argc==2) + //ndcid=atoi(argv[1]); + + string homedir = [ [[[[NSFileManager defaultManager] URLsForDirectory:NSDocumentDirectory inDomains:NSUserDomainMask] objectAtIndex:0] path] UTF8String]; + SetHomeDir(homedir); + + freopen( (homedir + "/log.txt").c_str(), "wb", stdout); + + printf("Home dir is: %s\n",GetPath("/").c_str()); + + common_linux_setup(); + + settings.profile.run_counts=0; + + dc_init(argc,argv); + + dc_run(); + + return 0; +} + +void os_DoEvents() { + +} + + +u32 os_Push(void*, u32, bool) { + return 1; +} + +void os_SetWindowText(const char* t) { + puts(t); +} + +void os_CreateWindow() { + +} + +void UpdateInputState(u32 port) { + +} + +void get_mic_data(u8* ) { + +} + +void* libPvr_GetRenderTarget() { + return 0; +} + +void* libPvr_GetRenderSurface() { + return 0; + +} + +bool gl_init(void*, void*) { + return true; +} + +void gl_term() { + +} + +void gl_swap() { + +} \ No newline at end of file diff --git a/shell/ios/emulator/reicast.entitlements b/shell/ios/emulator/reicast.entitlements index 42cfb9cdc..0c67376eb 100644 --- a/shell/ios/emulator/reicast.entitlements +++ b/shell/ios/emulator/reicast.entitlements @@ -1,8 +1,5 @@ - - get-task-allow - - + diff --git a/shell/lin86/Makefile b/shell/lin86/Makefile index 8913396f9..7d2e02384 100644 --- a/shell/lin86/Makefile +++ b/shell/lin86/Makefile @@ -2,7 +2,8 @@ LOCAL_PATH := $(call my-dir) FOR_LINUX :=1 NOT_ARM := 1 -NO_REC := 1 +X86_REC := 1 +#NO_REC := 1 #NO_REND := 1 WEBUI :=1 @@ -20,23 +21,25 @@ LD=${CC} MFLAGS := -m32 #-marm -march=armv7-a -mtune=cortex-a9 -mfpu=neon -mfloat-abi=softfp -funroll-loops -ASFLAGS := -m32 +ASFLAGS := -32 #-march=armv7-a -mfpu=neon -mfloat-abi=softfp LDFLAGS := -m32 -g -Wl,-Map,$(notdir $@).map,--gc-sections -Wl,-O3 -Wl,--sort-common SOURCES := cfg/ hw/arm7/ hw/aica/ hw/asic/ hw/ hw/gdrom/ hw/maple/ \ hw/mem/ hw/pvr/ hw/sh4/ hw/sh4/rec_v2/ plugins/ profiler/ serial_ipc/ \ - hw/extdev/ hw/arm/ imgread/ linux/ linux-dist/ ./ rec-ARM/ deps/zlib/ deps/chdr/ deps/crypto/ arm_emitter/ + hw/extdev/ hw/arm/ imgread/ linux/ linux-dist/ ./ rec-x86/ deps/zlib/ deps/chdr/ deps/crypto/ arm_emitter/ + + +CFLAGS := -m32 -g -O3 -D RELEASE -c -D TARGET_LINUX_x86 -D USES_HOMEDIR -D HOST_NO_AREC #-D NO_REND +CFLAGS += -D SUPPORT_X11 +CFLAGS += -frename-registers -fno-strict-aliasing -fsingle-precision-constant +CFLAGS += -ffast-math -ftree-vectorize -CXXFLAGS := -m32 -g -O3 -D RELEASE -c -D TARGET_LINUX_x86 -D USES_HOMEDIR -D HOST_NO_REC #-D NO_REND -CXXFLAGS += -frename-registers -fno-strict-aliasing -fsingle-precision-constant -CXXFLAGS += -ffast-math -ftree-vectorize #-fprefetch-loop-arrays #-std=c++0x - -CXXFLAGS += $(CFLAGS) $(MFLAGS) -fno-exceptions -fno-rtti +CXXFLAGS += $(CFLAGS) $(MFLAGS) -fno-exceptions -fno-rtti -fpermissive CXXFLAGS += -D SUPPORT_X11 # use this to do GLES on x11 (also, update the libs) @@ -44,19 +47,19 @@ CXXFLAGS += -D SUPPORT_X11 ifdef PGO_MAKE - CXXFLAGS += -fprofile-generate -pg + CFLAGS += -fprofile-generate -pg LDFLAGS += -fprofile-generate else - CXXFLAGS += -fomit-frame-pointer + CFLAGS += -fomit-frame-pointer endif ifdef PGO_USE - CXXFLAGS += -fprofile-use + CFLAGS += -fprofile-use endif ifdef LTO_TEST - CXXFLAGS += -flto -fwhole-program + CFLAGS += -flto -fwhole-program LDFLAGS +=-flto -fwhole-program endif @@ -68,7 +71,7 @@ LIBS += -lm -lrt LIBS += -ldl -lGL #for desktop gl #use this for GLES #LIBS += -lEGL -lGLESv2 #-lglslcompiler -lIMGegl -lpvr2d -lsrv_um -LIBS += -lpthread -lasound -lX11 -lXdmcp -lXau +LIBS += -lpthread -lasound -lX11 OBJECTS=$(RZDCY_FILES:.cpp=.build_obj) @@ -85,7 +88,6 @@ PACKAGE_FILES=$(EXECUTABLE_STRIPPED) default.gcw0.desktop icon-32.png all: $(CPPFILES) $(EXECUTABLE) $(EXECUTABLE_STRIPPED) $(EXECUTABLE): $(OBJECTS) - echo $(RZDCY_FILES) $(CXX) $(MFLAGS) $(EXTRAFLAGS) $(LDFLAGS) $(OBJECTS) $(LIBS) -o $@ $(EXECUTABLE_STRIPPED): $(EXECUTABLE) @@ -93,11 +95,11 @@ $(EXECUTABLE_STRIPPED): $(EXECUTABLE) obj/%.build_obj : $(RZDCY_SRC_DIR)/%.cpp mkdir -p $(dir $@) - $(CXX) $(EXTRAFLAGS) $(INCS) $(CXXFLAGS) $< -o $@ + $(CXX) $(EXTRAFLAGS) $(INCS) $(CFLAGS) $(CXXFLAGS) $< -o $@ obj/%.build_obj : $(RZDCY_SRC_DIR)/%.c mkdir -p $(dir $@) - $(CC) $(EXTRAFLAGS) $(INCS) $(CXXFLAGS) $< -o $@ + $(CC) $(EXTRAFLAGS) $(INCS) $(CFLAGS) $< -o $@ obj/%.build_obj : $(RZDCY_SRC_DIR)/%.S mkdir -p $(dir $@) diff --git a/shell/mac86/Makefile b/shell/mac86/Makefile new file mode 100644 index 000000000..aab1ebf97 --- /dev/null +++ b/shell/mac86/Makefile @@ -0,0 +1,102 @@ + +LOCAL_PATH := $(call my-dir) +FOR_LINUX :=1 +NOT_ARM := 1 +NO_REC := 1 +NO_REND := 1 +#WEBUI :=1 + +RZDCY_SRC_DIR = ../../core + +include $(RZDCY_SRC_DIR)/core.mk + + +CXX=${CC_PREFIX}g++ +CC=${CC_PREFIX}gcc +AS=${CC_PREFIX}as +STRIP=${CC_PREFIX}strip + +LD=${CC} + +MFLAGS := -m32 +#-marm -march=armv7-a -mtune=cortex-a9 -mfpu=neon -mfloat-abi=softfp -funroll-loops +ASFLAGS := -m32 +#-march=armv7-a -mfpu=neon -mfloat-abi=softfp + +LDFLAGS := -m32 -g + +SOURCES := cfg/ hw/arm7/ hw/aica/ hw/asic/ hw/ hw/gdrom/ hw/maple/ \ + hw/mem/ hw/pvr/ hw/sh4/ hw/sh4/rec_v2/ plugins/ profiler/ serial_ipc/ \ + hw/extdev/ hw/arm/ imgread/ linux/ linux-dist/ ./ rec-ARM/ deps/zlib/ deps/chdr/ deps/crypto/ arm_emitter/ + + +CXXFLAGS := -m32 -g -O3 -D RELEASE -c -D TARGET_LINUX_x86 -D HOST_NO_REC -D NO_REND +CXXFLAGS += -fno-strict-aliasing +CXXFLAGS += -ffast-math -ftree-vectorize +#-fprefetch-loop-arrays +#-std=c++0x + +CXXFLAGS += $(CFLAGS) $(MFLAGS) -fno-exceptions -fno-rtti +# CXXFLAGS += -D SUPPORT_X11 + + +ifdef PGO_MAKE + CXXFLAGS += -fprofile-generate -pg + LDFLAGS += -fprofile-generate +else + CXXFLAGS += -fomit-frame-pointer +endif + +ifdef PGO_USE + CXXFLAGS += -fprofile-use +endif + + +ifdef LTO_TEST + CXXFLAGS += -flto -fwhole-program + LDFLAGS +=-flto -fwhole-program +endif + +INCS := -I$(RZDCY_SRC_DIR) -I$(RZDCY_SRC_DIR)/deps -I$(RZDCY_SRC_DIR)/khronos -I../linux-deps/include + +LIBS := -L../linux-deps/lib/x86 -L./enta_viv +#LIBS += -lglapi +LIBS += -lm # -lrt -lEGL -lGLESv2 #-lglslcompiler -lIMGegl -lpvr2d -lsrv_um +LIBS += -lpthread # -lX11 -lXdmcp -lXau + + +OBJECTS=$(RZDCY_FILES:.cpp=.build_obj) +OBJECTS:=$(OBJECTS:.c=.build_obj) +OBJECTS:=$(OBJECTS:.S=.build_obj) +OBJECTS:=$(patsubst $(RZDCY_SRC_DIR)/%,obj/%,$(OBJECTS)) + + +EXECUTABLE_STRIPPED=nosym-reicast.elf +EXECUTABLE=reicast.elf + +PACKAGE_FILES=$(EXECUTABLE_STRIPPED) default.gcw0.desktop icon-32.png + +all: $(CPPFILES) $(EXECUTABLE) $(EXECUTABLE_STRIPPED) + +$(EXECUTABLE): $(OBJECTS) + echo $(RZDCY_FILES) + $(CXX) $(MFLAGS) $(EXTRAFLAGS) $(LDFLAGS) $(OBJECTS) $(LIBS) -o $@ + +$(EXECUTABLE_STRIPPED): $(EXECUTABLE) + cp $< $@ && $(STRIP) $@ + +obj/%.build_obj : $(RZDCY_SRC_DIR)/%.cpp + mkdir -p $(dir $@) + $(CXX) $(EXTRAFLAGS) $(INCS) $(CXXFLAGS) $< -o $@ + +obj/%.build_obj : $(RZDCY_SRC_DIR)/%.c + mkdir -p $(dir $@) + $(CC) $(EXTRAFLAGS) $(INCS) $(CXXFLAGS) $< -o $@ + +obj/%.build_obj : $(RZDCY_SRC_DIR)/%.S + mkdir -p $(dir $@) + $(AS) $(ASFLAGS) $(INCS) $< -o $@ + + +clean: + rm $(OBJECTS) $(EXECUTABLE) -f diff --git a/shell/reicast.vcxproj b/shell/reicast.vcxproj index 6315fa26a..d3f104ad5 100644 --- a/shell/reicast.vcxproj +++ b/shell/reicast.vcxproj @@ -140,6 +140,12 @@ true true + + true + true + true + true + true true @@ -157,6 +163,24 @@ true true + + true + true + true + true + + + true + true + true + true + + + true + true + true + true + @@ -281,6 +305,12 @@ + + true + true + true + true + true true @@ -290,6 +320,12 @@ + + true + true + true + true + @@ -310,6 +346,12 @@ true true + + true + true + true + true + {58B14048-EACB-4780-8B1E-9C84C2C30A8E} diff --git a/shell/reicast.vcxproj.filters b/shell/reicast.vcxproj.filters index 83249949a..b47ab6dcb 100644 --- a/shell/reicast.vcxproj.filters +++ b/shell/reicast.vcxproj.filters @@ -411,6 +411,18 @@ reios + + rec-x86 + + + rec-x86 + + + rec-x86 + + + linux + @@ -533,6 +545,9 @@ {f614dd66-5d30-4548-a209-f857f95fb505} + + {df854851-d3b5-4549-8248-acdfa954be44} + @@ -895,6 +910,12 @@ reios + + rec-x86 + + + linux + @@ -903,5 +924,8 @@ rec-ARM + + rec-x86 + \ No newline at end of file