1 /*
2  * Copyright (c) 2015, Marcos Medeiros
3  * Licensed under BSD 3-clause.
4  */
5 #ifndef MIPS3_X64
6 #define MIPS3_X64
7 
8 #include <unordered_map>
9 #include "xbyak/xbyak.h"
10 #include "../mips3.h"
11 
12 #ifdef HAS_UDIS86
13 #include "udis86/udis86.h"
14 #endif
15 
16 namespace mips
17 {
18 
19 
20 class mips3_x64 : public Xbyak::CodeGenerator
21 {
22 public:
23     mips3_x64(mips3 *interpreter);
24     void run(int cycles);
25 
26 private:
27     int64_t m_icounter;
28     addr_t m_drc_pc;
29     bool m_is_delay_slot;
30     void run_this(void *ptr);
31     void *compile_block(addr_t pc);
32     void *get_block(addr_t pc);
33     bool compile_special(uint32_t opcode);
34     bool compile_regimm(uint32_t opcode);
35     bool compile_instruction(uint32_t opcode);
36     bool compile_cop0(uint32_t opcode);
37     bool compile_cop1(uint32_t opcode);
38     void check_icounter();
39     bool cop1_fallback(uint32_t opcode);
40     void set_next_pc(addr_t addr);
41     void fallback(uint32_t opcode, void (mips3::*f)(uint32_t));
42     void update_icounter();
43     void jmp_to_block(uint64_t addr);
44     void jmp_to_register(int reg);
45     void translate_failed();
46     void update_cp0_count();
47     void prolog();
48     void epilog(bool do_ret=true);
49 
50     uint8_t *m_cache;
51     mips3 *m_core;
52     void *m_current_block;
53     uint64_t m_block_icounter;
54     bool m_translate_failed;
55     bool m_stop_translation;
56     unordered_map<addr_t, void(*)> m_blocks;
57 #ifdef HAS_UDIS86
58     ud_t m_udobj;
59 #endif
60 
61     // COP1 branch
62     bool BC1F(uint32_t opcode);
63     bool BC1FL(uint32_t opcode);
64     bool BC1T(uint32_t opcode);
65     bool BC1TL(uint32_t opcode);
66 
67     // Arithmetic
68     bool ADD(uint32_t opcode);
69     bool SUB(uint32_t opcode);
70     bool MULT(uint32_t opcode);
71     bool DIV(uint32_t opcode);
72     bool ADDU(uint32_t opcode);
73     bool SUBU(uint32_t opcode);
74     bool MULTU(uint32_t opcode);
75     bool DIVU(uint32_t opcode);
76 
77     bool ADDI(uint32_t opcode);
78     bool ADDIU(uint32_t opcode);
79     bool DADDI(uint32_t opcode);
80     bool DADDIU(uint32_t opcode);
81 
82     bool DADD(uint32_t opcode);
83     bool DSUB(uint32_t opcode);
84     bool DMULT(uint32_t opcode);
85     bool DDIV(uint32_t opcode);
86     bool DADDU(uint32_t opcode);
87     bool DSUBU(uint32_t opcode);
88     bool DMULTU(uint32_t opcode);
89     bool DDIVU(uint32_t opcode);
90 
91     // Bitwise
92     bool AND(uint32_t opcode);
93     bool XOR(uint32_t opcode);
94     bool OR(uint32_t opcode);
95     bool NOR(uint32_t opcode);
96     bool ANDI(uint32_t opcode);
97     bool XORI(uint32_t opcode);
98     bool ORI(uint32_t opcode);
99 
100     // Shifts
101     bool SLL(uint32_t opcode);
102     bool SRL(uint32_t opcode);
103     bool SRA(uint32_t opcode);
104     bool SLLV(uint32_t opcode);
105     bool SRLV(uint32_t opcode);
106     bool SRAV(uint32_t opcode);
107     bool DSLLV(uint32_t opcode);
108     bool DSLRV(uint32_t opcode);
109     bool SLT(uint32_t opcode);
110     bool SLTU(uint32_t opcode);
111     bool DSLL(uint32_t opcode);
112     bool DSRL(uint32_t opcode);
113     bool DSRA(uint32_t opcode);
114     bool DSRAV(uint32_t opcode);
115     bool DSLL32(uint32_t opcode);
116     bool DSRL32(uint32_t opcode);
117     bool DSRA32(uint32_t opcode);
118 
119     // Jump & Branchs
120     bool J(uint32_t opcode);
121     bool JR(uint32_t opcode);
122     bool JAL(uint32_t opcode);
123     bool JALR(uint32_t opcode);
124     bool BLTZ(uint32_t opcode);
125     bool BLTZAL(uint32_t opcode);
126     bool BGEZ(uint32_t opcode);
127     bool BGEZAL(uint32_t opcode);
128     bool BEQ(uint32_t opcode);
129     bool BNE(uint32_t opcode);
130     bool BLEZ(uint32_t opcode);
131     bool BGTZ(uint32_t opcode);
132 
133     // Load & Store
134     bool LUI(uint32_t opcode);
135     bool SB(uint32_t opcode);
136     bool SH(uint32_t opcode);
137     bool SW(uint32_t opcode);
138     bool SD(uint32_t opcode);
139     bool SDL(uint32_t opcode);
140     bool SDR(uint32_t opcode);
141     bool LWL(uint32_t opcode);
142     bool LWR(uint32_t opcode);
143     bool LDL(uint32_t opcode);
144     bool LDR(uint32_t opcode);
145     bool LB(uint32_t opcode);
146     bool LBU(uint32_t opcode);
147     bool LH(uint32_t opcode);
148     bool LHU(uint32_t opcode);
149     bool LW(uint32_t opcode);
150     bool LWU(uint32_t opcode);
151     bool LD(uint32_t opcode);
152     bool LL(uint32_t opcode);
153     bool LWC1(uint32_t opcode);
154     bool SWC1(uint32_t opcode);
155 
156     // Misc
157     bool SLTI(uint32_t opcode);
158     bool SLTIU(uint32_t opcode);
159     bool MFHI(uint32_t opcode);
160     bool MTHI(uint32_t opcode);
161     bool MFLO(uint32_t opcode);
162     bool MTLO(uint32_t opcode);
163 
164 };
165 
166 }
167 
168 #endif // MIPS3_X64
169 
170